tuimon 0.1.0 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/AI.md +191 -0
- package/README.md +223 -87
- package/dist/browser.d.ts.map +1 -1
- package/dist/browser.js +3 -0
- package/dist/browser.js.map +1 -1
- package/dist/cli.js +171 -3
- package/dist/cli.js.map +1 -1
- package/dist/config.d.ts +17 -0
- package/dist/config.d.ts.map +1 -0
- package/dist/config.js +106 -0
- package/dist/config.js.map +1 -0
- package/dist/fkeybar.d.ts.map +1 -1
- package/dist/fkeybar.js +13 -0
- package/dist/fkeybar.js.map +1 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +148 -18
- package/dist/index.js.map +1 -1
- package/dist/layout/generator-css.d.ts +3 -0
- package/dist/layout/generator-css.d.ts.map +1 -0
- package/dist/layout/generator-css.js +202 -0
- package/dist/layout/generator-css.js.map +1 -0
- package/dist/layout/generator-js.d.ts +3 -0
- package/dist/layout/generator-js.d.ts.map +1 -0
- package/dist/layout/generator-js.js +353 -0
- package/dist/layout/generator-js.js.map +1 -0
- package/dist/layout/generator.d.ts +4 -0
- package/dist/layout/generator.d.ts.map +1 -0
- package/dist/layout/generator.js +124 -0
- package/dist/layout/generator.js.map +1 -0
- package/dist/layout/theme.d.ts +4 -0
- package/dist/layout/theme.d.ts.map +1 -0
- package/dist/layout/theme.js +28 -0
- package/dist/layout/theme.js.map +1 -0
- package/dist/layout/types.d.ts +68 -0
- package/dist/layout/types.d.ts.map +1 -0
- package/dist/layout/types.js +3 -0
- package/dist/layout/types.js.map +1 -0
- package/dist/quick/auto-layout.d.ts +5 -0
- package/dist/quick/auto-layout.d.ts.map +1 -0
- package/dist/quick/auto-layout.js +262 -0
- package/dist/quick/auto-layout.js.map +1 -0
- package/dist/quick/db/detect.d.ts +16 -0
- package/dist/quick/db/detect.d.ts.map +1 -0
- package/dist/quick/db/detect.js +131 -0
- package/dist/quick/db/detect.js.map +1 -0
- package/dist/quick/db/mongo.d.ts +10 -0
- package/dist/quick/db/mongo.d.ts.map +1 -0
- package/dist/quick/db/mongo.js +81 -0
- package/dist/quick/db/mongo.js.map +1 -0
- package/dist/quick/db/mysql.d.ts +8 -0
- package/dist/quick/db/mysql.d.ts.map +1 -0
- package/dist/quick/db/mysql.js +43 -0
- package/dist/quick/db/mysql.js.map +1 -0
- package/dist/quick/db/postgres.d.ts +8 -0
- package/dist/quick/db/postgres.d.ts.map +1 -0
- package/dist/quick/db/postgres.js +47 -0
- package/dist/quick/db/postgres.js.map +1 -0
- package/dist/quick/db/sqlite.d.ts +8 -0
- package/dist/quick/db/sqlite.d.ts.map +1 -0
- package/dist/quick/db/sqlite.js +43 -0
- package/dist/quick/db/sqlite.js.map +1 -0
- package/dist/quick/db-mode.d.ts +13 -0
- package/dist/quick/db-mode.d.ts.map +1 -0
- package/dist/quick/db-mode.js +159 -0
- package/dist/quick/db-mode.js.map +1 -0
- package/dist/quick/detect.d.ts +4 -0
- package/dist/quick/detect.d.ts.map +1 -0
- package/dist/quick/detect.js +76 -0
- package/dist/quick/detect.js.map +1 -0
- package/dist/quick/file-mode.d.ts +5 -0
- package/dist/quick/file-mode.d.ts.map +1 -0
- package/dist/quick/file-mode.js +158 -0
- package/dist/quick/file-mode.js.map +1 -0
- package/dist/quick/parsers/csv.d.ts +3 -0
- package/dist/quick/parsers/csv.d.ts.map +1 -0
- package/dist/quick/parsers/csv.js +145 -0
- package/dist/quick/parsers/csv.js.map +1 -0
- package/dist/quick/parsers/detect-meta.d.ts +7 -0
- package/dist/quick/parsers/detect-meta.d.ts.map +1 -0
- package/dist/quick/parsers/detect-meta.js +35 -0
- package/dist/quick/parsers/detect-meta.js.map +1 -0
- package/dist/quick/parsers/json.d.ts +3 -0
- package/dist/quick/parsers/json.d.ts.map +1 -0
- package/dist/quick/parsers/json.js +74 -0
- package/dist/quick/parsers/json.js.map +1 -0
- package/dist/quick/parsers/log.d.ts +3 -0
- package/dist/quick/parsers/log.d.ts.map +1 -0
- package/dist/quick/parsers/log.js +185 -0
- package/dist/quick/parsers/log.js.map +1 -0
- package/dist/quick/parsers/modsec.d.ts +3 -0
- package/dist/quick/parsers/modsec.d.ts.map +1 -0
- package/dist/quick/parsers/modsec.js +338 -0
- package/dist/quick/parsers/modsec.js.map +1 -0
- package/dist/quick/types.d.ts +90 -0
- package/dist/quick/types.d.ts.map +1 -0
- package/dist/quick/types.js +3 -0
- package/dist/quick/types.js.map +1 -0
- package/dist/quick/watch-mode.d.ts +3 -0
- package/dist/quick/watch-mode.d.ts.map +1 -0
- package/dist/quick/watch-mode.js +156 -0
- package/dist/quick/watch-mode.js.map +1 -0
- package/dist/server.js +2 -2
- package/dist/server.js.map +1 -1
- package/dist/types.d.ts +8 -1
- package/dist/types.d.ts.map +1 -1
- package/examples/demo.ts +134 -0
- package/examples/generate-access-log.ts +42 -0
- package/examples/screenshot-test.ts +105 -0
- package/examples/screenshot.png +0 -0
- package/frame-log.txt +830 -0
- package/package.json +10 -5
package/dist/server.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"server.js","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAA6C,MAAM,WAAW,CAAA;AACnF,OAAO,EAAE,YAAY,EAAE,UAAU,EAAE,MAAM,SAAS,CAAA;
|
|
1
|
+
{"version":3,"file":"server.js","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"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"}
|
package/dist/types.d.ts
CHANGED
|
@@ -7,7 +7,8 @@ export interface KeyBinding {
|
|
|
7
7
|
}
|
|
8
8
|
export type FKeyMap = Partial<Record<FKey, KeyBinding>>;
|
|
9
9
|
export interface PageConfig {
|
|
10
|
-
/** Absolute or cwd-relative path to the HTML file for this page
|
|
10
|
+
/** Absolute or cwd-relative path to the HTML file for this page.
|
|
11
|
+
* Required unless `layout` is provided — layout pages generate HTML automatically. */
|
|
11
12
|
html: string;
|
|
12
13
|
/** If true, this is the starting page. Exactly one page must be default. */
|
|
13
14
|
default?: boolean;
|
|
@@ -26,6 +27,9 @@ export interface PageConfig {
|
|
|
26
27
|
* and TuiMon will log a warning at startup.
|
|
27
28
|
*/
|
|
28
29
|
keys?: FKeyMap;
|
|
30
|
+
/** Declarative layout config — if provided, TuiMon generates the HTML automatically.
|
|
31
|
+
* Cannot be used together with `html` on the same page. */
|
|
32
|
+
layout?: import('./layout/types.js').LayoutConfig;
|
|
29
33
|
}
|
|
30
34
|
export type PageMap = Record<string, PageConfig>;
|
|
31
35
|
export interface TuiMonOptions {
|
|
@@ -87,6 +91,7 @@ export interface BrowserHandle {
|
|
|
87
91
|
pushData: (data: Record<string, unknown>) => Promise<void>;
|
|
88
92
|
navigate: (url: string) => Promise<void>;
|
|
89
93
|
resize: (width: number, height: number) => Promise<void>;
|
|
94
|
+
evaluate: (expression: string) => Promise<void>;
|
|
90
95
|
close: () => Promise<void>;
|
|
91
96
|
}
|
|
92
97
|
export interface FKeyBarHandle {
|
|
@@ -94,6 +99,8 @@ export interface FKeyBarHandle {
|
|
|
94
99
|
setKeys: (keys: FKeyMap) => void;
|
|
95
100
|
/** Show a temporary message in the bar for duration ms */
|
|
96
101
|
notify: (message: string, duration?: number) => void;
|
|
102
|
+
/** Force redraw the bar at current position */
|
|
103
|
+
redraw: () => void;
|
|
97
104
|
stop: () => void;
|
|
98
105
|
}
|
|
99
106
|
export interface KeyHandlerHandle {
|
package/dist/types.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"AAEA,MAAM,MAAM,IAAI,GACZ,IAAI,GAAG,IAAI,GAAG,IAAI,GAAG,IAAI,GAAG,IAAI,GAAG,IAAI,GACvC,IAAI,GAAG,IAAI,GAAG,IAAI,GAAG,KAAK,GAAG,KAAK,GAAG,KAAK,CAAA;AAE9C,gEAAgE;AAChE,MAAM,MAAM,WAAW,GAAG,MAAM,CAAA;AAEhC,MAAM,WAAW,UAAU;IACzB,KAAK,EAAE,MAAM,CAAA;IACb,MAAM,EAAE,MAAM,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAAA;CACnC;AAED,MAAM,MAAM,OAAO,GAAG,OAAO,CAAC,MAAM,CAAC,IAAI,EAAE,UAAU,CAAC,CAAC,CAAA;AAIvD,MAAM,WAAW,UAAU;IACzB
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"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"}
|
package/examples/demo.ts
ADDED
|
@@ -0,0 +1,134 @@
|
|
|
1
|
+
#!/usr/bin/env npx tsx
|
|
2
|
+
|
|
3
|
+
import tuimon from '../src/index.js'
|
|
4
|
+
import { cpus, freemem, totalmem, loadavg } from 'node:os'
|
|
5
|
+
|
|
6
|
+
// ─── Fake data generators ────────────────────────────────────────────────────
|
|
7
|
+
|
|
8
|
+
const logs: string[] = []
|
|
9
|
+
let reqTotal = 0
|
|
10
|
+
|
|
11
|
+
function getCpuPercent(): number {
|
|
12
|
+
const list = cpus()
|
|
13
|
+
const total = list.reduce((a, c) => a + Object.values(c.times).reduce((x, y) => x + y, 0), 0)
|
|
14
|
+
const idle = list.reduce((a, c) => a + c.times.idle, 0)
|
|
15
|
+
return Math.round(100 - (idle / total) * 100)
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
function getMemPercent(): number {
|
|
19
|
+
return Math.round(((totalmem() - freemem()) / totalmem()) * 100)
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
function formatUptime(s: number): string {
|
|
23
|
+
const h = Math.floor(s / 3600)
|
|
24
|
+
const m = Math.floor((s % 3600) / 60)
|
|
25
|
+
return `${h}h ${m}m`
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
// ─── Start dashboard ─────────────────────────────────────────────────────────
|
|
29
|
+
|
|
30
|
+
const dash = await tuimon.start({
|
|
31
|
+
pages: {
|
|
32
|
+
overview: {
|
|
33
|
+
html: '', // will be overridden by layout
|
|
34
|
+
default: true,
|
|
35
|
+
label: 'Overview',
|
|
36
|
+
layout: {
|
|
37
|
+
title: 'TuiMon Demo',
|
|
38
|
+
stats: [
|
|
39
|
+
{ id: 'cpu', label: 'CPU', type: 'gauge' },
|
|
40
|
+
{ id: 'mem', label: 'Memory', type: 'gauge' },
|
|
41
|
+
{ id: 'reqs', label: 'Requests/s', type: 'stat' },
|
|
42
|
+
{ id: 'uptime', label: 'Uptime', type: 'stat' },
|
|
43
|
+
],
|
|
44
|
+
panels: [
|
|
45
|
+
{ id: 'traffic', label: 'Real-Time Traffic', type: 'line', span: 2 },
|
|
46
|
+
{ id: 'health', label: 'Node Health', type: 'status-grid', throttle: 5000 },
|
|
47
|
+
{ id: 'endpoints', label: 'Endpoint Distribution', type: 'doughnut', throttle: 3000 },
|
|
48
|
+
{ id: 'events', label: 'Recent Events', type: 'event-log', throttle: 2000 },
|
|
49
|
+
{ id: 'methods', label: 'HTTP Methods', type: 'bar', throttle: 1000 },
|
|
50
|
+
],
|
|
51
|
+
},
|
|
52
|
+
keys: {
|
|
53
|
+
F5: {
|
|
54
|
+
label: 'Force Refresh',
|
|
55
|
+
action: async () => { await dash.render(getData()) },
|
|
56
|
+
},
|
|
57
|
+
F10: {
|
|
58
|
+
label: 'Quit',
|
|
59
|
+
action: () => { process.exit(0) },
|
|
60
|
+
},
|
|
61
|
+
},
|
|
62
|
+
},
|
|
63
|
+
},
|
|
64
|
+
|
|
65
|
+
refresh: 250,
|
|
66
|
+
renderDelay: 0,
|
|
67
|
+
data: () => getData(),
|
|
68
|
+
})
|
|
69
|
+
|
|
70
|
+
function getData(): Record<string, unknown> {
|
|
71
|
+
const cpu = getCpuPercent()
|
|
72
|
+
const mem = getMemPercent()
|
|
73
|
+
const reqRate = Math.round(80 + Math.random() * 300)
|
|
74
|
+
reqTotal += reqRate
|
|
75
|
+
|
|
76
|
+
// Random events
|
|
77
|
+
if (Math.random() > 0.7) {
|
|
78
|
+
const events = [
|
|
79
|
+
{ text: 'Deploy completed successfully', type: 'success' as const },
|
|
80
|
+
{ text: `Request spike: ${reqRate} req/s`, type: 'warning' as const },
|
|
81
|
+
{ text: 'Health check passed', type: 'info' as const },
|
|
82
|
+
{ text: 'Cache cleared', type: 'info' as const },
|
|
83
|
+
{ text: 'Connection pool resized', type: 'warning' as const },
|
|
84
|
+
]
|
|
85
|
+
const evt = events[Math.floor(Math.random() * events.length)]!
|
|
86
|
+
logs.unshift(evt)
|
|
87
|
+
if (logs.length > 15) logs.pop()
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
// Simulate node health
|
|
91
|
+
const nodes = ['Node-1', 'Node-2', 'Node-3', 'Node-4', 'Node-5'].map((label) => {
|
|
92
|
+
const r = Math.random()
|
|
93
|
+
const status = r > 0.95 ? 'error' as const : r > 0.85 ? 'warn' as const : 'ok' as const
|
|
94
|
+
return { label, status }
|
|
95
|
+
})
|
|
96
|
+
|
|
97
|
+
return {
|
|
98
|
+
// Stats — lazy format (just numbers)
|
|
99
|
+
cpu,
|
|
100
|
+
mem,
|
|
101
|
+
reqs: { value: reqRate, trend: reqRate > 200 ? '+' + reqRate : '', unit: 'req/s' },
|
|
102
|
+
uptime: formatUptime(Math.round(process.uptime())),
|
|
103
|
+
|
|
104
|
+
// Line chart — key:value pairs, TuiMon accumulates history
|
|
105
|
+
traffic: {
|
|
106
|
+
Requests: reqRate,
|
|
107
|
+
Errors: Math.round(Math.random() * 8),
|
|
108
|
+
Latency: Math.round(20 + Math.random() * 60),
|
|
109
|
+
},
|
|
110
|
+
|
|
111
|
+
// Status grid — detailed format
|
|
112
|
+
health: nodes,
|
|
113
|
+
|
|
114
|
+
// Doughnut — key:value pairs
|
|
115
|
+
endpoints: {
|
|
116
|
+
'/api/users': 340,
|
|
117
|
+
'/api/posts': 220,
|
|
118
|
+
'/api/auth': 180,
|
|
119
|
+
'/health': 90,
|
|
120
|
+
'/ws': 45,
|
|
121
|
+
},
|
|
122
|
+
|
|
123
|
+
// Event log — detailed format
|
|
124
|
+
events: logs,
|
|
125
|
+
|
|
126
|
+
// Bar chart — key:value pairs
|
|
127
|
+
methods: {
|
|
128
|
+
GET: Math.round(200 + Math.random() * 100),
|
|
129
|
+
POST: Math.round(50 + Math.random() * 80),
|
|
130
|
+
PUT: Math.round(10 + Math.random() * 30),
|
|
131
|
+
DELETE: Math.round(5 + Math.random() * 15),
|
|
132
|
+
},
|
|
133
|
+
}
|
|
134
|
+
}
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
#!/usr/bin/env npx tsx
|
|
2
|
+
|
|
3
|
+
// Generates a realistic nginx access.log with 1000 entries
|
|
4
|
+
import { writeFileSync } from 'node:fs'
|
|
5
|
+
|
|
6
|
+
const methods = ['GET', 'GET', 'GET', 'GET', 'POST', 'POST', 'PUT', 'DELETE']
|
|
7
|
+
const paths = [
|
|
8
|
+
'/api/users', '/api/users/123', '/api/posts', '/api/posts/456',
|
|
9
|
+
'/api/auth/login', '/api/auth/logout', '/api/comments',
|
|
10
|
+
'/health', '/metrics', '/api/orders', '/api/products',
|
|
11
|
+
'/static/app.js', '/static/style.css', '/images/logo.png',
|
|
12
|
+
'/admin', '/admin/users', '/api/search?q=test',
|
|
13
|
+
]
|
|
14
|
+
const statuses = [200, 200, 200, 200, 200, 201, 204, 301, 304, 400, 401, 403, 404, 404, 500, 502]
|
|
15
|
+
const agents = [
|
|
16
|
+
'Mozilla/5.0 (Windows NT 10.0; Win64; x64) Chrome/120.0',
|
|
17
|
+
'Mozilla/5.0 (Macintosh; Intel Mac OS X 14_0) Safari/17.0',
|
|
18
|
+
'curl/7.88.0',
|
|
19
|
+
'PostmanRuntime/7.36.0',
|
|
20
|
+
'python-requests/2.31.0',
|
|
21
|
+
'Googlebot/2.1',
|
|
22
|
+
]
|
|
23
|
+
|
|
24
|
+
const lines: string[] = []
|
|
25
|
+
const baseTime = new Date('2026-04-04T10:00:00Z')
|
|
26
|
+
|
|
27
|
+
for (let i = 0; i < 1000; i++) {
|
|
28
|
+
const time = new Date(baseTime.getTime() + i * 3600) // ~1 per 3.6 seconds
|
|
29
|
+
const ip = `${10 + Math.floor(Math.random() * 240)}.${Math.floor(Math.random() * 256)}.${Math.floor(Math.random() * 256)}.${Math.floor(Math.random() * 256)}`
|
|
30
|
+
const method = methods[Math.floor(Math.random() * methods.length)]!
|
|
31
|
+
const path = paths[Math.floor(Math.random() * paths.length)]!
|
|
32
|
+
const status = statuses[Math.floor(Math.random() * statuses.length)]!
|
|
33
|
+
const bytes = Math.floor(Math.random() * 50000)
|
|
34
|
+
const agent = agents[Math.floor(Math.random() * agents.length)]!
|
|
35
|
+
const ts = time.toISOString().replace('T', ':').replace(/\.\d+Z/, ' +0000')
|
|
36
|
+
|
|
37
|
+
lines.push(`${ip} - - [${ts}] "${method} ${path} HTTP/1.1" ${status} ${bytes} "-" "${agent}"`)
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
const outPath = '/tmp/access.log'
|
|
41
|
+
writeFileSync(outPath, lines.join('\n') + '\n')
|
|
42
|
+
console.log(`Generated ${lines.length} log entries at ${outPath}`)
|
|
@@ -0,0 +1,105 @@
|
|
|
1
|
+
#!/usr/bin/env npx tsx
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Takes a screenshot of the default template with dummy data
|
|
5
|
+
* and saves it to examples/screenshot.png — open in any image viewer.
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
import { writeFileSync, mkdirSync, writeFileSync as wf } from 'node:fs'
|
|
9
|
+
import path from 'node:path'
|
|
10
|
+
import { tmpdir } from 'node:os'
|
|
11
|
+
import { chromium } from 'playwright'
|
|
12
|
+
import { generateDashboardHtml } from '../src/layout/generator.js'
|
|
13
|
+
import type { LayoutConfig } from '../src/layout/types.js'
|
|
14
|
+
|
|
15
|
+
const layout: LayoutConfig = {
|
|
16
|
+
title: 'TuiMon Demo',
|
|
17
|
+
stats: [
|
|
18
|
+
{ id: 'cpu', label: 'CPU', type: 'gauge' },
|
|
19
|
+
{ id: 'mem', label: 'Memory', type: 'gauge' },
|
|
20
|
+
{ id: 'reqs', label: 'Requests/s', type: 'stat' },
|
|
21
|
+
{ id: 'uptime', label: 'Uptime', type: 'stat' },
|
|
22
|
+
],
|
|
23
|
+
panels: [
|
|
24
|
+
{ id: 'traffic', label: 'Real-Time Traffic', type: 'line', span: 2 },
|
|
25
|
+
{ id: 'health', label: 'Node Health', type: 'status-grid' },
|
|
26
|
+
{ id: 'endpoints', label: 'Endpoint Distribution', type: 'doughnut' },
|
|
27
|
+
{ id: 'events', label: 'Recent Events', type: 'event-log' },
|
|
28
|
+
{ id: 'methods', label: 'HTTP Methods', type: 'bar' },
|
|
29
|
+
],
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
// Generate HTML
|
|
33
|
+
const html = generateDashboardHtml(layout)
|
|
34
|
+
const tmpDir = path.join(tmpdir(), `tuimon-screenshot-${Date.now()}`)
|
|
35
|
+
mkdirSync(tmpDir, { recursive: true })
|
|
36
|
+
const htmlPath = path.join(tmpDir, 'dashboard.html')
|
|
37
|
+
writeFileSync(htmlPath, html, 'utf-8')
|
|
38
|
+
|
|
39
|
+
console.log('Launching browser...')
|
|
40
|
+
|
|
41
|
+
const browser = await chromium.launch({ headless: true })
|
|
42
|
+
const page = await browser.newPage()
|
|
43
|
+
await page.setViewportSize({ width: 1600, height: 900 })
|
|
44
|
+
await page.goto(`file://${htmlPath}`, { waitUntil: 'domcontentloaded' })
|
|
45
|
+
|
|
46
|
+
// Push some dummy data a few times to build chart history
|
|
47
|
+
for (let i = 0; i < 30; i++) {
|
|
48
|
+
await page.evaluate((data: Record<string, unknown>) => {
|
|
49
|
+
const win = globalThis as Record<string, unknown>
|
|
50
|
+
if (typeof win['__tuimon_update__'] === 'function') {
|
|
51
|
+
;(win['__tuimon_update__'] as (d: Record<string, unknown>) => void)(data)
|
|
52
|
+
}
|
|
53
|
+
}, {
|
|
54
|
+
cpu: 35 + Math.round(Math.random() * 40),
|
|
55
|
+
mem: 55 + Math.round(Math.random() * 20),
|
|
56
|
+
reqs: { value: Math.round(100 + Math.random() * 300), trend: '+12', unit: 'req/s' },
|
|
57
|
+
uptime: '2h 15m',
|
|
58
|
+
traffic: {
|
|
59
|
+
Requests: Math.round(100 + Math.random() * 250),
|
|
60
|
+
Errors: Math.round(Math.random() * 15),
|
|
61
|
+
Latency: Math.round(20 + Math.random() * 60),
|
|
62
|
+
},
|
|
63
|
+
health: [
|
|
64
|
+
{ label: 'Node-1', status: 'ok' },
|
|
65
|
+
{ label: 'Node-2', status: 'ok' },
|
|
66
|
+
{ label: 'Node-3', status: Math.random() > 0.5 ? 'warn' : 'ok' },
|
|
67
|
+
{ label: 'Node-4', status: 'ok' },
|
|
68
|
+
{ label: 'Node-5', status: Math.random() > 0.8 ? 'error' : 'ok' },
|
|
69
|
+
],
|
|
70
|
+
endpoints: {
|
|
71
|
+
'/api/users': 340,
|
|
72
|
+
'/api/posts': 220,
|
|
73
|
+
'/api/auth': 180,
|
|
74
|
+
'/health': 90,
|
|
75
|
+
'/ws': 45,
|
|
76
|
+
},
|
|
77
|
+
events: [
|
|
78
|
+
{ text: 'Deploy completed successfully', type: 'success', time: '2:50 PM' },
|
|
79
|
+
{ text: 'Request spike detected: 342 req/s', type: 'warning', time: '2:48 PM' },
|
|
80
|
+
{ text: 'Health check passed all nodes', type: 'info', time: '2:45 PM' },
|
|
81
|
+
{ text: 'Cache cleared — 2.3GB freed', type: 'info', time: '2:42 PM' },
|
|
82
|
+
{ text: 'Connection timeout to DB replica', type: 'error', time: '2:40 PM' },
|
|
83
|
+
{ text: 'Auto-scaled to 5 replicas', type: 'success', time: '2:38 PM' },
|
|
84
|
+
],
|
|
85
|
+
methods: {
|
|
86
|
+
GET: Math.round(200 + Math.random() * 100),
|
|
87
|
+
POST: Math.round(50 + Math.random() * 80),
|
|
88
|
+
PUT: Math.round(10 + Math.random() * 30),
|
|
89
|
+
DELETE: Math.round(5 + Math.random() * 15),
|
|
90
|
+
},
|
|
91
|
+
})
|
|
92
|
+
await new Promise((r) => setTimeout(r, 50))
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
// Wait for charts to render
|
|
96
|
+
await new Promise((r) => setTimeout(r, 500))
|
|
97
|
+
|
|
98
|
+
// Take screenshot
|
|
99
|
+
const outPath = path.resolve('examples/screenshot.png')
|
|
100
|
+
const buf = await page.screenshot({ type: 'png' })
|
|
101
|
+
writeFileSync(outPath, buf)
|
|
102
|
+
|
|
103
|
+
await browser.close()
|
|
104
|
+
console.log(`Screenshot saved to: ${outPath}`)
|
|
105
|
+
console.log('Open it in your image viewer or VS Code to see the dashboard.')
|
|
Binary file
|