ChoruYt commited on
Commit
239ce1c
·
verified ·
1 Parent(s): b7eaba9

Create cpu.js

Browse files
Files changed (1) hide show
  1. cpu.js +213 -0
cpu.js ADDED
@@ -0,0 +1,213 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const express = require('express');
2
+ const WebSocket = require('ws');
3
+ const os = require('os');
4
+ const app = express();
5
+
6
+ app.use(express.json({ limit: '10mb' }));
7
+
8
+ // Real CPU + System Metrics
9
+ function getCpuMetrics() {
10
+ const cpus = os.cpus();
11
+ const totalLoad = cpus.reduce((sum, cpu) => {
12
+ const total = Object.values(cpu.times).reduce((a, b) => a + b, 0);
13
+ const idle = cpu.times.idle;
14
+ return sum + (1 - idle / total);
15
+ }, 0) / cpus.length;
16
+
17
+ return {
18
+ id: process.env.WORKER_ID || 'cpu1',
19
+ hostname: os.hostname(),
20
+ totalMemory: Math.round(os.totalmem() / 1024 / 1024) + 'MB',
21
+ freeMemory: Math.round(os.freemem() / 1024 / 1024) + 'MB',
22
+ memoryUsage: Math.round((os.totalmem() - os.freemem()) / os.totalmem() * 100) + '%',
23
+ cpuCount: cpus.length,
24
+ cpuLoad: Math.round(totalLoad * 100),
25
+ uptime: Math.round(process.uptime() / 60) + 'min',
26
+ nodeVersion: process.version,
27
+ timestamp: Date.now()
28
+ };
29
+ }
30
+
31
+ // Broker connection
32
+ let broker = null;
33
+ let taskQueue = [];
34
+ let currentTask = null;
35
+ let lastHeartbeat = Date.now();
36
+
37
+ function connectBroker() {
38
+ const brokerHost = process.env.BROKER_HOST || 'wss://choruyt-broker-exocore.hf.space';
39
+ broker = new WebSocket(brokerHost);
40
+
41
+ broker.on('open', () => {
42
+ console.log(`✅ Broker connected - Worker ${getCpuMetrics().id}`);
43
+ broker.send(JSON.stringify({
44
+ type: 'register',
45
+ role: 'cpu_worker',
46
+ metrics: getCpuMetrics()
47
+ }));
48
+ });
49
+
50
+ broker.on('message', async (data) => {
51
+ const msg = JSON.parse(data.toString());
52
+
53
+ if (msg.type === 'cpu_task') {
54
+ if (!currentTask) {
55
+ currentTask = msg;
56
+ const result = await executeCpuTask(msg.task);
57
+
58
+ if (broker.readyState === WebSocket.OPEN) {
59
+ broker.send(JSON.stringify({
60
+ type: 'cpu_result',
61
+ taskId: msg.task.id,
62
+ result,
63
+ from: getCpuMetrics().id,
64
+ metrics: getCpuMetrics()
65
+ }));
66
+ }
67
+
68
+ currentTask = null;
69
+ processTaskQueue();
70
+ } else {
71
+ taskQueue.push(msg);
72
+ }
73
+ }
74
+ });
75
+
76
+ broker.on('close', () => {
77
+ console.log('🔌 Broker disconnected, reconnecting...');
78
+ setTimeout(connectBroker, 3000);
79
+ });
80
+
81
+ broker.on('error', (err) => {
82
+ console.log('Broker error:', err.message);
83
+ });
84
+ }
85
+
86
+ async function executeCpuTask(task) {
87
+ const startTime = Date.now();
88
+
89
+ try {
90
+ switch(task.type) {
91
+ case 'preprocess':
92
+ // Real tokenization + analysis
93
+ const tokens = tokenize(task.data);
94
+ const wordCount = task.data.split(/\s+/).length;
95
+ const charCount = task.data.length;
96
+
97
+ // CPU-intensive batch processing (non-blocking)
98
+ await cpuIntensiveWork(1000); // Simulate 1s CPU work
99
+
100
+ return {
101
+ cpuBoost: true,
102
+ metrics: getCpuMetrics(),
103
+ task: 'preprocess',
104
+ tokens,
105
+ wordCount,
106
+ charCount,
107
+ estimatedPromptTokens: Math.round(tokens * 1.3), // Rough embedding estimate
108
+ time: Date.now() - startTime
109
+ };
110
+
111
+ case 'embedding':
112
+ const vector = generateMockEmbedding(task.data);
113
+ await cpuIntensiveWork(2000);
114
+ return {
115
+ cpuBoost: true,
116
+ dim: vector.length,
117
+ time: Date.now() - startTime
118
+ };
119
+
120
+ default:
121
+ await cpuIntensiveWork(500);
122
+ return {
123
+ cpuBoost: true,
124
+ message: `Completed ${task.type}`,
125
+ time: Date.now() - startTime
126
+ };
127
+ }
128
+ } catch (e) {
129
+ return { cpuBoost: false, error: e.message, time: Date.now() - startTime };
130
+ }
131
+ }
132
+
133
+ // CPU work simulation (uses real CPU)
134
+ function cpuIntensiveWork(iterations) {
135
+ return new Promise(resolve => {
136
+ let i = 0;
137
+ function work() {
138
+ for (let j = 0; j < 10000; j++) {
139
+ Math.sqrt(Math.random() * iterations);
140
+ }
141
+ i++;
142
+ if (i < iterations / 10000) {
143
+ setImmediate(work);
144
+ } else {
145
+ resolve();
146
+ }
147
+ }
148
+ work();
149
+ });
150
+ }
151
+
152
+ // Simple tokenizer
153
+ function tokenize(text) {
154
+ return text.match(/[\w\d\s\u4e00-\u9fff\uac00-\ud7af]+/gi)?.length || 0;
155
+ }
156
+
157
+ function generateMockEmbedding(text) {
158
+ const hash = Array.from(text).reduce((a, c) => a + c.charCodeAt(0), 0);
159
+ return new Array(384).fill(0).map((_, i) =>
160
+ Math.sin(hash + i) * 0.1 + Math.random() * 0.1
161
+ );
162
+ }
163
+
164
+ function processTaskQueue() {
165
+ if (taskQueue.length > 0 && !currentTask && broker?.readyState === WebSocket.OPEN) {
166
+ const nextTask = taskQueue.shift();
167
+ broker.send(JSON.stringify(nextTask));
168
+ }
169
+ }
170
+
171
+ // Health endpoints
172
+ app.get('/', (req, res) => {
173
+ const metrics = getCpuMetrics();
174
+ res.json({
175
+ status: 'CPU Worker Active',
176
+ workerId: metrics.id,
177
+ ...metrics,
178
+ queueLength: taskQueue.length,
179
+ busy: !!currentTask,
180
+ connected: broker?.readyState === WebSocket.OPEN
181
+ });
182
+ });
183
+
184
+ app.get('/health', (req, res) => {
185
+ res.json({
186
+ status: 'ok',
187
+ cpuLoad: getCpuMetrics().cpuLoad,
188
+ memoryUsage: getCpuMetrics().memoryUsage
189
+ });
190
+ });
191
+
192
+ // Heartbeat
193
+ setInterval(() => {
194
+ if (broker?.readyState === WebSocket.OPEN) {
195
+ broker.send(JSON.stringify({
196
+ type: 'heartbeat',
197
+ metrics: getCpuMetrics()
198
+ }));
199
+ }
200
+ }, 30000);
201
+
202
+ // Startup
203
+ connectBroker();
204
+
205
+ const server = app.listen(7860, () => {
206
+ console.log(`🚀 CPU Worker ${getCpuMetrics().id} ready on port 7860`);
207
+ });
208
+
209
+ process.on('SIGTERM', () => {
210
+ console.log('Shutting down...');
211
+ if (broker) broker.close();
212
+ server.close(() => process.exit(0));
213
+ });