pi-maestro-mobile 0.1.2

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.
Files changed (110) hide show
  1. package/README.md +85 -0
  2. package/dist/cli.d.ts +3 -0
  3. package/dist/cli.d.ts.map +1 -0
  4. package/dist/cli.js +84 -0
  5. package/dist/cli.js.map +1 -0
  6. package/dist/event-log.d.ts +18 -0
  7. package/dist/event-log.d.ts.map +1 -0
  8. package/dist/event-log.js +31 -0
  9. package/dist/event-log.js.map +1 -0
  10. package/dist/extension.d.ts +3 -0
  11. package/dist/extension.d.ts.map +1 -0
  12. package/dist/extension.js +118 -0
  13. package/dist/extension.js.map +1 -0
  14. package/dist/host-controller.d.ts +69 -0
  15. package/dist/host-controller.d.ts.map +1 -0
  16. package/dist/host-controller.js +195 -0
  17. package/dist/host-controller.js.map +1 -0
  18. package/dist/index.d.ts +11 -0
  19. package/dist/index.d.ts.map +1 -0
  20. package/dist/index.js +12 -0
  21. package/dist/index.js.map +1 -0
  22. package/dist/jsonl-index.d.ts +19 -0
  23. package/dist/jsonl-index.d.ts.map +1 -0
  24. package/dist/jsonl-index.js +84 -0
  25. package/dist/jsonl-index.js.map +1 -0
  26. package/dist/jsonl-pager.d.ts +29 -0
  27. package/dist/jsonl-pager.d.ts.map +1 -0
  28. package/dist/jsonl-pager.js +237 -0
  29. package/dist/jsonl-pager.js.map +1 -0
  30. package/dist/jsonl-replay.d.ts +9 -0
  31. package/dist/jsonl-replay.d.ts.map +1 -0
  32. package/dist/jsonl-replay.js +140 -0
  33. package/dist/jsonl-replay.js.map +1 -0
  34. package/dist/live-sessions.d.ts +47 -0
  35. package/dist/live-sessions.d.ts.map +1 -0
  36. package/dist/live-sessions.js +201 -0
  37. package/dist/live-sessions.js.map +1 -0
  38. package/dist/maestro-settings.d.ts +40 -0
  39. package/dist/maestro-settings.d.ts.map +1 -0
  40. package/dist/maestro-settings.js +122 -0
  41. package/dist/maestro-settings.js.map +1 -0
  42. package/dist/maestro-state.d.ts +31 -0
  43. package/dist/maestro-state.d.ts.map +1 -0
  44. package/dist/maestro-state.js +219 -0
  45. package/dist/maestro-state.js.map +1 -0
  46. package/dist/mobile-agent.d.ts +86 -0
  47. package/dist/mobile-agent.d.ts.map +1 -0
  48. package/dist/mobile-agent.js +2 -0
  49. package/dist/mobile-agent.js.map +1 -0
  50. package/dist/mobile-ui-context.d.ts +26 -0
  51. package/dist/mobile-ui-context.d.ts.map +1 -0
  52. package/dist/mobile-ui-context.js +164 -0
  53. package/dist/mobile-ui-context.js.map +1 -0
  54. package/dist/monitor-projection.d.ts +19 -0
  55. package/dist/monitor-projection.d.ts.map +1 -0
  56. package/dist/monitor-projection.js +79 -0
  57. package/dist/monitor-projection.js.map +1 -0
  58. package/dist/pi/pi-sdk-runtime.d.ts +17 -0
  59. package/dist/pi/pi-sdk-runtime.d.ts.map +1 -0
  60. package/dist/pi/pi-sdk-runtime.js +57 -0
  61. package/dist/pi/pi-sdk-runtime.js.map +1 -0
  62. package/dist/server/helpers.d.ts +23 -0
  63. package/dist/server/helpers.d.ts.map +1 -0
  64. package/dist/server/helpers.js +179 -0
  65. package/dist/server/helpers.js.map +1 -0
  66. package/dist/server/mobile-host-server.d.ts +43 -0
  67. package/dist/server/mobile-host-server.d.ts.map +1 -0
  68. package/dist/server/mobile-host-server.js +715 -0
  69. package/dist/server/mobile-host-server.js.map +1 -0
  70. package/dist/server/ws-command-handlers.d.ts +18 -0
  71. package/dist/server/ws-command-handlers.d.ts.map +1 -0
  72. package/dist/server/ws-command-handlers.js +173 -0
  73. package/dist/server/ws-command-handlers.js.map +1 -0
  74. package/dist/session-runner.d.ts +130 -0
  75. package/dist/session-runner.d.ts.map +1 -0
  76. package/dist/session-runner.js +576 -0
  77. package/dist/session-runner.js.map +1 -0
  78. package/dist/types.d.ts +83 -0
  79. package/dist/types.d.ts.map +1 -0
  80. package/dist/types.js +2 -0
  81. package/dist/types.js.map +1 -0
  82. package/dist/usage-reader.d.ts +49 -0
  83. package/dist/usage-reader.d.ts.map +1 -0
  84. package/dist/usage-reader.js +189 -0
  85. package/dist/usage-reader.js.map +1 -0
  86. package/dist/vendor/shared/index.d.ts +4 -0
  87. package/dist/vendor/shared/index.d.ts.map +1 -0
  88. package/dist/vendor/shared/index.js +4 -0
  89. package/dist/vendor/shared/index.js.map +1 -0
  90. package/dist/vendor/shared/protocol.d.ts +471 -0
  91. package/dist/vendor/shared/protocol.d.ts.map +1 -0
  92. package/dist/vendor/shared/protocol.js +34 -0
  93. package/dist/vendor/shared/protocol.js.map +1 -0
  94. package/dist/vendor/shared/timeline.d.ts +15 -0
  95. package/dist/vendor/shared/timeline.d.ts.map +1 -0
  96. package/dist/vendor/shared/timeline.js +21 -0
  97. package/dist/vendor/shared/timeline.js.map +1 -0
  98. package/dist/vendor/shared/validation.d.ts +8 -0
  99. package/dist/vendor/shared/validation.d.ts.map +1 -0
  100. package/dist/vendor/shared/validation.js +25 -0
  101. package/dist/vendor/shared/validation.js.map +1 -0
  102. package/dist/version-detector.d.ts +36 -0
  103. package/dist/version-detector.d.ts.map +1 -0
  104. package/dist/version-detector.js +141 -0
  105. package/dist/version-detector.js.map +1 -0
  106. package/dist/workspace-telemetry.d.ts +10 -0
  107. package/dist/workspace-telemetry.d.ts.map +1 -0
  108. package/dist/workspace-telemetry.js +84 -0
  109. package/dist/workspace-telemetry.js.map +1 -0
  110. package/package.json +64 -0
@@ -0,0 +1,141 @@
1
+ /**
2
+ * version-detector — 探测 Pi / pi-maestro-flow / Maestro CLI 版本
3
+ *
4
+ * 多路径回退,兼容宿主机与 Docker 两种部署形态:
5
+ * 1. 宿主全局安装:~/.pi/agent/npm/node_modules/<pkg>/package.json(pi 生态扩展)
6
+ * 2. 自身依赖:Node 解析本进程 node_modules 里的包(容器/纯净环境)
7
+ * 3. CLI 执行:execFile("<bin>", ["--version"])(最后兜底,仅在路径探测失败时)
8
+ *
9
+ * 所有探测在 Host 启动时执行一次并缓存,运行中不重复探测。
10
+ */
11
+ import { readFile } from "node:fs/promises";
12
+ import { join } from "node:path";
13
+ import { homedir } from "node:os";
14
+ import { execFile } from "node:child_process";
15
+ /** package.json 中提取 version(接受字符串或已解析对象;空/异常安全) */
16
+ function readPkgVersion(raw) {
17
+ try {
18
+ const pkg = typeof raw === "string" ? JSON.parse(raw) : raw;
19
+ return typeof pkg.version === "string" && pkg.version.length > 0 ? pkg.version : undefined;
20
+ }
21
+ catch {
22
+ return undefined;
23
+ }
24
+ }
25
+ async function versionFromPkgPath(pkgPath) {
26
+ try {
27
+ return readPkgVersion(await readFile(pkgPath, "utf8"));
28
+ }
29
+ catch {
30
+ return undefined;
31
+ }
32
+ }
33
+ /** pi 扩展目录候选:macOS/Linux 均默认 ~/.pi/agent/npm/node_modules/<pkg> */
34
+ function piAgentModulePath(pkgName) {
35
+ return join(homedir(), ".pi", "agent", "npm", "node_modules", pkgName, "package.json");
36
+ }
37
+ /** execFile 兜底:bin 不存在/超时均返回 undefined(3s 超时,版本命令无 stdin 输入)
38
+ * Windows:npm 全局 bin 是 pi.cmd / maestro.cmd,无 shell 的 execFile("pi") 找不到 .cmd —— 先探测 .cmd 再回退裸名 */
39
+ function binVersion(bin) {
40
+ if (process.platform === "win32") {
41
+ return binVersionRaw(`${bin}.cmd`).then((v) => v ?? binVersionRaw(bin));
42
+ }
43
+ return binVersionRaw(bin);
44
+ }
45
+ function binVersionRaw(bin) {
46
+ return new Promise((resolve) => {
47
+ const child = execFile(bin, ["--version"], { timeout: 3000 }, (error, stdout) => {
48
+ if (error)
49
+ return resolve(undefined);
50
+ const v = String(stdout).trim().split(/\s+/).pop();
51
+ resolve(v && /^\d/.test(v) ? v : undefined);
52
+ });
53
+ child.on("error", () => resolve(undefined));
54
+ });
55
+ }
56
+ export class VersionDetector {
57
+ cache = null;
58
+ detecting = null;
59
+ /** 探测(结果缓存;并发调用共享同一次探测) */
60
+ async detect() {
61
+ if (this.cache)
62
+ return this.cache;
63
+ if (!this.detecting) {
64
+ this.detecting = this.detectOnce().then((v) => {
65
+ this.cache = v;
66
+ this.detecting = null;
67
+ return v;
68
+ });
69
+ }
70
+ return this.detecting;
71
+ }
72
+ /** 测试注入用:清空缓存 */
73
+ reset() {
74
+ this.cache = null;
75
+ this.detecting = null;
76
+ }
77
+ async detectOnce() {
78
+ const [piVersion, flowVersion, maestroCliVersion] = await Promise.all([
79
+ this.detectPi(),
80
+ this.detectFlow(),
81
+ this.detectMaestroCli(),
82
+ ]);
83
+ return {
84
+ ...(piVersion ? { piVersion } : {}),
85
+ ...(flowVersion ? { flowVersion } : {}),
86
+ ...(maestroCliVersion ? { maestroCliVersion } : {}),
87
+ };
88
+ }
89
+ /** Pi:自身依赖(host 直接依赖 SDK,最可靠)→ 宿主 ~/.pi 目录 → pi bin */
90
+ async detectPi() {
91
+ return (await this.selfDependencyVersion("@earendil-works/pi-coding-agent")
92
+ ?? await versionFromPkgPath(piAgentModulePath("@earendil-works/pi-coding-agent"))
93
+ ?? await binVersion("pi"));
94
+ }
95
+ /** pi-maestro-flow:宿主 ~/.pi 目录(扩展安装位置)→ 自身依赖 */
96
+ async detectFlow() {
97
+ return (await versionFromPkgPath(piAgentModulePath("pi-maestro-flow"))
98
+ ?? await this.selfDependencyVersion("pi-maestro-flow"));
99
+ }
100
+ /** Maestro CLI:npm -g maestro-flow → bin 兜底 */
101
+ async detectMaestroCli() {
102
+ return (await this.globalModuleVersion("maestro-flow")
103
+ ?? await binVersion("maestro"));
104
+ }
105
+ /** 本进程 node_modules 依赖版本(createRequire 链式向上解析) */
106
+ selfDependencyVersion(pkgName) {
107
+ return (async () => {
108
+ try {
109
+ const { createRequire } = await import("node:module");
110
+ const require = createRequire(import.meta.url);
111
+ return readPkgVersion(require(`${pkgName}/package.json`));
112
+ }
113
+ catch {
114
+ return undefined;
115
+ }
116
+ })();
117
+ }
118
+ /** npm 全局目录探测(macOS homebrew / Linux nvm 路径差异大,仅试常见前缀) */
119
+ async globalModuleVersion(pkgName) {
120
+ // 覆盖 macOS(homebrew/自定义 PREFIX)、Linux(/usr/local、nvm)与 Windows(%APPDATA%\npm)
121
+ const prefixes = [];
122
+ if (process.env.PREFIX)
123
+ prefixes.push(process.env.PREFIX);
124
+ if (process.env.APPDATA)
125
+ prefixes.push(join(process.env.APPDATA, "npm"));
126
+ prefixes.push("/opt/homebrew/lib/node_modules", "/usr/local/lib/node_modules");
127
+ for (const prefix of prefixes) {
128
+ const v = await versionFromPkgPath(join(prefix, pkgName, "package.json"));
129
+ if (v)
130
+ return v;
131
+ }
132
+ return undefined;
133
+ }
134
+ }
135
+ /** 便捷函数:探测全部组件版本(内部自带缓存语义) */
136
+ export async function detectComponentVersions(detector) {
137
+ return detector.detect();
138
+ }
139
+ /** 测试导出:Windows .cmd 探测路径 */
140
+ export const binVersionForTest = binVersion;
141
+ //# sourceMappingURL=version-detector.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"version-detector.js","sourceRoot":"","sources":["../src/version-detector.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AACH,OAAO,EAAE,QAAQ,EAAE,MAAM,kBAAkB,CAAC;AAC5C,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AACjC,OAAO,EAAE,OAAO,EAAE,MAAM,SAAS,CAAC;AAClC,OAAO,EAAE,QAAQ,EAAE,MAAM,oBAAoB,CAAC;AAW9C,mDAAmD;AACnD,SAAS,cAAc,CAAC,GAAmC;IACzD,IAAI,CAAC;QACH,MAAM,GAAG,GAAG,OAAO,GAAG,KAAK,QAAQ,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,GAAG,CAA0B,CAAC,CAAC,CAAC,GAAG,CAAC;QACrF,OAAO,OAAO,GAAG,CAAC,OAAO,KAAK,QAAQ,IAAI,GAAG,CAAC,OAAO,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC,CAAC,SAAS,CAAC;IAC7F,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,SAAS,CAAC;IACnB,CAAC;AACH,CAAC;AAED,KAAK,UAAU,kBAAkB,CAAC,OAAe;IAC/C,IAAI,CAAC;QACH,OAAO,cAAc,CAAC,MAAM,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC,CAAC,CAAC;IACzD,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,SAAS,CAAC;IACnB,CAAC;AACH,CAAC;AAED,mEAAmE;AACnE,SAAS,iBAAiB,CAAC,OAAe;IACxC,OAAO,IAAI,CAAC,OAAO,EAAE,EAAE,KAAK,EAAE,OAAO,EAAE,KAAK,EAAE,cAAc,EAAE,OAAO,EAAE,cAAc,CAAC,CAAC;AACzF,CAAC;AAED;mGACmG;AACnG,SAAS,UAAU,CAAC,GAAW;IAC7B,IAAI,OAAO,CAAC,QAAQ,KAAK,OAAO,EAAE,CAAC;QACjC,OAAO,aAAa,CAAC,GAAG,GAAG,MAAM,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,IAAI,aAAa,CAAC,GAAG,CAAC,CAAC,CAAC;IAC1E,CAAC;IACD,OAAO,aAAa,CAAC,GAAG,CAAC,CAAC;AAC5B,CAAC;AAED,SAAS,aAAa,CAAC,GAAW;IAChC,OAAO,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,EAAE;QAC7B,MAAM,KAAK,GAAG,QAAQ,CAAC,GAAG,EAAE,CAAC,WAAW,CAAC,EAAE,EAAE,OAAO,EAAE,IAAI,EAAE,EAAE,CAAC,KAAK,EAAE,MAAM,EAAE,EAAE;YAC9E,IAAI,KAAK;gBAAE,OAAO,OAAO,CAAC,SAAS,CAAC,CAAC;YACrC,MAAM,CAAC,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,IAAI,EAAE,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC,GAAG,EAAE,CAAC;YACnD,OAAO,CAAC,CAAC,IAAI,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC;QAC9C,CAAC,CAAC,CAAC;QACH,KAAK,CAAC,EAAE,CAAC,OAAO,EAAE,GAAG,EAAE,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC,CAAC;IAC9C,CAAC,CAAC,CAAC;AACL,CAAC;AAED,MAAM,OAAO,eAAe;IAClB,KAAK,GAA6B,IAAI,CAAC;IACvC,SAAS,GAAsC,IAAI,CAAC;IAE5D,2BAA2B;IAC3B,KAAK,CAAC,MAAM;QACV,IAAI,IAAI,CAAC,KAAK;YAAE,OAAO,IAAI,CAAC,KAAK,CAAC;QAClC,IAAI,CAAC,IAAI,CAAC,SAAS,EAAE,CAAC;YACpB,IAAI,CAAC,SAAS,GAAG,IAAI,CAAC,UAAU,EAAE,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE;gBAC5C,IAAI,CAAC,KAAK,GAAG,CAAC,CAAC;gBACf,IAAI,CAAC,SAAS,GAAG,IAAI,CAAC;gBACtB,OAAO,CAAC,CAAC;YACX,CAAC,CAAC,CAAC;QACL,CAAC;QACD,OAAO,IAAI,CAAC,SAAS,CAAC;IACxB,CAAC;IAED,iBAAiB;IACjB,KAAK;QACH,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC;QAClB,IAAI,CAAC,SAAS,GAAG,IAAI,CAAC;IACxB,CAAC;IAEO,KAAK,CAAC,UAAU;QACtB,MAAM,CAAC,SAAS,EAAE,WAAW,EAAE,iBAAiB,CAAC,GAAG,MAAM,OAAO,CAAC,GAAG,CAAC;YACpE,IAAI,CAAC,QAAQ,EAAE;YACf,IAAI,CAAC,UAAU,EAAE;YACjB,IAAI,CAAC,gBAAgB,EAAE;SACxB,CAAC,CAAC;QACH,OAAO;YACL,GAAG,CAAC,SAAS,CAAC,CAAC,CAAC,EAAE,SAAS,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;YACnC,GAAG,CAAC,WAAW,CAAC,CAAC,CAAC,EAAE,WAAW,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;YACvC,GAAG,CAAC,iBAAiB,CAAC,CAAC,CAAC,EAAE,iBAAiB,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;SACpD,CAAC;IACJ,CAAC;IAED,uDAAuD;IAC/C,KAAK,CAAC,QAAQ;QACpB,OAAO,CACL,MAAM,IAAI,CAAC,qBAAqB,CAAC,iCAAiC,CAAC;eAChE,MAAM,kBAAkB,CAAC,iBAAiB,CAAC,iCAAiC,CAAC,CAAC;eAC9E,MAAM,UAAU,CAAC,IAAI,CAAC,CAC1B,CAAC;IACJ,CAAC;IAED,gDAAgD;IACxC,KAAK,CAAC,UAAU;QACtB,OAAO,CACL,MAAM,kBAAkB,CAAC,iBAAiB,CAAC,iBAAiB,CAAC,CAAC;eAC3D,MAAM,IAAI,CAAC,qBAAqB,CAAC,iBAAiB,CAAC,CACvD,CAAC;IACJ,CAAC;IAED,+CAA+C;IACvC,KAAK,CAAC,gBAAgB;QAC5B,OAAO,CACL,MAAM,IAAI,CAAC,mBAAmB,CAAC,cAAc,CAAC;eAC3C,MAAM,UAAU,CAAC,SAAS,CAAC,CAC/B,CAAC;IACJ,CAAC;IAED,kDAAkD;IAC1C,qBAAqB,CAAC,OAAe;QAC3C,OAAO,CAAC,KAAK,IAAI,EAAE;YACjB,IAAI,CAAC;gBACH,MAAM,EAAE,aAAa,EAAE,GAAG,MAAM,MAAM,CAAC,aAAa,CAAC,CAAC;gBACtD,MAAM,OAAO,GAAG,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;gBAC/C,OAAO,cAAc,CAAC,OAAO,CAAC,GAAG,OAAO,eAAe,CAAmC,CAAC,CAAC;YAC9F,CAAC;YAAC,MAAM,CAAC;gBACP,OAAO,SAAS,CAAC;YACnB,CAAC;QACH,CAAC,CAAC,EAAE,CAAC;IACP,CAAC;IAED,0DAA0D;IAClD,KAAK,CAAC,mBAAmB,CAAC,OAAe;QAC/C,8EAA8E;QAC9E,MAAM,QAAQ,GAAa,EAAE,CAAC;QAC9B,IAAI,OAAO,CAAC,GAAG,CAAC,MAAM;YAAE,QAAQ,CAAC,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC;QAC1D,IAAI,OAAO,CAAC,GAAG,CAAC,OAAO;YAAE,QAAQ,CAAC,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,OAAO,EAAE,KAAK,CAAC,CAAC,CAAC;QACzE,QAAQ,CAAC,IAAI,CAAC,gCAAgC,EAAE,6BAA6B,CAAC,CAAC;QAC/E,KAAK,MAAM,MAAM,IAAI,QAAQ,EAAE,CAAC;YAC9B,MAAM,CAAC,GAAG,MAAM,kBAAkB,CAAC,IAAI,CAAC,MAAM,EAAE,OAAO,EAAE,cAAc,CAAC,CAAC,CAAC;YAC1E,IAAI,CAAC;gBAAE,OAAO,CAAC,CAAC;QAClB,CAAC;QACD,OAAO,SAAS,CAAC;IACnB,CAAC;CACF;AAED,8BAA8B;AAC9B,MAAM,CAAC,KAAK,UAAU,uBAAuB,CAAC,QAAyB;IACrE,OAAO,QAAQ,CAAC,MAAM,EAAE,CAAC;AAC3B,CAAC;AAED,6BAA6B;AAC7B,MAAM,CAAC,MAAM,iBAAiB,GAAG,UAAU,CAAC"}
@@ -0,0 +1,10 @@
1
+ import type { WorkspaceOwnerState, WorkspaceTelemetryState } from "./vendor/shared/index.js";
2
+ /** 兼容别名:投影层使用 shared 类型(单一来源) */
3
+ export type WorkspaceOwner = WorkspaceOwnerState;
4
+ export type WorkspaceTelemetry = WorkspaceTelemetryState;
5
+ export declare class WorkspaceTelemetryReader {
6
+ private readonly staleMs;
7
+ constructor(staleMs?: number);
8
+ read(): Promise<WorkspaceTelemetry>;
9
+ }
10
+ //# sourceMappingURL=workspace-telemetry.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"workspace-telemetry.d.ts","sourceRoot":"","sources":["../src/workspace-telemetry.ts"],"names":[],"mappings":"AAoBA,OAAO,KAAK,EAAE,mBAAmB,EAAE,uBAAuB,EAAa,MAAM,0BAA0B,CAAC;AAExG,iCAAiC;AACjC,MAAM,MAAM,cAAc,GAAG,mBAAmB,CAAC;AACjD,MAAM,MAAM,kBAAkB,GAAG,uBAAuB,CAAC;AAKzD,qBAAa,wBAAwB;IACvB,OAAO,CAAC,QAAQ,CAAC,OAAO;gBAAP,OAAO,SAAqB;IAEnD,IAAI,IAAI,OAAO,CAAC,kBAAkB,CAAC;CAmD1C"}
@@ -0,0 +1,84 @@
1
+ /**
2
+ * WorkspaceTelemetry — 读取 pi-maestro-teammate workspace-peer 运行时状态
3
+ *
4
+ * 合同(pi-maestro-teammate 持久化):
5
+ * ~/.pi/teammate/workspaces/<workspaceId>/runtime/owners/<ownerId>.json
6
+ * { workspaceId, normalizedCwd, ownerId, pid, sessionId, publishedAt,
7
+ * contextPressure, agents[], settled[], backgroundJobs[] }
8
+ * ~/.pi/teammate/workspaces/<id>/runtime/identities/claims/<key>.heartbeat.json
9
+ *
10
+ * 语义:
11
+ * - 每个 owner = 一个活的 Pi 会话(workspace owner claim 持有者)
12
+ * - heartbeat 新鲜度 = 会话是否活跃
13
+ * - agents[] = 正在运行的子 agent(teammate dispatch)
14
+ * - backgroundJobs[] = 后台任务
15
+ *
16
+ * 这正是 Monitor/Teammate Tab 需要的"窗口状态"合同。
17
+ */
18
+ import { readFile, readdir } from "node:fs/promises";
19
+ import { join } from "node:path";
20
+ import { homedir } from "node:os";
21
+ const WORKSPACES_ROOT = join(homedir(), ".pi", "teammate", "workspaces");
22
+ const HEARTBEAT_STALE_MS = 90_000; // 90s 无心跳视为不活跃
23
+ export class WorkspaceTelemetryReader {
24
+ staleMs;
25
+ constructor(staleMs = HEARTBEAT_STALE_MS) {
26
+ this.staleMs = staleMs;
27
+ }
28
+ async read() {
29
+ const owners = [];
30
+ let wsDirs = [];
31
+ try {
32
+ wsDirs = await readdir(WORKSPACES_ROOT);
33
+ }
34
+ catch {
35
+ return { owners: [], observedAt: new Date().toISOString(), aliveCount: 0 };
36
+ }
37
+ for (const wsId of wsDirs) {
38
+ const ownersDir = join(WORKSPACES_ROOT, wsId, "runtime", "owners");
39
+ let files;
40
+ try {
41
+ files = await readdir(ownersDir);
42
+ }
43
+ catch {
44
+ continue;
45
+ }
46
+ for (const f of files) {
47
+ if (!f.endsWith(".json") || f.includes(".tmp"))
48
+ continue;
49
+ try {
50
+ const raw = await readFile(join(ownersDir, f), "utf8");
51
+ const d = JSON.parse(raw);
52
+ if (d.kind !== "owner")
53
+ continue;
54
+ // 畸形 publishedAt 跳过:NaN 会让 alive/排序失效(correctness)
55
+ const publishedAt = Number(d.publishedAt);
56
+ if (!Number.isFinite(publishedAt) || publishedAt <= 0)
57
+ continue;
58
+ const ageMs = Math.max(0, Date.now() - publishedAt);
59
+ owners.push({
60
+ workspaceId: String(d.workspaceId ?? wsId),
61
+ normalizedCwd: String(d.normalizedCwd ?? ""),
62
+ ownerId: String(d.ownerId ?? ""),
63
+ pid: Number(d.pid ?? 0),
64
+ sessionId: String(d.sessionId ?? ""),
65
+ publishedAt,
66
+ contextPressure: (d.contextPressure ?? null),
67
+ agents: Array.isArray(d.agents) ? d.agents : [],
68
+ settled: Array.isArray(d.settled) ? d.settled : [],
69
+ backgroundJobs: Array.isArray(d.backgroundJobs) ? d.backgroundJobs : [],
70
+ alive: ageMs < this.staleMs,
71
+ ageMs,
72
+ });
73
+ }
74
+ catch {
75
+ // skip malformed
76
+ }
77
+ }
78
+ }
79
+ owners.sort((a, b) => b.publishedAt - a.publishedAt);
80
+ const aliveCount = owners.filter((o) => o.alive).length;
81
+ return { owners, observedAt: new Date().toISOString(), aliveCount };
82
+ }
83
+ }
84
+ //# sourceMappingURL=workspace-telemetry.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"workspace-telemetry.js","sourceRoot":"","sources":["../src/workspace-telemetry.ts"],"names":[],"mappings":"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"}
package/package.json ADDED
@@ -0,0 +1,64 @@
1
+ {
2
+ "name": "pi-maestro-mobile",
3
+ "version": "0.1.2",
4
+ "type": "module",
5
+ "description": "Maestro Mobile Host — PC 端常驻服务:Pi agent 会话桥 + Monitor telemetry 投影 + 移动端 WS/HTTP 服务",
6
+ "license": "MIT",
7
+ "repository": {
8
+ "type": "git",
9
+ "url": "git+https://github.com/netcookies/pi-maestro-app-party.git",
10
+ "directory": "apps/host"
11
+ },
12
+ "main": "./dist/index.js",
13
+ "types": "./dist/index.d.ts",
14
+ "exports": {
15
+ ".": {
16
+ "types": "./dist/index.d.ts",
17
+ "default": "./dist/index.js"
18
+ }
19
+ },
20
+ "bin": {
21
+ "pi-maestro-mobile": "./dist/cli.js"
22
+ },
23
+ "files": [
24
+ "dist",
25
+ "README.md"
26
+ ],
27
+ "scripts": {
28
+ "build": "bash build.sh",
29
+ "typecheck": "bash scripts/vendor-shared.sh && npx tsc --noEmit; rc=$?; git checkout -- src 2>/dev/null; rm -rf src/vendor; exit $rc",
30
+ "test": "vitest run",
31
+ "test:coverage": "vitest run --coverage",
32
+ "dev": "tsx src/cli.ts",
33
+ "start": "node dist/cli.js",
34
+ "prepublishOnly": "bash build.sh && vitest run"
35
+ },
36
+ "dependencies": {
37
+ "@earendil-works/pi-coding-agent": "^0.79.0",
38
+ "ws": "^8.18.0"
39
+ },
40
+ "devDependencies": {
41
+ "@types/node": "^22.0.0",
42
+ "@types/ws": "^8.18.0",
43
+ "tsx": "^4.20.0",
44
+ "typescript": "^5.8.0",
45
+ "vitest": "^4.1.0"
46
+ },
47
+ "engines": {
48
+ "node": ">=22.19"
49
+ },
50
+ "keywords": [
51
+ "pi",
52
+ "pi-agent",
53
+ "maestro",
54
+ "mobile",
55
+ "remote",
56
+ "websocket",
57
+ "teammate"
58
+ ],
59
+ "pi": {
60
+ "extensions": [
61
+ "./dist/extension.js"
62
+ ]
63
+ }
64
+ }