@reskill/agent-aware-server 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/dist/cli.d.ts ADDED
@@ -0,0 +1,10 @@
1
+ #!/usr/bin/env node
2
+ /**
3
+ * Agent-aware CLI
4
+ * 启动 HTTP Server
5
+ *
6
+ * 使用方式:
7
+ * npx agent-aware-server start
8
+ */
9
+ export {};
10
+ //# sourceMappingURL=cli.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cli.d.ts","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":";AACA;;;;;;GAMG"}
package/dist/cli.js ADDED
@@ -0,0 +1,69 @@
1
+ #!/usr/bin/env node
2
+ /**
3
+ * Agent-aware CLI
4
+ * 启动 HTTP Server
5
+ *
6
+ * 使用方式:
7
+ * npx agent-aware-server start
8
+ */
9
+ import { serve } from '@hono/node-server';
10
+ import { createHttpApi } from './httpApi.js';
11
+ import { BehaviorStore } from './store/behaviorStore.js';
12
+ const HTTP_PORT = 4100;
13
+ const DATA_DIR = './data';
14
+ function start() {
15
+ const store = new BehaviorStore(DATA_DIR);
16
+ const app = createHttpApi(store);
17
+ console.log(`
18
+ ╔═══════════════════════════════════════════════════════════╗
19
+ ║ ║
20
+ ║ Agent-aware Server ║
21
+ ║ ║
22
+ ║ HTTP API: http://localhost:${HTTP_PORT} ║
23
+ ║ ║
24
+ ║ Endpoints: ║
25
+ ║ POST /behaviors - SDK 上报行为数据 ║
26
+ ║ GET /behaviors - 查询行为列表 ║
27
+ ║ GET /summary - 获取行为摘要 ║
28
+ ║ GET /hotspots - 获取交互热点 ║
29
+ ║ DELETE /behaviors - 清空数据 ║
30
+ ║ ║
31
+ ╚═══════════════════════════════════════════════════════════╝
32
+ `);
33
+ serve({
34
+ fetch: app.fetch,
35
+ port: HTTP_PORT,
36
+ });
37
+ console.log('[AgentAware] Server started');
38
+ }
39
+ function showHelp() {
40
+ console.log(`
41
+ Agent-aware CLI
42
+
43
+ 用法:
44
+ npx agent-aware-server <command>
45
+
46
+ 命令:
47
+ start 启动 HTTP Server(默认端口 4100)
48
+
49
+ 示例:
50
+ npx agent-aware-server start
51
+ `);
52
+ }
53
+ // 主入口
54
+ const command = process.argv[2];
55
+ switch (command) {
56
+ case 'start':
57
+ case undefined:
58
+ start();
59
+ break;
60
+ case '--help':
61
+ case '-h':
62
+ showHelp();
63
+ break;
64
+ default:
65
+ console.error(`未知命令: ${command}`);
66
+ showHelp();
67
+ process.exit(1);
68
+ }
69
+ //# sourceMappingURL=cli.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cli.js","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":";AACA;;;;;;GAMG;AAEH,OAAO,EAAE,KAAK,EAAE,MAAM,mBAAmB,CAAA;AACzC,OAAO,EAAE,aAAa,EAAE,MAAM,cAAc,CAAA;AAC5C,OAAO,EAAE,aAAa,EAAE,MAAM,0BAA0B,CAAA;AAExD,MAAM,SAAS,GAAG,IAAI,CAAA;AACtB,MAAM,QAAQ,GAAG,QAAQ,CAAA;AAEzB,SAAS,KAAK;IACZ,MAAM,KAAK,GAAG,IAAI,aAAa,CAAC,QAAQ,CAAC,CAAA;IACzC,MAAM,GAAG,GAAG,aAAa,CAAC,KAAK,CAAC,CAAA;IAEhC,OAAO,CAAC,GAAG,CAAC;;;;;iCAKmB,SAAS;;;;;;;;;;CAUzC,CAAC,CAAA;IAEA,KAAK,CAAC;QACJ,KAAK,EAAE,GAAG,CAAC,KAAK;QAChB,IAAI,EAAE,SAAS;KAChB,CAAC,CAAA;IAEF,OAAO,CAAC,GAAG,CAAC,6BAA6B,CAAC,CAAA;AAC5C,CAAC;AAED,SAAS,QAAQ;IACf,OAAO,CAAC,GAAG,CAAC;;;;;;;;;;;CAWb,CAAC,CAAA;AACF,CAAC;AAED,MAAM;AACN,MAAM,OAAO,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;AAE/B,QAAQ,OAAO,EAAE,CAAC;IAChB,KAAK,OAAO,CAAC;IACb,KAAK,SAAS;QACZ,KAAK,EAAE,CAAA;QACP,MAAK;IACP,KAAK,QAAQ,CAAC;IACd,KAAK,IAAI;QACP,QAAQ,EAAE,CAAA;QACV,MAAK;IACP;QACE,OAAO,CAAC,KAAK,CAAC,SAAS,OAAO,EAAE,CAAC,CAAA;QACjC,QAAQ,EAAE,CAAA;QACV,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;AACnB,CAAC"}
@@ -0,0 +1,11 @@
1
+ /**
2
+ * HTTP API
3
+ * 基于 SPEC-SRV-001
4
+ *
5
+ * 支持 SDK 上报和 AI 查询
6
+ */
7
+ import { Hono } from 'hono';
8
+ import type { BehaviorStore } from './store/behaviorStore';
9
+ import type { ErrorStore } from './store/errorStore';
10
+ export declare function createHttpApi(store: BehaviorStore, errorStore?: ErrorStore): Hono;
11
+ //# sourceMappingURL=httpApi.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"httpApi.d.ts","sourceRoot":"","sources":["../src/httpApi.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,EAAE,IAAI,EAAE,MAAM,MAAM,CAAA;AAE3B,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,uBAAuB,CAAA;AAC1D,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAA;AAWpD,wBAAgB,aAAa,CAAC,KAAK,EAAE,aAAa,EAAE,UAAU,CAAC,EAAE,UAAU,GAAG,IAAI,CAoIjF"}
@@ -0,0 +1,116 @@
1
+ /**
2
+ * HTTP API
3
+ * 基于 SPEC-SRV-001
4
+ *
5
+ * 支持 SDK 上报和 AI 查询
6
+ */
7
+ import { Hono } from 'hono';
8
+ import { cors } from 'hono/cors';
9
+ export function createHttpApi(store, errorStore) {
10
+ const app = new Hono();
11
+ // 启用 CORS - 允许所有来源(开发环境)
12
+ // 使用动态 origin 回显请求的 Origin,以支持 credentials 模式
13
+ app.use('/*', cors({
14
+ origin: (origin) => origin || '*', // 回显请求的 Origin,如果没有则用 *
15
+ allowMethods: ['GET', 'POST', 'DELETE', 'OPTIONS'],
16
+ allowHeaders: ['Content-Type'],
17
+ exposeHeaders: ['Content-Length'],
18
+ maxAge: 600,
19
+ credentials: true, // 支持携带 Cookie
20
+ }));
21
+ // ============ SDK 上报 ============
22
+ // POST /behaviors - 接收行为数据
23
+ app.post('/behaviors', async (c) => {
24
+ try {
25
+ const body = await c.req.json();
26
+ const behaviors = body.behaviors || [];
27
+ await store.addBatch(behaviors);
28
+ const response = {
29
+ ok: true,
30
+ count: behaviors.length,
31
+ };
32
+ return c.json(response);
33
+ }
34
+ catch (error) {
35
+ return c.json({ ok: false, error: 'Invalid JSON' }, 400);
36
+ }
37
+ });
38
+ // ============ AI 查询 ============
39
+ // GET /behaviors - 查询行为数据
40
+ app.get('/behaviors', async (c) => {
41
+ const typesParam = c.req.query('types');
42
+ const limitParam = c.req.query('limit');
43
+ const types = typesParam ? typesParam.split(',') : undefined;
44
+ const limit = limitParam ? parseInt(limitParam, 10) : undefined;
45
+ const behaviors = await store.query({ types, limit });
46
+ return c.json(behaviors);
47
+ });
48
+ // GET /summary - 获取行为摘要
49
+ app.get('/summary', async (c) => {
50
+ const summary = await store.getSummary();
51
+ return c.json(summary);
52
+ });
53
+ // GET /hotspots - 获取热点区域
54
+ app.get('/hotspots', async (c) => {
55
+ const limitParam = c.req.query('limit');
56
+ const limit = limitParam ? parseInt(limitParam, 10) : undefined;
57
+ const hotspots = await store.getHotspots(limit);
58
+ return c.json(hotspots);
59
+ });
60
+ // GET /health - 健康检查
61
+ app.get('/health', async (c) => {
62
+ const summary = await store.getSummary();
63
+ const response = {
64
+ status: 'ok',
65
+ totalInteractions: summary.totalInteractions,
66
+ };
67
+ return c.json(response);
68
+ });
69
+ // DELETE /behaviors - 清空数据
70
+ app.delete('/behaviors', async (c) => {
71
+ await store.clear();
72
+ return c.json({ ok: true });
73
+ });
74
+ // ============ Errors API ============
75
+ if (errorStore) {
76
+ // POST /errors - 接收错误数据
77
+ app.post('/errors', async (c) => {
78
+ try {
79
+ const body = await c.req.json();
80
+ const errors = body.errors || [];
81
+ await errorStore.addBatch(errors);
82
+ const response = {
83
+ ok: true,
84
+ count: errors.length,
85
+ };
86
+ return c.json(response);
87
+ }
88
+ catch (error) {
89
+ return c.json({ ok: false, error: 'Invalid JSON' }, 400);
90
+ }
91
+ });
92
+ // GET /errors - 查询错误数据
93
+ app.get('/errors', async (c) => {
94
+ const errorTypesParam = c.req.query('errorTypes');
95
+ const limitParam = c.req.query('limit');
96
+ const errorTypes = errorTypesParam
97
+ ? errorTypesParam.split(',')
98
+ : undefined;
99
+ const limit = limitParam ? parseInt(limitParam, 10) : undefined;
100
+ const errors = await errorStore.query({ errorTypes, limit });
101
+ return c.json(errors);
102
+ });
103
+ // GET /errors/summary - 获取错误摘要
104
+ app.get('/errors/summary', async (c) => {
105
+ const summary = await errorStore.getSummary();
106
+ return c.json(summary);
107
+ });
108
+ // DELETE /errors - 清空错误数据
109
+ app.delete('/errors', async (c) => {
110
+ await errorStore.clear();
111
+ return c.json({ ok: true });
112
+ });
113
+ }
114
+ return app;
115
+ }
116
+ //# sourceMappingURL=httpApi.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"httpApi.js","sourceRoot":"","sources":["../src/httpApi.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,6 @@
1
+ /**
2
+ * Agent-aware Server 入口
3
+ * HTTP Server (Hono)
4
+ */
5
+ export {};
6
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;GAGG"}
package/dist/index.js ADDED
@@ -0,0 +1,28 @@
1
+ /**
2
+ * Agent-aware Server 入口
3
+ * HTTP Server (Hono)
4
+ */
5
+ import { serve } from '@hono/node-server';
6
+ import { createHttpApi } from './httpApi';
7
+ import { BehaviorStore } from './store/behaviorStore';
8
+ import { ErrorStore } from './store/errorStore';
9
+ const PORT = 4100;
10
+ const DATA_DIR = './data';
11
+ const store = new BehaviorStore(DATA_DIR);
12
+ const errorStore = new ErrorStore(DATA_DIR);
13
+ const app = createHttpApi(store, errorStore);
14
+ console.log(`[AgentAware Server] Starting on port ${PORT}...`);
15
+ serve({
16
+ fetch: app.fetch,
17
+ port: PORT,
18
+ });
19
+ console.log(`[AgentAware Server] HTTP API listening on http://localhost:${PORT}`);
20
+ console.log(`[AgentAware Server] Endpoints:`);
21
+ console.log(` POST /behaviors - 接收行为数据`);
22
+ console.log(` GET /health - 健康检查`);
23
+ console.log(` DELETE /behaviors - 清空行为数据`);
24
+ console.log(` POST /errors - 接收错误数据`);
25
+ console.log(` GET /errors - 查询错误数据`);
26
+ console.log(` GET /errors/summary - 获取错误摘要`);
27
+ console.log(` DELETE /errors - 清空错误数据`);
28
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,EAAE,KAAK,EAAE,MAAM,mBAAmB,CAAA;AACzC,OAAO,EAAE,aAAa,EAAE,MAAM,WAAW,CAAA;AACzC,OAAO,EAAE,aAAa,EAAE,MAAM,uBAAuB,CAAA;AACrD,OAAO,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAA;AAE/C,MAAM,IAAI,GAAG,IAAI,CAAA;AACjB,MAAM,QAAQ,GAAG,QAAQ,CAAA;AAEzB,MAAM,KAAK,GAAG,IAAI,aAAa,CAAC,QAAQ,CAAC,CAAA;AACzC,MAAM,UAAU,GAAG,IAAI,UAAU,CAAC,QAAQ,CAAC,CAAA;AAC3C,MAAM,GAAG,GAAG,aAAa,CAAC,KAAK,EAAE,UAAU,CAAC,CAAA;AAE5C,OAAO,CAAC,GAAG,CAAC,wCAAwC,IAAI,KAAK,CAAC,CAAA;AAE9D,KAAK,CAAC;IACJ,KAAK,EAAE,GAAG,CAAC,KAAK;IAChB,IAAI,EAAE,IAAI;CACX,CAAC,CAAA;AAEF,OAAO,CAAC,GAAG,CAAC,8DAA8D,IAAI,EAAE,CAAC,CAAA;AACjF,OAAO,CAAC,GAAG,CAAC,gCAAgC,CAAC,CAAA;AAC7C,OAAO,CAAC,GAAG,CAAC,oCAAoC,CAAC,CAAA;AACjD,OAAO,CAAC,GAAG,CAAC,kCAAkC,CAAC,CAAA;AAC/C,OAAO,CAAC,GAAG,CAAC,oCAAoC,CAAC,CAAA;AACjD,OAAO,CAAC,GAAG,CAAC,oCAAoC,CAAC,CAAA;AACjD,OAAO,CAAC,GAAG,CAAC,oCAAoC,CAAC,CAAA;AACjD,OAAO,CAAC,GAAG,CAAC,oCAAoC,CAAC,CAAA;AACjD,OAAO,CAAC,GAAG,CAAC,oCAAoC,CAAC,CAAA"}
@@ -0,0 +1,43 @@
1
+ /**
2
+ * BehaviorStore - 行为数据存储
3
+ * 基于 SPEC-SRV-002
4
+ */
5
+ import type { Behavior, QueryOptions, Summary, Hotspot } from '../types';
6
+ export declare class BehaviorStore {
7
+ private dataDir;
8
+ private filePath;
9
+ constructor(dataDir?: string);
10
+ /**
11
+ * 添加单条行为
12
+ */
13
+ add(behavior: Behavior): Promise<void>;
14
+ /**
15
+ * 批量添加行为
16
+ */
17
+ addBatch(newBehaviors: Behavior[]): Promise<void>;
18
+ /**
19
+ * 查询行为
20
+ */
21
+ query(options?: QueryOptions): Promise<Behavior[]>;
22
+ /**
23
+ * 获取摘要
24
+ */
25
+ getSummary(): Promise<Summary>;
26
+ /**
27
+ * 获取热点区域
28
+ */
29
+ getHotspots(limit?: number): Promise<Hotspot[]>;
30
+ /**
31
+ * 清空数据
32
+ */
33
+ clear(): Promise<void>;
34
+ /**
35
+ * 读取数据文件
36
+ */
37
+ private read;
38
+ /**
39
+ * 写入数据文件
40
+ */
41
+ private write;
42
+ }
43
+ //# sourceMappingURL=behaviorStore.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"behaviorStore.d.ts","sourceRoot":"","sources":["../../src/store/behaviorStore.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAIH,OAAO,KAAK,EACV,QAAQ,EAER,YAAY,EACZ,OAAO,EACP,OAAO,EACR,MAAM,UAAU,CAAA;AAMjB,qBAAa,aAAa;IACxB,OAAO,CAAC,OAAO,CAAQ;IACvB,OAAO,CAAC,QAAQ,CAAQ;gBAEZ,OAAO,GAAE,MAAiB;IAKtC;;OAEG;IACG,GAAG,CAAC,QAAQ,EAAE,QAAQ,GAAG,OAAO,CAAC,IAAI,CAAC;IAI5C;;OAEG;IACG,QAAQ,CAAC,YAAY,EAAE,QAAQ,EAAE,GAAG,OAAO,CAAC,IAAI,CAAC;IAYvD;;OAEG;IACG,KAAK,CAAC,OAAO,GAAE,YAAiB,GAAG,OAAO,CAAC,QAAQ,EAAE,CAAC;IAe5D;;OAEG;IACG,UAAU,IAAI,OAAO,CAAC,OAAO,CAAC;IAwBpC;;OAEG;IACG,WAAW,CAAC,KAAK,GAAE,MAAU,GAAG,OAAO,CAAC,OAAO,EAAE,CAAC;IAiCxD;;OAEG;IACG,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC;IAI5B;;OAEG;YACW,IAAI;IAUlB;;OAEG;YACW,KAAK;CAKpB"}
@@ -0,0 +1,126 @@
1
+ /**
2
+ * BehaviorStore - 行为数据存储
3
+ * 基于 SPEC-SRV-002
4
+ */
5
+ import { readFile, writeFile, mkdir } from 'node:fs/promises';
6
+ import { join } from 'node:path';
7
+ const DATA_FILE = 'behaviors.json';
8
+ const MAX_BEHAVIORS = 1000;
9
+ const STORAGE_VERSION = '1.0';
10
+ export class BehaviorStore {
11
+ constructor(dataDir = './data') {
12
+ this.dataDir = dataDir;
13
+ this.filePath = join(dataDir, DATA_FILE);
14
+ }
15
+ /**
16
+ * 添加单条行为
17
+ */
18
+ async add(behavior) {
19
+ await this.addBatch([behavior]);
20
+ }
21
+ /**
22
+ * 批量添加行为
23
+ */
24
+ async addBatch(newBehaviors) {
25
+ const data = await this.read();
26
+ data.behaviors.push(...newBehaviors);
27
+ // 限制数量
28
+ while (data.behaviors.length > MAX_BEHAVIORS) {
29
+ data.behaviors.shift();
30
+ }
31
+ await this.write(data);
32
+ }
33
+ /**
34
+ * 查询行为
35
+ */
36
+ async query(options = {}) {
37
+ const { types, limit = 50 } = options;
38
+ const data = await this.read();
39
+ let results = data.behaviors;
40
+ // 按类型过滤
41
+ if (types && types.length > 0) {
42
+ results = results.filter((b) => types.includes(b.type));
43
+ }
44
+ // 返回最新的 N 条
45
+ return results.slice(-limit);
46
+ }
47
+ /**
48
+ * 获取摘要
49
+ */
50
+ async getSummary() {
51
+ const data = await this.read();
52
+ const behaviors = data.behaviors;
53
+ const totalInteractions = behaviors.length;
54
+ const rageClickCount = behaviors.filter((b) => b.type === 'rage_click').length;
55
+ const deadClickCount = behaviors.filter((b) => b.type === 'dead_click').length;
56
+ const totalClicks = behaviors.filter((b) => ['click', 'rage_click', 'dead_click'].includes(b.type)).length;
57
+ const frustrationScore = totalClicks > 0
58
+ ? Math.min(100, Math.round(((rageClickCount + deadClickCount) / totalClicks) * 100))
59
+ : 0;
60
+ return {
61
+ totalInteractions,
62
+ frustrationScore,
63
+ rageClickCount,
64
+ deadClickCount,
65
+ };
66
+ }
67
+ /**
68
+ * 获取热点区域
69
+ */
70
+ async getHotspots(limit = 5) {
71
+ const data = await this.read();
72
+ // 按 selector 分组统计
73
+ const selectorStats = new Map();
74
+ for (const behavior of data.behaviors) {
75
+ const selector = behavior.target.selector;
76
+ const existing = selectorStats.get(selector);
77
+ if (existing) {
78
+ existing.count++;
79
+ }
80
+ else {
81
+ selectorStats.set(selector, {
82
+ count: 1,
83
+ name: behavior.target.name,
84
+ });
85
+ }
86
+ }
87
+ // 转换并排序
88
+ const hotspots = Array.from(selectorStats.entries())
89
+ .map(([selector, stats]) => ({
90
+ selector,
91
+ name: stats.name,
92
+ interactionCount: stats.count,
93
+ }))
94
+ .sort((a, b) => b.interactionCount - a.interactionCount)
95
+ .slice(0, limit);
96
+ return hotspots;
97
+ }
98
+ /**
99
+ * 清空数据
100
+ */
101
+ async clear() {
102
+ await this.write({ version: STORAGE_VERSION, behaviors: [] });
103
+ }
104
+ /**
105
+ * 读取数据文件
106
+ */
107
+ async read() {
108
+ try {
109
+ const content = await readFile(this.filePath, 'utf-8');
110
+ return JSON.parse(content);
111
+ }
112
+ catch {
113
+ // 文件不存在或损坏,返回空数据
114
+ return { version: STORAGE_VERSION, behaviors: [] };
115
+ }
116
+ }
117
+ /**
118
+ * 写入数据文件
119
+ */
120
+ async write(data) {
121
+ // 确保目录存在
122
+ await mkdir(this.dataDir, { recursive: true });
123
+ await writeFile(this.filePath, JSON.stringify(data, null, 2), 'utf-8');
124
+ }
125
+ }
126
+ //# sourceMappingURL=behaviorStore.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"behaviorStore.js","sourceRoot":"","sources":["../../src/store/behaviorStore.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,39 @@
1
+ /**
2
+ * ErrorStore - 错误数据存储
3
+ * 基于 SPEC-SRV-003: Errors API
4
+ */
5
+ import type { ErrorRecord, ErrorQueryOptions, ErrorSummary } from '../types';
6
+ export declare class ErrorStore {
7
+ private dataDir;
8
+ private filePath;
9
+ constructor(dataDir?: string);
10
+ /**
11
+ * 添加单条错误
12
+ */
13
+ add(error: ErrorRecord): Promise<void>;
14
+ /**
15
+ * 批量添加错误
16
+ */
17
+ addBatch(newErrors: ErrorRecord[]): Promise<void>;
18
+ /**
19
+ * 查询错误
20
+ */
21
+ query(options?: ErrorQueryOptions): Promise<ErrorRecord[]>;
22
+ /**
23
+ * 获取错误摘要
24
+ */
25
+ getSummary(): Promise<ErrorSummary>;
26
+ /**
27
+ * 清空数据
28
+ */
29
+ clear(): Promise<void>;
30
+ /**
31
+ * 读取数据文件
32
+ */
33
+ private read;
34
+ /**
35
+ * 写入数据文件
36
+ */
37
+ private write;
38
+ }
39
+ //# sourceMappingURL=errorStore.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"errorStore.d.ts","sourceRoot":"","sources":["../../src/store/errorStore.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAIH,OAAO,KAAK,EACV,WAAW,EAEX,iBAAiB,EACjB,YAAY,EACb,MAAM,UAAU,CAAA;AAMjB,qBAAa,UAAU;IACrB,OAAO,CAAC,OAAO,CAAQ;IACvB,OAAO,CAAC,QAAQ,CAAQ;gBAEZ,OAAO,GAAE,MAAiB;IAKtC;;OAEG;IACG,GAAG,CAAC,KAAK,EAAE,WAAW,GAAG,OAAO,CAAC,IAAI,CAAC;IAI5C;;OAEG;IACG,QAAQ,CAAC,SAAS,EAAE,WAAW,EAAE,GAAG,OAAO,CAAC,IAAI,CAAC;IAYvD;;OAEG;IACG,KAAK,CAAC,OAAO,GAAE,iBAAsB,GAAG,OAAO,CAAC,WAAW,EAAE,CAAC;IAepE;;OAEG;IACG,UAAU,IAAI,OAAO,CAAC,YAAY,CAAC;IAuBzC;;OAEG;IACG,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC;IAI5B;;OAEG;YACW,IAAI;IAUlB;;OAEG;YACW,KAAK;CAKpB"}
@@ -0,0 +1,95 @@
1
+ /**
2
+ * ErrorStore - 错误数据存储
3
+ * 基于 SPEC-SRV-003: Errors API
4
+ */
5
+ import { readFile, writeFile, mkdir } from 'node:fs/promises';
6
+ import { join } from 'node:path';
7
+ const DATA_FILE = 'errors.json';
8
+ const MAX_ERRORS = 1000;
9
+ const STORAGE_VERSION = '1.0';
10
+ export class ErrorStore {
11
+ constructor(dataDir = './data') {
12
+ this.dataDir = dataDir;
13
+ this.filePath = join(dataDir, DATA_FILE);
14
+ }
15
+ /**
16
+ * 添加单条错误
17
+ */
18
+ async add(error) {
19
+ await this.addBatch([error]);
20
+ }
21
+ /**
22
+ * 批量添加错误
23
+ */
24
+ async addBatch(newErrors) {
25
+ const data = await this.read();
26
+ data.errors.push(...newErrors);
27
+ // 限制数量
28
+ while (data.errors.length > MAX_ERRORS) {
29
+ data.errors.shift();
30
+ }
31
+ await this.write(data);
32
+ }
33
+ /**
34
+ * 查询错误
35
+ */
36
+ async query(options = {}) {
37
+ const { errorTypes, limit = 50 } = options;
38
+ const data = await this.read();
39
+ let results = data.errors;
40
+ // 按类型过滤
41
+ if (errorTypes && errorTypes.length > 0) {
42
+ results = results.filter((e) => errorTypes.includes(e.errorType));
43
+ }
44
+ // 返回最新的 N 条
45
+ return results.slice(-limit);
46
+ }
47
+ /**
48
+ * 获取错误摘要
49
+ */
50
+ async getSummary() {
51
+ const data = await this.read();
52
+ const errors = data.errors;
53
+ const totalErrors = errors.length;
54
+ const runtimeErrorCount = errors.filter((e) => e.errorType === 'runtime').length;
55
+ const unhandledRejectionCount = errors.filter((e) => e.errorType === 'unhandled_rejection').length;
56
+ const consoleErrorCount = errors.filter((e) => e.errorType === 'console').length;
57
+ // 最近 5 条错误
58
+ const recentErrors = errors.slice(-5);
59
+ return {
60
+ totalErrors,
61
+ runtimeErrorCount,
62
+ unhandledRejectionCount,
63
+ consoleErrorCount,
64
+ recentErrors,
65
+ };
66
+ }
67
+ /**
68
+ * 清空数据
69
+ */
70
+ async clear() {
71
+ await this.write({ version: STORAGE_VERSION, errors: [] });
72
+ }
73
+ /**
74
+ * 读取数据文件
75
+ */
76
+ async read() {
77
+ try {
78
+ const content = await readFile(this.filePath, 'utf-8');
79
+ return JSON.parse(content);
80
+ }
81
+ catch {
82
+ // 文件不存在或损坏,返回空数据
83
+ return { version: STORAGE_VERSION, errors: [] };
84
+ }
85
+ }
86
+ /**
87
+ * 写入数据文件
88
+ */
89
+ async write(data) {
90
+ // 确保目录存在
91
+ await mkdir(this.dataDir, { recursive: true });
92
+ await writeFile(this.filePath, JSON.stringify(data, null, 2), 'utf-8');
93
+ }
94
+ }
95
+ //# sourceMappingURL=errorStore.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"errorStore.js","sourceRoot":"","sources":["../../src/store/errorStore.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,95 @@
1
+ /**
2
+ * Server 端类型定义
3
+ */
4
+ export type BehaviorType = 'click' | 'rage_click' | 'dead_click' | 'scroll' | 'hover' | 'edit';
5
+ export type FrustrationType = 'rage_click' | 'dead_click' | 'error_click';
6
+ export type ErrorType = 'runtime' | 'unhandled_rejection' | 'console';
7
+ export interface Behavior {
8
+ id: string;
9
+ timestamp: number;
10
+ sessionId: string;
11
+ type: BehaviorType;
12
+ target: {
13
+ selector: string;
14
+ tagName: string;
15
+ name?: string;
16
+ };
17
+ position?: {
18
+ x: number;
19
+ y: number;
20
+ };
21
+ data: Record<string, unknown>;
22
+ semanticHints?: string[];
23
+ }
24
+ export interface StorageData {
25
+ version: string;
26
+ behaviors: Behavior[];
27
+ }
28
+ export interface QueryOptions {
29
+ types?: BehaviorType[];
30
+ limit?: number;
31
+ }
32
+ export interface Summary {
33
+ totalInteractions: number;
34
+ frustrationScore: number;
35
+ rageClickCount: number;
36
+ deadClickCount: number;
37
+ }
38
+ export interface Hotspot {
39
+ selector: string;
40
+ name?: string;
41
+ interactionCount: number;
42
+ }
43
+ export interface BehaviorsRequest {
44
+ behaviors: Behavior[];
45
+ }
46
+ export interface BehaviorsResponse {
47
+ ok: boolean;
48
+ count: number;
49
+ }
50
+ export interface HealthResponse {
51
+ status: 'ok';
52
+ totalInteractions: number;
53
+ }
54
+ export interface ErrorRecord {
55
+ id: string;
56
+ timestamp: number;
57
+ sessionId: string;
58
+ type: 'error';
59
+ errorType: ErrorType;
60
+ error: {
61
+ message: string;
62
+ stack?: string;
63
+ source?: 'source' | 'console';
64
+ handling?: 'handled' | 'unhandled';
65
+ };
66
+ context?: {
67
+ url?: string;
68
+ line?: number;
69
+ column?: number;
70
+ };
71
+ semanticHints?: string[];
72
+ }
73
+ export interface ErrorStorageData {
74
+ version: string;
75
+ errors: ErrorRecord[];
76
+ }
77
+ export interface ErrorQueryOptions {
78
+ errorTypes?: ErrorType[];
79
+ limit?: number;
80
+ }
81
+ export interface ErrorSummary {
82
+ totalErrors: number;
83
+ runtimeErrorCount: number;
84
+ unhandledRejectionCount: number;
85
+ consoleErrorCount: number;
86
+ recentErrors: ErrorRecord[];
87
+ }
88
+ export interface ErrorsRequest {
89
+ errors: ErrorRecord[];
90
+ }
91
+ export interface ErrorsResponse {
92
+ ok: boolean;
93
+ count: number;
94
+ }
95
+ //# sourceMappingURL=types.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"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"}
package/dist/types.js ADDED
@@ -0,0 +1,5 @@
1
+ /**
2
+ * Server 端类型定义
3
+ */
4
+ export {};
5
+ //# sourceMappingURL=types.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.js","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"AAAA;;GAEG"}
package/package.json ADDED
@@ -0,0 +1,52 @@
1
+ {
2
+ "name": "@reskill/agent-aware-server",
3
+ "version": "0.2.0",
4
+ "description": "Agent-aware RUM Server - HTTP API for user behavior tracking",
5
+ "type": "module",
6
+ "main": "./dist/index.js",
7
+ "types": "./dist/index.d.ts",
8
+ "bin": {
9
+ "agent-aware-server": "./dist/cli.js"
10
+ },
11
+ "files": [
12
+ "dist"
13
+ ],
14
+ "repository": {
15
+ "type": "git",
16
+ "url": "git+https://github.com/kanyun-inc/agent-aware.git",
17
+ "directory": "packages/server"
18
+ },
19
+ "author": "Kanyun Inc",
20
+ "license": "MIT",
21
+ "bugs": {
22
+ "url": "https://github.com/kanyun-inc/agent-aware/issues"
23
+ },
24
+ "homepage": "https://github.com/kanyun-inc/agent-aware/tree/main/packages/server#readme",
25
+ "dependencies": {
26
+ "@hono/node-server": "^1.13.0",
27
+ "hono": "^4.0.0"
28
+ },
29
+ "devDependencies": {
30
+ "@types/node": "^20.10.0",
31
+ "tsx": "^4.7.0",
32
+ "typescript": "^5.3.0",
33
+ "vitest": "^2.1.0"
34
+ },
35
+ "keywords": [
36
+ "rum",
37
+ "agent-aware",
38
+ "user-behavior",
39
+ "ai"
40
+ ],
41
+ "publishConfig": {
42
+ "access": "public"
43
+ },
44
+ "scripts": {
45
+ "build": "tsc",
46
+ "dev": "tsx watch src/index.ts",
47
+ "start": "node dist/index.js",
48
+ "test": "vitest run",
49
+ "test:watch": "vitest",
50
+ "typecheck": "tsc --noEmit"
51
+ }
52
+ }