@taskcast/cli 1.2.1 → 1.3.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.
@@ -0,0 +1,8 @@
1
+ import { Command } from 'commander';
2
+ export declare function runServiceStart(_healthTimeoutMs?: number): Promise<void>;
3
+ export declare function runServiceStop(): Promise<void>;
4
+ export declare function runServiceStatus(): Promise<void>;
5
+ export declare function runServiceRestart(_healthTimeoutMs?: number): Promise<void>;
6
+ export declare function registerServiceCommand(program: Command): void;
7
+ export declare function pollHealth(port: number, timeoutMs?: number): Promise<boolean>;
8
+ //# sourceMappingURL=service.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"service.d.ts","sourceRoot":"","sources":["../../src/commands/service.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AAkDnC,wBAAsB,eAAe,CAAC,gBAAgB,SAAO,GAAG,OAAO,CAAC,IAAI,CAAC,CAqB5E;AAED,wBAAsB,cAAc,IAAI,OAAO,CAAC,IAAI,CAAC,CASpD;AAED,wBAAsB,gBAAgB,IAAI,OAAO,CAAC,IAAI,CAAC,CA6BtD;AAGD,wBAAsB,iBAAiB,CAAC,gBAAgB,SAAO,GAAG,OAAO,CAAC,IAAI,CAAC,CAgB9E;AAED,wBAAgB,sBAAsB,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI,CAmF7D;AAqBD,wBAAsB,UAAU,CAAC,IAAI,EAAE,MAAM,EAAE,SAAS,SAAO,GAAG,OAAO,CAAC,OAAO,CAAC,CAcjF"}
@@ -0,0 +1,237 @@
1
+ import { existsSync, mkdirSync, readFileSync, writeFileSync } from 'fs';
2
+ import { dirname } from 'path';
3
+ import { createServiceManager } from '../service/resolve.js';
4
+ import { getServicePaths } from '../service/paths.js';
5
+ function resolveNodePath() {
6
+ return process.execPath;
7
+ }
8
+ // Note: resolveEntryPoint uses import.meta.url which cannot be mocked in Vitest ESM tests.
9
+ // The entryPoint value is verified structurally (mockInstall called) but not by exact path.
10
+ /* v8 ignore next 3 */
11
+ function resolveEntryPoint() {
12
+ return new URL('../index.js', import.meta.url).pathname;
13
+ }
14
+ function ensureConfigFile(paths, configOpt) {
15
+ if (configOpt)
16
+ return configOpt;
17
+ // Check if any config already exists
18
+ if (existsSync(paths.defaultConfigPath)) {
19
+ return paths.defaultConfigPath;
20
+ }
21
+ // Create default config with SQLite
22
+ const dir = dirname(paths.defaultConfigPath);
23
+ mkdirSync(dir, { recursive: true });
24
+ const dbPath = paths.defaultDbPath;
25
+ const content = `# Taskcast service configuration
26
+ port: 3721
27
+
28
+ adapters:
29
+ shortTermStore:
30
+ provider: sqlite
31
+ path: ${dbPath}
32
+ longTermStore:
33
+ provider: sqlite
34
+ path: ${dbPath}
35
+ `;
36
+ writeFileSync(paths.defaultConfigPath, content);
37
+ console.log(`[taskcast] Created default config at ${paths.defaultConfigPath}`);
38
+ return paths.defaultConfigPath;
39
+ }
40
+ // Exported action functions — used directly by alias commands in index.ts
41
+ // _healthTimeoutMs is injectable for testing (default 5000ms)
42
+ export async function runServiceStart(_healthTimeoutMs = 5000) {
43
+ const mgr = createServiceManager();
44
+ const st = await mgr.status();
45
+ if (st.state === 'running') {
46
+ console.log('[taskcast] Service is already running.');
47
+ return;
48
+ }
49
+ await mgr.start();
50
+ const paths = getServicePaths();
51
+ const port = await getPortFromConfig();
52
+ const started = await pollHealth(port, _healthTimeoutMs);
53
+ if (started) {
54
+ console.log(`[taskcast] Service started on http://localhost:${port}`);
55
+ }
56
+ else {
57
+ console.error('[taskcast] Service may have failed to start. Check logs:');
58
+ if (paths.stdoutLog) {
59
+ console.error(` ${paths.stdoutLog}`);
60
+ }
61
+ else {
62
+ console.error(' journalctl --user -u taskcast');
63
+ }
64
+ }
65
+ }
66
+ export async function runServiceStop() {
67
+ const mgr = createServiceManager();
68
+ const st = await mgr.status();
69
+ if (st.state !== 'running') {
70
+ console.log('[taskcast] Service is not running.');
71
+ return;
72
+ }
73
+ await mgr.stop();
74
+ console.log('[taskcast] Service stopped.');
75
+ }
76
+ export async function runServiceStatus() {
77
+ const mgr = createServiceManager();
78
+ const st = await mgr.status();
79
+ if (st.state === 'not-installed') {
80
+ console.log('Service: not installed');
81
+ return;
82
+ }
83
+ if (st.state === 'stopped') {
84
+ console.log('Service: stopped');
85
+ return;
86
+ }
87
+ console.log(`Service: running (pid ${st.pid})`);
88
+ try {
89
+ const port = await getPortFromConfig();
90
+ const res = await fetch(`http://localhost:${port}/health/detail`);
91
+ if (res.ok) {
92
+ const body = await res.json();
93
+ if (body.uptime != null) {
94
+ const h = Math.floor(body.uptime / 3600);
95
+ const m = Math.floor((body.uptime % 3600) / 60);
96
+ console.log(`Uptime: ${h}h ${m}m`);
97
+ }
98
+ if (body.adapters?.shortTermStore) {
99
+ console.log(`Storage: ${body.adapters.shortTermStore.provider}`);
100
+ }
101
+ }
102
+ }
103
+ catch {
104
+ // Health endpoint not reachable — just show basic status
105
+ }
106
+ }
107
+ // _healthTimeoutMs is injectable for testing (default 5000ms)
108
+ export async function runServiceRestart(_healthTimeoutMs = 5000) {
109
+ const mgr = createServiceManager();
110
+ await mgr.restart();
111
+ const paths = getServicePaths();
112
+ const port = await getPortFromConfig();
113
+ const started = await pollHealth(port, _healthTimeoutMs);
114
+ if (started) {
115
+ console.log(`[taskcast] Service restarted on http://localhost:${port}`);
116
+ }
117
+ else {
118
+ console.error('[taskcast] Service may have failed to restart. Check logs:');
119
+ if (paths.stdoutLog) {
120
+ console.error(` ${paths.stdoutLog}`);
121
+ }
122
+ else {
123
+ console.error(' journalctl --user -u taskcast');
124
+ }
125
+ }
126
+ }
127
+ export function registerServiceCommand(program) {
128
+ const service = program
129
+ .command('service')
130
+ .description('Manage Taskcast as a system service');
131
+ service
132
+ .command('install')
133
+ .description('Register Taskcast as a system service with auto-start on boot')
134
+ .option('-c, --config <path>', 'config file path')
135
+ .option('-p, --port <port>', 'port to listen on', '3721')
136
+ .option('-s, --storage <type>', 'storage backend: memory | redis | sqlite')
137
+ .option('--db-path <path>', 'SQLite database file path')
138
+ .action(async (opts) => {
139
+ const port = Number(opts.port);
140
+ if (!Number.isFinite(port) || port < 1 || port > 65535 || port !== Math.floor(port)) {
141
+ console.error(`[taskcast] Invalid port: ${opts.port}`);
142
+ process.exit(1);
143
+ }
144
+ const mgr = createServiceManager();
145
+ const paths = getServicePaths();
146
+ const configPath = ensureConfigFile(paths, opts.config);
147
+ // When using auto-generated config (SQLite default) and user didn't
148
+ // explicitly set --storage, ensure the service starts with sqlite.
149
+ const autoSqlite = !opts.config && !opts.storage;
150
+ const storage = opts.storage ?? (autoSqlite ? 'sqlite' : undefined);
151
+ const dbPath = opts.dbPath ?? (autoSqlite ? paths.defaultDbPath : undefined);
152
+ const installOpts = {
153
+ port,
154
+ config: configPath,
155
+ nodePath: resolveNodePath(),
156
+ entryPoint: resolveEntryPoint(),
157
+ ...(storage !== undefined ? { storage } : {}),
158
+ ...(dbPath !== undefined ? { dbPath } : {}),
159
+ };
160
+ await mgr.install(installOpts);
161
+ // Write state file with the installed port so start/restart poll the right port
162
+ const statePath = paths.serviceStatePath;
163
+ mkdirSync(dirname(statePath), { recursive: true });
164
+ writeFileSync(statePath, JSON.stringify({ port }));
165
+ console.log('[taskcast] Service installed successfully.');
166
+ console.log('[taskcast] Run `taskcast service start` to start the service.');
167
+ });
168
+ service
169
+ .command('uninstall')
170
+ .description('Remove Taskcast system service registration')
171
+ .action(async () => {
172
+ const mgr = createServiceManager();
173
+ await mgr.uninstall();
174
+ console.log('[taskcast] Service uninstalled successfully.');
175
+ });
176
+ service
177
+ .command('start')
178
+ .description('Start Taskcast via system service manager')
179
+ .action(() => runServiceStart());
180
+ service
181
+ .command('stop')
182
+ .description('Stop Taskcast system service')
183
+ .action(() => runServiceStop());
184
+ service
185
+ .command('restart')
186
+ .description('Restart Taskcast system service')
187
+ .action(() => runServiceRestart());
188
+ service
189
+ .command('reload')
190
+ .description('Restart Taskcast system service (alias for restart)')
191
+ .action(() => runServiceRestart());
192
+ service
193
+ .command('status')
194
+ .description('Show Taskcast service status')
195
+ .action(runServiceStatus);
196
+ }
197
+ async function getPortFromConfig() {
198
+ try {
199
+ const paths = getServicePaths();
200
+ // Try state file first (written by install, has the exact installed port)
201
+ try {
202
+ const state = JSON.parse(readFileSync(paths.serviceStatePath, 'utf8'));
203
+ if (typeof state.port === 'number')
204
+ return state.port;
205
+ }
206
+ catch {
207
+ // State file not present — fall through to config file
208
+ }
209
+ const text = readFileSync(paths.defaultConfigPath, 'utf8');
210
+ const match = text.match(/^port:\s*(\d+)/m);
211
+ if (match)
212
+ return Number(match[1]);
213
+ }
214
+ catch {
215
+ // Config not readable — use default
216
+ }
217
+ return 3721;
218
+ }
219
+ export async function pollHealth(port, timeoutMs = 5000) {
220
+ const start = Date.now();
221
+ while (Date.now() - start < timeoutMs) {
222
+ try {
223
+ const res = await fetch(`http://localhost:${port}/health`);
224
+ if (res.ok)
225
+ return true;
226
+ }
227
+ catch {
228
+ // Not ready yet
229
+ }
230
+ const remaining = timeoutMs - (Date.now() - start);
231
+ if (remaining <= 0)
232
+ break;
233
+ await new Promise(r => setTimeout(r, Math.min(500, remaining)));
234
+ }
235
+ return false;
236
+ }
237
+ //# sourceMappingURL=service.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"service.js","sourceRoot":"","sources":["../../src/commands/service.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,UAAU,EAAE,SAAS,EAAE,YAAY,EAAE,aAAa,EAAE,MAAM,IAAI,CAAA;AACvE,OAAO,EAAE,OAAO,EAAE,MAAM,MAAM,CAAA;AAC9B,OAAO,EAAE,oBAAoB,EAAE,MAAM,uBAAuB,CAAA;AAC5D,OAAO,EAAE,eAAe,EAAE,MAAM,qBAAqB,CAAA;AAGrD,SAAS,eAAe;IACtB,OAAO,OAAO,CAAC,QAAQ,CAAA;AACzB,CAAC;AAED,2FAA2F;AAC3F,4FAA4F;AAC5F,sBAAsB;AACtB,SAAS,iBAAiB;IACxB,OAAO,IAAI,GAAG,CAAC,aAAa,EAAE,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,QAAQ,CAAA;AACzD,CAAC;AAED,SAAS,gBAAgB,CAAC,KAAyC,EAAE,SAAkB;IACrF,IAAI,SAAS;QAAE,OAAO,SAAS,CAAA;IAE/B,qCAAqC;IACrC,IAAI,UAAU,CAAC,KAAK,CAAC,iBAAiB,CAAC,EAAE,CAAC;QACxC,OAAO,KAAK,CAAC,iBAAiB,CAAA;IAChC,CAAC;IAED,oCAAoC;IACpC,MAAM,GAAG,GAAG,OAAO,CAAC,KAAK,CAAC,iBAAiB,CAAC,CAAA;IAC5C,SAAS,CAAC,GAAG,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAA;IAEnC,MAAM,MAAM,GAAG,KAAK,CAAC,aAAa,CAAA;IAClC,MAAM,OAAO,GAAG;;;;;;YAMN,MAAM;;;YAGN,MAAM;CACjB,CAAA;IACC,aAAa,CAAC,KAAK,CAAC,iBAAiB,EAAE,OAAO,CAAC,CAAA;IAC/C,OAAO,CAAC,GAAG,CAAC,wCAAwC,KAAK,CAAC,iBAAiB,EAAE,CAAC,CAAA;IAE9E,OAAO,KAAK,CAAC,iBAAiB,CAAA;AAChC,CAAC;AAED,0EAA0E;AAC1E,8DAA8D;AAC9D,MAAM,CAAC,KAAK,UAAU,eAAe,CAAC,gBAAgB,GAAG,IAAI;IAC3D,MAAM,GAAG,GAAG,oBAAoB,EAAE,CAAA;IAClC,MAAM,EAAE,GAAG,MAAM,GAAG,CAAC,MAAM,EAAE,CAAA;IAC7B,IAAI,EAAE,CAAC,KAAK,KAAK,SAAS,EAAE,CAAC;QAC3B,OAAO,CAAC,GAAG,CAAC,wCAAwC,CAAC,CAAA;QACrD,OAAM;IACR,CAAC;IACD,MAAM,GAAG,CAAC,KAAK,EAAE,CAAA;IACjB,MAAM,KAAK,GAAG,eAAe,EAAE,CAAA;IAC/B,MAAM,IAAI,GAAG,MAAM,iBAAiB,EAAE,CAAA;IACtC,MAAM,OAAO,GAAG,MAAM,UAAU,CAAC,IAAI,EAAE,gBAAgB,CAAC,CAAA;IACxD,IAAI,OAAO,EAAE,CAAC;QACZ,OAAO,CAAC,GAAG,CAAC,kDAAkD,IAAI,EAAE,CAAC,CAAA;IACvE,CAAC;SAAM,CAAC;QACN,OAAO,CAAC,KAAK,CAAC,0DAA0D,CAAC,CAAA;QACzE,IAAI,KAAK,CAAC,SAAS,EAAE,CAAC;YACpB,OAAO,CAAC,KAAK,CAAC,KAAK,KAAK,CAAC,SAAS,EAAE,CAAC,CAAA;QACvC,CAAC;aAAM,CAAC;YACN,OAAO,CAAC,KAAK,CAAC,iCAAiC,CAAC,CAAA;QAClD,CAAC;IACH,CAAC;AACH,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,cAAc;IAClC,MAAM,GAAG,GAAG,oBAAoB,EAAE,CAAA;IAClC,MAAM,EAAE,GAAG,MAAM,GAAG,CAAC,MAAM,EAAE,CAAA;IAC7B,IAAI,EAAE,CAAC,KAAK,KAAK,SAAS,EAAE,CAAC;QAC3B,OAAO,CAAC,GAAG,CAAC,oCAAoC,CAAC,CAAA;QACjD,OAAM;IACR,CAAC;IACD,MAAM,GAAG,CAAC,IAAI,EAAE,CAAA;IAChB,OAAO,CAAC,GAAG,CAAC,6BAA6B,CAAC,CAAA;AAC5C,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,gBAAgB;IACpC,MAAM,GAAG,GAAG,oBAAoB,EAAE,CAAA;IAClC,MAAM,EAAE,GAAG,MAAM,GAAG,CAAC,MAAM,EAAE,CAAA;IAC7B,IAAI,EAAE,CAAC,KAAK,KAAK,eAAe,EAAE,CAAC;QACjC,OAAO,CAAC,GAAG,CAAC,0BAA0B,CAAC,CAAA;QACvC,OAAM;IACR,CAAC;IACD,IAAI,EAAE,CAAC,KAAK,KAAK,SAAS,EAAE,CAAC;QAC3B,OAAO,CAAC,GAAG,CAAC,oBAAoB,CAAC,CAAA;QACjC,OAAM;IACR,CAAC;IACD,OAAO,CAAC,GAAG,CAAC,2BAA2B,EAAE,CAAC,GAAG,GAAG,CAAC,CAAA;IACjD,IAAI,CAAC;QACH,MAAM,IAAI,GAAG,MAAM,iBAAiB,EAAE,CAAA;QACtC,MAAM,GAAG,GAAG,MAAM,KAAK,CAAC,oBAAoB,IAAI,gBAAgB,CAAC,CAAA;QACjE,IAAI,GAAG,CAAC,EAAE,EAAE,CAAC;YACX,MAAM,IAAI,GAAG,MAAM,GAAG,CAAC,IAAI,EAA0E,CAAA;YACrG,IAAI,IAAI,CAAC,MAAM,IAAI,IAAI,EAAE,CAAC;gBACxB,MAAM,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,MAAM,GAAG,IAAI,CAAC,CAAA;gBACxC,MAAM,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,IAAI,CAAC,MAAM,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC,CAAA;gBAC/C,OAAO,CAAC,GAAG,CAAC,cAAc,CAAC,KAAK,CAAC,GAAG,CAAC,CAAA;YACvC,CAAC;YACD,IAAI,IAAI,CAAC,QAAQ,EAAE,cAAc,EAAE,CAAC;gBAClC,OAAO,CAAC,GAAG,CAAC,cAAc,IAAI,CAAC,QAAQ,CAAC,cAAc,CAAC,QAAQ,EAAE,CAAC,CAAA;YACpE,CAAC;QACH,CAAC;IACH,CAAC;IAAC,MAAM,CAAC;QACP,yDAAyD;IAC3D,CAAC;AACH,CAAC;AAED,8DAA8D;AAC9D,MAAM,CAAC,KAAK,UAAU,iBAAiB,CAAC,gBAAgB,GAAG,IAAI;IAC7D,MAAM,GAAG,GAAG,oBAAoB,EAAE,CAAA;IAClC,MAAM,GAAG,CAAC,OAAO,EAAE,CAAA;IACnB,MAAM,KAAK,GAAG,eAAe,EAAE,CAAA;IAC/B,MAAM,IAAI,GAAG,MAAM,iBAAiB,EAAE,CAAA;IACtC,MAAM,OAAO,GAAG,MAAM,UAAU,CAAC,IAAI,EAAE,gBAAgB,CAAC,CAAA;IACxD,IAAI,OAAO,EAAE,CAAC;QACZ,OAAO,CAAC,GAAG,CAAC,oDAAoD,IAAI,EAAE,CAAC,CAAA;IACzE,CAAC;SAAM,CAAC;QACN,OAAO,CAAC,KAAK,CAAC,4DAA4D,CAAC,CAAA;QAC3E,IAAI,KAAK,CAAC,SAAS,EAAE,CAAC;YACpB,OAAO,CAAC,KAAK,CAAC,KAAK,KAAK,CAAC,SAAS,EAAE,CAAC,CAAA;QACvC,CAAC;aAAM,CAAC;YACN,OAAO,CAAC,KAAK,CAAC,iCAAiC,CAAC,CAAA;QAClD,CAAC;IACH,CAAC;AACH,CAAC;AAED,MAAM,UAAU,sBAAsB,CAAC,OAAgB;IACrD,MAAM,OAAO,GAAG,OAAO;SACpB,OAAO,CAAC,SAAS,CAAC;SAClB,WAAW,CAAC,qCAAqC,CAAC,CAAA;IAErD,OAAO;SACJ,OAAO,CAAC,SAAS,CAAC;SAClB,WAAW,CAAC,+DAA+D,CAAC;SAC5E,MAAM,CAAC,qBAAqB,EAAE,kBAAkB,CAAC;SACjD,MAAM,CAAC,mBAAmB,EAAE,mBAAmB,EAAE,MAAM,CAAC;SACxD,MAAM,CAAC,sBAAsB,EAAE,0CAA0C,CAAC;SAC1E,MAAM,CAAC,kBAAkB,EAAE,2BAA2B,CAAC;SACvD,MAAM,CAAC,KAAK,EAAE,IAA0E,EAAE,EAAE;QAC3F,MAAM,IAAI,GAAG,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,CAAA;QAC9B,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,IAAI,CAAC,IAAI,IAAI,GAAG,CAAC,IAAI,IAAI,GAAG,KAAK,IAAI,IAAI,KAAK,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC;YACpF,OAAO,CAAC,KAAK,CAAC,4BAA4B,IAAI,CAAC,IAAI,EAAE,CAAC,CAAA;YACtD,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;QACjB,CAAC;QAED,MAAM,GAAG,GAAG,oBAAoB,EAAE,CAAA;QAClC,MAAM,KAAK,GAAG,eAAe,EAAE,CAAA;QAE/B,MAAM,UAAU,GAAG,gBAAgB,CAAC,KAAK,EAAE,IAAI,CAAC,MAAM,CAAC,CAAA;QAEvD,oEAAoE;QACpE,mEAAmE;QACnE,MAAM,UAAU,GAAG,CAAC,IAAI,CAAC,MAAM,IAAI,CAAC,IAAI,CAAC,OAAO,CAAA;QAChD,MAAM,OAAO,GAAG,IAAI,CAAC,OAAO,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,SAAS,CAAC,CAAA;QACnE,MAAM,MAAM,GAAG,IAAI,CAAC,MAAM,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC,KAAK,CAAC,aAAa,CAAC,CAAC,CAAC,SAAS,CAAC,CAAA;QAE5E,MAAM,WAAW,GAA0B;YACzC,IAAI;YACJ,MAAM,EAAE,UAAU;YAClB,QAAQ,EAAE,eAAe,EAAE;YAC3B,UAAU,EAAE,iBAAiB,EAAE;YAC/B,GAAG,CAAC,OAAO,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,OAAO,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;YAC7C,GAAG,CAAC,MAAM,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;SAC5C,CAAA;QAED,MAAM,GAAG,CAAC,OAAO,CAAC,WAAW,CAAC,CAAA;QAE9B,gFAAgF;QAChF,MAAM,SAAS,GAAG,KAAK,CAAC,gBAAgB,CAAA;QACxC,SAAS,CAAC,OAAO,CAAC,SAAS,CAAC,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAA;QAClD,aAAa,CAAC,SAAS,EAAE,IAAI,CAAC,SAAS,CAAC,EAAE,IAAI,EAAE,CAAC,CAAC,CAAA;QAElD,OAAO,CAAC,GAAG,CAAC,4CAA4C,CAAC,CAAA;QACzD,OAAO,CAAC,GAAG,CAAC,+DAA+D,CAAC,CAAA;IAC9E,CAAC,CAAC,CAAA;IAEJ,OAAO;SACJ,OAAO,CAAC,WAAW,CAAC;SACpB,WAAW,CAAC,6CAA6C,CAAC;SAC1D,MAAM,CAAC,KAAK,IAAI,EAAE;QACjB,MAAM,GAAG,GAAG,oBAAoB,EAAE,CAAA;QAClC,MAAM,GAAG,CAAC,SAAS,EAAE,CAAA;QACrB,OAAO,CAAC,GAAG,CAAC,8CAA8C,CAAC,CAAA;IAC7D,CAAC,CAAC,CAAA;IAEJ,OAAO;SACJ,OAAO,CAAC,OAAO,CAAC;SAChB,WAAW,CAAC,2CAA2C,CAAC;SACxD,MAAM,CAAC,GAAG,EAAE,CAAC,eAAe,EAAE,CAAC,CAAA;IAElC,OAAO;SACJ,OAAO,CAAC,MAAM,CAAC;SACf,WAAW,CAAC,8BAA8B,CAAC;SAC3C,MAAM,CAAC,GAAG,EAAE,CAAC,cAAc,EAAE,CAAC,CAAA;IAEjC,OAAO;SACJ,OAAO,CAAC,SAAS,CAAC;SAClB,WAAW,CAAC,iCAAiC,CAAC;SAC9C,MAAM,CAAC,GAAG,EAAE,CAAC,iBAAiB,EAAE,CAAC,CAAA;IAEpC,OAAO;SACJ,OAAO,CAAC,QAAQ,CAAC;SACjB,WAAW,CAAC,qDAAqD,CAAC;SAClE,MAAM,CAAC,GAAG,EAAE,CAAC,iBAAiB,EAAE,CAAC,CAAA;IAEpC,OAAO;SACJ,OAAO,CAAC,QAAQ,CAAC;SACjB,WAAW,CAAC,8BAA8B,CAAC;SAC3C,MAAM,CAAC,gBAAgB,CAAC,CAAA;AAC7B,CAAC;AAED,KAAK,UAAU,iBAAiB;IAC9B,IAAI,CAAC;QACH,MAAM,KAAK,GAAG,eAAe,EAAE,CAAA;QAC/B,0EAA0E;QAC1E,IAAI,CAAC;YACH,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,YAAY,CAAC,KAAK,CAAC,gBAAgB,EAAE,MAAM,CAAC,CAAsB,CAAA;YAC3F,IAAI,OAAO,KAAK,CAAC,IAAI,KAAK,QAAQ;gBAAE,OAAO,KAAK,CAAC,IAAI,CAAA;QACvD,CAAC;QAAC,MAAM,CAAC;YACP,uDAAuD;QACzD,CAAC;QACD,MAAM,IAAI,GAAG,YAAY,CAAC,KAAK,CAAC,iBAAiB,EAAE,MAAM,CAAC,CAAA;QAC1D,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,iBAAiB,CAAC,CAAA;QAC3C,IAAI,KAAK;YAAE,OAAO,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAA;IACpC,CAAC;IAAC,MAAM,CAAC;QACP,oCAAoC;IACtC,CAAC;IACD,OAAO,IAAI,CAAA;AACb,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,UAAU,CAAC,IAAY,EAAE,SAAS,GAAG,IAAI;IAC7D,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,EAAE,CAAA;IACxB,OAAO,IAAI,CAAC,GAAG,EAAE,GAAG,KAAK,GAAG,SAAS,EAAE,CAAC;QACtC,IAAI,CAAC;YACH,MAAM,GAAG,GAAG,MAAM,KAAK,CAAC,oBAAoB,IAAI,SAAS,CAAC,CAAA;YAC1D,IAAI,GAAG,CAAC,EAAE;gBAAE,OAAO,IAAI,CAAA;QACzB,CAAC;QAAC,MAAM,CAAC;YACP,gBAAgB;QAClB,CAAC;QACD,MAAM,SAAS,GAAG,SAAS,GAAG,CAAC,IAAI,CAAC,GAAG,EAAE,GAAG,KAAK,CAAC,CAAA;QAClD,IAAI,SAAS,IAAI,CAAC;YAAE,MAAK;QACzB,MAAM,IAAI,OAAO,CAAC,CAAC,CAAC,EAAE,CAAC,UAAU,CAAC,CAAC,EAAE,IAAI,CAAC,GAAG,CAAC,GAAG,EAAE,SAAS,CAAC,CAAC,CAAC,CAAA;IACjE,CAAC;IACD,OAAO,KAAK,CAAA;AACd,CAAC"}
@@ -1 +1 @@
1
- {"version":3,"file":"start.d.ts","sourceRoot":"","sources":["../../src/commands/start.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AAqBnC,wBAAgB,oBAAoB,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI,CA4H3D"}
1
+ {"version":3,"file":"start.d.ts","sourceRoot":"","sources":["../../src/commands/start.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AAqBnC,wBAAgB,oBAAoB,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI,CA4I3D"}
@@ -20,7 +20,7 @@ export function registerStartCommand(program) {
20
20
  .option('--playground', 'serve the interactive playground UI at /_playground/')
21
21
  .option('-v, --verbose', 'enable verbose logging')
22
22
  .action(async (options) => {
23
- let { config: fileConfig, source } = await loadConfigFile(options.config);
23
+ let { config: fileConfig, source, path: configPath } = await loadConfigFile(options.config);
24
24
  if (source === 'none') {
25
25
  const shouldCreate = await promptCreateGlobalConfig();
26
26
  if (shouldCreate) {
@@ -28,6 +28,8 @@ export function registerStartCommand(program) {
28
28
  if (createdPath) {
29
29
  const created = await loadConfigFile(createdPath);
30
30
  fileConfig = created.config;
31
+ source = created.source;
32
+ configPath = created.path;
31
33
  }
32
34
  }
33
35
  }
@@ -38,13 +40,17 @@ export function registerStartCommand(program) {
38
40
  let broadcast;
39
41
  let longTermStore;
40
42
  const storage = options.storage ?? process.env['TASKCAST_STORAGE'] ?? (redisUrl ? 'redis' : 'memory');
43
+ let shortTermLabel;
44
+ let longTermLabel;
41
45
  if (storage === 'sqlite') {
46
+ const dbPath = options.dbPath ?? './taskcast.db';
42
47
  const sqliteOpts = options.dbPath ? { path: options.dbPath } : {};
43
48
  const adapters = createSqliteAdapters(sqliteOpts);
44
49
  broadcast = new MemoryBroadcastProvider();
45
50
  shortTermStore = adapters.shortTermStore;
46
51
  longTermStore = adapters.longTermStore;
47
- console.log(`[taskcast] Using SQLite storage at ${options.dbPath ?? './taskcast.db'}`);
52
+ shortTermLabel = `sqlite @ ${dbPath}`;
53
+ longTermLabel = `sqlite @ ${dbPath}`;
48
54
  }
49
55
  else if (storage === 'redis' || redisUrl) {
50
56
  const pubClient = new Redis(redisUrl);
@@ -53,16 +59,24 @@ export function registerStartCommand(program) {
53
59
  const adapters = createRedisAdapters(pubClient, subClient, storeClient);
54
60
  broadcast = adapters.broadcast;
55
61
  shortTermStore = adapters.shortTermStore;
62
+ shortTermLabel = `redis @ ${redisUrl}`;
63
+ longTermLabel = '(none)';
56
64
  }
57
65
  else {
58
- console.warn('[taskcast] No TASKCAST_REDIS_URL configured — using in-memory adapters');
59
66
  broadcast = new MemoryBroadcastProvider();
60
67
  shortTermStore = new MemoryShortTermStore();
68
+ shortTermLabel = 'memory';
69
+ longTermLabel = '(none)';
61
70
  }
62
71
  if (storage !== 'sqlite' && postgresUrl) {
63
72
  const sql = postgres(postgresUrl);
64
73
  longTermStore = new PostgresLongTermStore(sql);
74
+ longTermLabel = `postgres @ ${postgresUrl}`;
65
75
  }
76
+ // Print startup configuration summary
77
+ console.log(`[taskcast] Config: ${configPath ?? '(none)'}`);
78
+ console.log(`[taskcast] Short-term store: ${shortTermLabel}`);
79
+ console.log(`[taskcast] Long-term store: ${longTermLabel}`);
66
80
  const engineOpts = { shortTermStore, broadcast };
67
81
  if (longTermStore !== undefined)
68
82
  engineOpts.longTermStore = longTermStore;
@@ -1 +1 @@
1
- {"version":3,"file":"start.js","sourceRoot":"","sources":["../../src/commands/start.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"start.js","sourceRoot":"","sources":["../../src/commands/start.ts"],"names":[],"mappings":"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"}
package/dist/index.js CHANGED
@@ -1,4 +1,5 @@
1
1
  #!/usr/bin/env node
2
+ import { createRequire } from 'module';
2
3
  import { Command } from 'commander';
3
4
  import { registerStartCommand } from './commands/start.js';
4
5
  import { registerMigrateCommand } from './commands/migrate.js';
@@ -9,11 +10,14 @@ import { registerPingCommand } from './commands/ping.js';
9
10
  import { registerDoctorCommand } from './commands/doctor.js';
10
11
  import { registerLogsCommand, registerTailCommand } from './commands/logs.js';
11
12
  import { registerTasksCommand } from './commands/tasks.js';
13
+ import { registerServiceCommand } from './commands/service.js';
14
+ const _require = createRequire(import.meta.url);
15
+ const { version } = _require('../package.json');
12
16
  const program = new Command();
13
17
  program
14
18
  .name('taskcast')
15
19
  .description('Taskcast — unified task tracking and streaming service')
16
- .version('0.3.1');
20
+ .version(version);
17
21
  registerStartCommand(program);
18
22
  registerMigrateCommand(program);
19
23
  registerPlaygroundCommand(program);
@@ -24,12 +28,25 @@ registerDoctorCommand(program);
24
28
  registerLogsCommand(program);
25
29
  registerTailCommand(program);
26
30
  registerTasksCommand(program);
27
- // Placeholders for unimplemented commands
28
- program.command('daemon').description('Start as background service (not yet implemented)')
29
- .action(() => { console.error('[taskcast] daemon mode is not yet implemented'); process.exit(1); });
30
- program.command('stop').description('Stop background service (not yet implemented)')
31
- .action(() => { console.error('[taskcast] stop is not yet implemented'); process.exit(1); });
32
- program.command('status').description('Show server status (not yet implemented)')
33
- .action(() => { console.error('[taskcast] status is not yet implemented'); process.exit(1); });
31
+ registerServiceCommand(program);
32
+ // Backward-compat aliases for old daemon/stop/status placeholder commands
33
+ program.command('daemon').description('Alias for `taskcast service start`')
34
+ /* v8 ignore next 4 */
35
+ .action(async () => {
36
+ const { runServiceStart } = await import('./commands/service.js');
37
+ await runServiceStart();
38
+ });
39
+ program.command('stop').description('Alias for `taskcast service stop`')
40
+ /* v8 ignore next 4 */
41
+ .action(async () => {
42
+ const { runServiceStop } = await import('./commands/service.js');
43
+ await runServiceStop();
44
+ });
45
+ program.command('status').description('Alias for `taskcast service status`')
46
+ /* v8 ignore next 4 */
47
+ .action(async () => {
48
+ const { runServiceStatus } = await import('./commands/service.js');
49
+ await runServiceStatus();
50
+ });
34
51
  program.parse();
35
52
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AACA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACnC,OAAO,EAAE,oBAAoB,EAAE,MAAM,qBAAqB,CAAA;AAC1D,OAAO,EAAE,sBAAsB,EAAE,MAAM,uBAAuB,CAAA;AAC9D,OAAO,EAAE,yBAAyB,EAAE,MAAM,0BAA0B,CAAA;AACpE,OAAO,EAAE,iBAAiB,EAAE,MAAM,kBAAkB,CAAA;AACpD,OAAO,EAAE,mBAAmB,EAAE,MAAM,oBAAoB,CAAA;AACxD,OAAO,EAAE,mBAAmB,EAAE,MAAM,oBAAoB,CAAA;AACxD,OAAO,EAAE,qBAAqB,EAAE,MAAM,sBAAsB,CAAA;AAC5D,OAAO,EAAE,mBAAmB,EAAE,mBAAmB,EAAE,MAAM,oBAAoB,CAAA;AAC7E,OAAO,EAAE,oBAAoB,EAAE,MAAM,qBAAqB,CAAA;AAE1D,MAAM,OAAO,GAAG,IAAI,OAAO,EAAE,CAAA;AAE7B,OAAO;KACJ,IAAI,CAAC,UAAU,CAAC;KAChB,WAAW,CAAC,wDAAwD,CAAC;KACrE,OAAO,CAAC,OAAO,CAAC,CAAA;AAEnB,oBAAoB,CAAC,OAAO,CAAC,CAAA;AAC7B,sBAAsB,CAAC,OAAO,CAAC,CAAA;AAC/B,yBAAyB,CAAC,OAAO,CAAC,CAAA;AAClC,iBAAiB,CAAC,OAAO,CAAC,CAAA;AAC1B,mBAAmB,CAAC,OAAO,CAAC,CAAA;AAC5B,mBAAmB,CAAC,OAAO,CAAC,CAAA;AAC5B,qBAAqB,CAAC,OAAO,CAAC,CAAA;AAC9B,mBAAmB,CAAC,OAAO,CAAC,CAAA;AAC5B,mBAAmB,CAAC,OAAO,CAAC,CAAA;AAC5B,oBAAoB,CAAC,OAAO,CAAC,CAAA;AAE7B,0CAA0C;AAC1C,OAAO,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC,WAAW,CAAC,mDAAmD,CAAC;KACvF,MAAM,CAAC,GAAG,EAAE,GAAG,OAAO,CAAC,KAAK,CAAC,+CAA+C,CAAC,CAAC,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA,CAAC,CAAC,CAAC,CAAA;AACpG,OAAO,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC,WAAW,CAAC,+CAA+C,CAAC;KACjF,MAAM,CAAC,GAAG,EAAE,GAAG,OAAO,CAAC,KAAK,CAAC,wCAAwC,CAAC,CAAC,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA,CAAC,CAAC,CAAC,CAAA;AAC7F,OAAO,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC,WAAW,CAAC,0CAA0C,CAAC;KAC9E,MAAM,CAAC,GAAG,EAAE,GAAG,OAAO,CAAC,KAAK,CAAC,0CAA0C,CAAC,CAAC,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA,CAAC,CAAC,CAAC,CAAA;AAE/F,OAAO,CAAC,KAAK,EAAE,CAAA"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AACA,OAAO,EAAE,aAAa,EAAE,MAAM,QAAQ,CAAA;AACtC,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACnC,OAAO,EAAE,oBAAoB,EAAE,MAAM,qBAAqB,CAAA;AAC1D,OAAO,EAAE,sBAAsB,EAAE,MAAM,uBAAuB,CAAA;AAC9D,OAAO,EAAE,yBAAyB,EAAE,MAAM,0BAA0B,CAAA;AACpE,OAAO,EAAE,iBAAiB,EAAE,MAAM,kBAAkB,CAAA;AACpD,OAAO,EAAE,mBAAmB,EAAE,MAAM,oBAAoB,CAAA;AACxD,OAAO,EAAE,mBAAmB,EAAE,MAAM,oBAAoB,CAAA;AACxD,OAAO,EAAE,qBAAqB,EAAE,MAAM,sBAAsB,CAAA;AAC5D,OAAO,EAAE,mBAAmB,EAAE,mBAAmB,EAAE,MAAM,oBAAoB,CAAA;AAC7E,OAAO,EAAE,oBAAoB,EAAE,MAAM,qBAAqB,CAAA;AAC1D,OAAO,EAAE,sBAAsB,EAAE,MAAM,uBAAuB,CAAA;AAE9D,MAAM,QAAQ,GAAG,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAA;AAC/C,MAAM,EAAE,OAAO,EAAE,GAAG,QAAQ,CAAC,iBAAiB,CAAwB,CAAA;AAEtE,MAAM,OAAO,GAAG,IAAI,OAAO,EAAE,CAAA;AAE7B,OAAO;KACJ,IAAI,CAAC,UAAU,CAAC;KAChB,WAAW,CAAC,wDAAwD,CAAC;KACrE,OAAO,CAAC,OAAO,CAAC,CAAA;AAEnB,oBAAoB,CAAC,OAAO,CAAC,CAAA;AAC7B,sBAAsB,CAAC,OAAO,CAAC,CAAA;AAC/B,yBAAyB,CAAC,OAAO,CAAC,CAAA;AAClC,iBAAiB,CAAC,OAAO,CAAC,CAAA;AAC1B,mBAAmB,CAAC,OAAO,CAAC,CAAA;AAC5B,mBAAmB,CAAC,OAAO,CAAC,CAAA;AAC5B,qBAAqB,CAAC,OAAO,CAAC,CAAA;AAC9B,mBAAmB,CAAC,OAAO,CAAC,CAAA;AAC5B,mBAAmB,CAAC,OAAO,CAAC,CAAA;AAC5B,oBAAoB,CAAC,OAAO,CAAC,CAAA;AAC7B,sBAAsB,CAAC,OAAO,CAAC,CAAA;AAE/B,0EAA0E;AAC1E,OAAO,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC,WAAW,CAAC,oCAAoC,CAAC;IACzE,sBAAsB;KACrB,MAAM,CAAC,KAAK,IAAI,EAAE;IACjB,MAAM,EAAE,eAAe,EAAE,GAAG,MAAM,MAAM,CAAC,uBAAuB,CAAC,CAAA;IACjE,MAAM,eAAe,EAAE,CAAA;AACzB,CAAC,CAAC,CAAA;AACJ,OAAO,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC,WAAW,CAAC,mCAAmC,CAAC;IACtE,sBAAsB;KACrB,MAAM,CAAC,KAAK,IAAI,EAAE;IACjB,MAAM,EAAE,cAAc,EAAE,GAAG,MAAM,MAAM,CAAC,uBAAuB,CAAC,CAAA;IAChE,MAAM,cAAc,EAAE,CAAA;AACxB,CAAC,CAAC,CAAA;AACJ,OAAO,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC,WAAW,CAAC,qCAAqC,CAAC;IAC1E,sBAAsB;KACrB,MAAM,CAAC,KAAK,IAAI,EAAE;IACjB,MAAM,EAAE,gBAAgB,EAAE,GAAG,MAAM,MAAM,CAAC,uBAAuB,CAAC,CAAA;IAClE,MAAM,gBAAgB,EAAE,CAAA;AAC1B,CAAC,CAAC,CAAA;AAEJ,OAAO,CAAC,KAAK,EAAE,CAAA"}
@@ -0,0 +1,26 @@
1
+ export interface ServiceInstallOptions {
2
+ port: number;
3
+ config?: string;
4
+ storage?: string;
5
+ dbPath?: string;
6
+ nodePath: string;
7
+ entryPoint: string;
8
+ }
9
+ export type ServiceStatus = {
10
+ state: 'running';
11
+ pid: number;
12
+ port?: number;
13
+ } | {
14
+ state: 'stopped';
15
+ } | {
16
+ state: 'not-installed';
17
+ };
18
+ export interface ServiceManager {
19
+ install(opts: ServiceInstallOptions): Promise<void>;
20
+ uninstall(): Promise<void>;
21
+ start(): Promise<void>;
22
+ stop(): Promise<void>;
23
+ restart(): Promise<void>;
24
+ status(): Promise<ServiceStatus>;
25
+ }
26
+ //# sourceMappingURL=interface.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"interface.d.ts","sourceRoot":"","sources":["../../src/service/interface.ts"],"names":[],"mappings":"AAEA,MAAM,WAAW,qBAAqB;IACpC,IAAI,EAAE,MAAM,CAAA;IACZ,MAAM,CAAC,EAAE,MAAM,CAAA;IACf,OAAO,CAAC,EAAE,MAAM,CAAA;IAChB,MAAM,CAAC,EAAE,MAAM,CAAA;IACf,QAAQ,EAAE,MAAM,CAAA;IAChB,UAAU,EAAE,MAAM,CAAA;CACnB;AAED,MAAM,MAAM,aAAa,GACrB;IAAE,KAAK,EAAE,SAAS,CAAC;IAAC,GAAG,EAAE,MAAM,CAAC;IAAC,IAAI,CAAC,EAAE,MAAM,CAAA;CAAE,GAChD;IAAE,KAAK,EAAE,SAAS,CAAA;CAAE,GACpB;IAAE,KAAK,EAAE,eAAe,CAAA;CAAE,CAAA;AAE9B,MAAM,WAAW,cAAc;IAC7B,OAAO,CAAC,IAAI,EAAE,qBAAqB,GAAG,OAAO,CAAC,IAAI,CAAC,CAAA;IACnD,SAAS,IAAI,OAAO,CAAC,IAAI,CAAC,CAAA;IAC1B,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC,CAAA;IACtB,IAAI,IAAI,OAAO,CAAC,IAAI,CAAC,CAAA;IACrB,OAAO,IAAI,OAAO,CAAC,IAAI,CAAC,CAAA;IACxB,MAAM,IAAI,OAAO,CAAC,aAAa,CAAC,CAAA;CACjC"}
@@ -0,0 +1,3 @@
1
+ // packages/cli/src/service/interface.ts
2
+ export {};
3
+ //# sourceMappingURL=interface.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"interface.js","sourceRoot":"","sources":["../../src/service/interface.ts"],"names":[],"mappings":"AAAA,wCAAwC"}
@@ -0,0 +1,11 @@
1
+ import type { ServiceManager, ServiceInstallOptions, ServiceStatus } from './interface.js';
2
+ export declare class LaunchdServiceManager implements ServiceManager {
3
+ private paths;
4
+ install(opts: ServiceInstallOptions): Promise<void>;
5
+ uninstall(): Promise<void>;
6
+ start(): Promise<void>;
7
+ stop(): Promise<void>;
8
+ restart(): Promise<void>;
9
+ status(): Promise<ServiceStatus>;
10
+ }
11
+ //# sourceMappingURL=launchd.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"launchd.d.ts","sourceRoot":"","sources":["../../src/service/launchd.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAE,cAAc,EAAE,qBAAqB,EAAE,aAAa,EAAE,MAAM,gBAAgB,CAAA;AAwC1F,qBAAa,qBAAsB,YAAW,cAAc;IAC1D,OAAO,CAAC,KAAK,CAAoB;IAE3B,OAAO,CAAC,IAAI,EAAE,qBAAqB,GAAG,OAAO,CAAC,IAAI,CAAC;IAcnD,SAAS,IAAI,OAAO,CAAC,IAAI,CAAC;IAY1B,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC;IAStB,IAAI,IAAI,OAAO,CAAC,IAAI,CAAC;IAKrB,OAAO,IAAI,OAAO,CAAC,IAAI,CAAC;IAKxB,MAAM,IAAI,OAAO,CAAC,aAAa,CAAC;CAgBvC"}
@@ -0,0 +1,97 @@
1
+ // packages/cli/src/service/launchd.ts
2
+ import { existsSync, writeFileSync, mkdirSync, unlinkSync } from 'fs';
3
+ import { execFileSync } from 'child_process';
4
+ import { dirname } from 'path';
5
+ import { getServicePaths, LAUNCHD_LABEL } from './paths.js';
6
+ function getUid() {
7
+ return process.getuid?.() ?? 501;
8
+ }
9
+ function generatePlist(opts, paths) {
10
+ const args = [opts.entryPoint, 'start', '--port', String(opts.port)];
11
+ if (opts.config)
12
+ args.push('--config', opts.config);
13
+ if (opts.storage)
14
+ args.push('--storage', opts.storage);
15
+ if (opts.dbPath)
16
+ args.push('--db-path', opts.dbPath);
17
+ const programArgs = [opts.nodePath, ...args]
18
+ .map(a => ` <string>${a}</string>`)
19
+ .join('\n');
20
+ return `<?xml version="1.0" encoding="UTF-8"?>
21
+ <!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
22
+ <plist version="1.0">
23
+ <dict>
24
+ <key>Label</key>
25
+ <string>${LAUNCHD_LABEL}</string>
26
+ <key>ProgramArguments</key>
27
+ <array>
28
+ ${programArgs}
29
+ </array>
30
+ <key>RunAtLoad</key>
31
+ <true/>
32
+ <key>KeepAlive</key>
33
+ <false/>
34
+ <key>StandardOutPath</key>
35
+ <string>${paths.stdoutLog}</string>
36
+ <key>StandardErrorPath</key>
37
+ <string>${paths.stderrLog}</string>
38
+ </dict>
39
+ </plist>
40
+ `;
41
+ }
42
+ export class LaunchdServiceManager {
43
+ paths = getServicePaths();
44
+ async install(opts) {
45
+ if (existsSync(this.paths.plistOrUnitPath)) {
46
+ throw new Error(`Taskcast service is already installed. Run \`taskcast service uninstall\` first.`);
47
+ }
48
+ // Ensure log directory exists
49
+ mkdirSync(this.paths.logDir, { recursive: true });
50
+ // Ensure plist parent directory exists
51
+ mkdirSync(dirname(this.paths.plistOrUnitPath), { recursive: true });
52
+ const plist = generatePlist(opts, this.paths);
53
+ writeFileSync(this.paths.plistOrUnitPath, plist);
54
+ }
55
+ async uninstall() {
56
+ if (!existsSync(this.paths.plistOrUnitPath))
57
+ return;
58
+ // Stop if running
59
+ const st = await this.status();
60
+ if (st.state === 'running') {
61
+ await this.stop();
62
+ }
63
+ unlinkSync(this.paths.plistOrUnitPath);
64
+ }
65
+ async start() {
66
+ if (!existsSync(this.paths.plistOrUnitPath)) {
67
+ throw new Error(`Taskcast service is not installed. Run \`taskcast service install\` first.`);
68
+ }
69
+ const uid = getUid();
70
+ execFileSync('launchctl', ['bootstrap', `gui/${uid}`, this.paths.plistOrUnitPath], { stdio: 'pipe' });
71
+ }
72
+ async stop() {
73
+ const uid = getUid();
74
+ execFileSync('launchctl', ['bootout', `gui/${uid}/${LAUNCHD_LABEL}`], { stdio: 'pipe' });
75
+ }
76
+ async restart() {
77
+ await this.stop();
78
+ await this.start();
79
+ }
80
+ async status() {
81
+ if (!existsSync(this.paths.plistOrUnitPath)) {
82
+ return { state: 'not-installed' };
83
+ }
84
+ try {
85
+ const output = execFileSync('launchctl', ['list', LAUNCHD_LABEL], { stdio: 'pipe' }).toString();
86
+ const pidMatch = output.match(/"PID"\s*=\s*(\d+)/);
87
+ if (pidMatch) {
88
+ return { state: 'running', pid: Number(pidMatch[1]) };
89
+ }
90
+ return { state: 'stopped' };
91
+ }
92
+ catch {
93
+ return { state: 'stopped' };
94
+ }
95
+ }
96
+ }
97
+ //# sourceMappingURL=launchd.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"launchd.js","sourceRoot":"","sources":["../../src/service/launchd.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,12 @@
1
+ export interface ServicePaths {
2
+ plistOrUnitPath: string;
3
+ logDir: string;
4
+ stdoutLog: string;
5
+ stderrLog: string;
6
+ defaultConfigPath: string;
7
+ defaultDbPath: string;
8
+ serviceStatePath: string;
9
+ }
10
+ export declare const LAUNCHD_LABEL = "com.taskcast.daemon";
11
+ export declare function getServicePaths(): ServicePaths;
12
+ //# sourceMappingURL=paths.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"paths.d.ts","sourceRoot":"","sources":["../../src/service/paths.ts"],"names":[],"mappings":"AAGA,MAAM,WAAW,YAAY;IAC3B,eAAe,EAAE,MAAM,CAAA;IACvB,MAAM,EAAE,MAAM,CAAA;IACd,SAAS,EAAE,MAAM,CAAA;IACjB,SAAS,EAAE,MAAM,CAAA;IACjB,iBAAiB,EAAE,MAAM,CAAA;IACzB,aAAa,EAAE,MAAM,CAAA;IACrB,gBAAgB,EAAE,MAAM,CAAA;CACzB;AAED,eAAO,MAAM,aAAa,wBAAwB,CAAA;AAElD,wBAAgB,eAAe,IAAI,YAAY,CAkC9C"}
@@ -0,0 +1,35 @@
1
+ import { homedir } from 'os';
2
+ import { join } from 'path';
3
+ export const LAUNCHD_LABEL = 'com.taskcast.daemon';
4
+ export function getServicePaths() {
5
+ const home = homedir();
6
+ const platform = process.platform;
7
+ const defaultConfigPath = join(home, '.taskcast', 'taskcast.config.yaml');
8
+ const defaultDbPath = join(home, '.taskcast', 'taskcast.db');
9
+ const serviceStatePath = join(home, '.taskcast', 'service.state.json');
10
+ if (platform === 'darwin') {
11
+ const logDir = join(home, 'Library/Application Support/taskcast');
12
+ return {
13
+ plistOrUnitPath: join(home, 'Library/LaunchAgents', `${LAUNCHD_LABEL}.plist`),
14
+ logDir,
15
+ stdoutLog: join(logDir, 'taskcast.log'),
16
+ stderrLog: join(logDir, 'taskcast.err.log'),
17
+ defaultConfigPath,
18
+ defaultDbPath,
19
+ serviceStatePath,
20
+ };
21
+ }
22
+ if (platform === 'linux') {
23
+ return {
24
+ plistOrUnitPath: join(home, '.config/systemd/user/taskcast.service'),
25
+ logDir: '', // systemd uses journalctl
26
+ stdoutLog: '', // journalctl --user -u taskcast
27
+ stderrLog: '', // journalctl --user -u taskcast
28
+ defaultConfigPath,
29
+ defaultDbPath,
30
+ serviceStatePath,
31
+ };
32
+ }
33
+ throw new Error(`Unsupported platform: ${platform}`);
34
+ }
35
+ //# sourceMappingURL=paths.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"paths.js","sourceRoot":"","sources":["../../src/service/paths.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,IAAI,CAAA;AAC5B,OAAO,EAAE,IAAI,EAAE,MAAM,MAAM,CAAA;AAY3B,MAAM,CAAC,MAAM,aAAa,GAAG,qBAAqB,CAAA;AAElD,MAAM,UAAU,eAAe;IAC7B,MAAM,IAAI,GAAG,OAAO,EAAE,CAAA;IACtB,MAAM,QAAQ,GAAG,OAAO,CAAC,QAAQ,CAAA;IAEjC,MAAM,iBAAiB,GAAG,IAAI,CAAC,IAAI,EAAE,WAAW,EAAE,sBAAsB,CAAC,CAAA;IACzE,MAAM,aAAa,GAAG,IAAI,CAAC,IAAI,EAAE,WAAW,EAAE,aAAa,CAAC,CAAA;IAC5D,MAAM,gBAAgB,GAAG,IAAI,CAAC,IAAI,EAAE,WAAW,EAAE,oBAAoB,CAAC,CAAA;IAEtE,IAAI,QAAQ,KAAK,QAAQ,EAAE,CAAC;QAC1B,MAAM,MAAM,GAAG,IAAI,CAAC,IAAI,EAAE,sCAAsC,CAAC,CAAA;QACjE,OAAO;YACL,eAAe,EAAE,IAAI,CAAC,IAAI,EAAE,sBAAsB,EAAE,GAAG,aAAa,QAAQ,CAAC;YAC7E,MAAM;YACN,SAAS,EAAE,IAAI,CAAC,MAAM,EAAE,cAAc,CAAC;YACvC,SAAS,EAAE,IAAI,CAAC,MAAM,EAAE,kBAAkB,CAAC;YAC3C,iBAAiB;YACjB,aAAa;YACb,gBAAgB;SACjB,CAAA;IACH,CAAC;IAED,IAAI,QAAQ,KAAK,OAAO,EAAE,CAAC;QACzB,OAAO;YACL,eAAe,EAAE,IAAI,CAAC,IAAI,EAAE,uCAAuC,CAAC;YACpE,MAAM,EAAE,EAAE,EAAE,0BAA0B;YACtC,SAAS,EAAE,EAAE,EAAE,gCAAgC;YAC/C,SAAS,EAAE,EAAE,EAAE,gCAAgC;YAC/C,iBAAiB;YACjB,aAAa;YACb,gBAAgB;SACjB,CAAA;IACH,CAAC;IAED,MAAM,IAAI,KAAK,CAAC,yBAAyB,QAAQ,EAAE,CAAC,CAAA;AACtD,CAAC"}
@@ -0,0 +1,3 @@
1
+ import type { ServiceManager } from './interface.js';
2
+ export declare function createServiceManager(): ServiceManager;
3
+ //# sourceMappingURL=resolve.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"resolve.d.ts","sourceRoot":"","sources":["../../src/service/resolve.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,gBAAgB,CAAA;AAIpD,wBAAgB,oBAAoB,IAAI,cAAc,CAIrD"}
@@ -0,0 +1,10 @@
1
+ import { LaunchdServiceManager } from './launchd.js';
2
+ import { SystemdServiceManager } from './systemd.js';
3
+ export function createServiceManager() {
4
+ if (process.platform === 'darwin')
5
+ return new LaunchdServiceManager();
6
+ if (process.platform === 'linux')
7
+ return new SystemdServiceManager();
8
+ throw new Error(`Unsupported platform: ${process.platform}`);
9
+ }
10
+ //# sourceMappingURL=resolve.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"resolve.js","sourceRoot":"","sources":["../../src/service/resolve.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,qBAAqB,EAAE,MAAM,cAAc,CAAA;AACpD,OAAO,EAAE,qBAAqB,EAAE,MAAM,cAAc,CAAA;AAEpD,MAAM,UAAU,oBAAoB;IAClC,IAAI,OAAO,CAAC,QAAQ,KAAK,QAAQ;QAAE,OAAO,IAAI,qBAAqB,EAAE,CAAA;IACrE,IAAI,OAAO,CAAC,QAAQ,KAAK,OAAO;QAAE,OAAO,IAAI,qBAAqB,EAAE,CAAA;IACpE,MAAM,IAAI,KAAK,CAAC,yBAAyB,OAAO,CAAC,QAAQ,EAAE,CAAC,CAAA;AAC9D,CAAC"}
@@ -0,0 +1,11 @@
1
+ import type { ServiceManager, ServiceInstallOptions, ServiceStatus } from './interface.js';
2
+ export declare class SystemdServiceManager implements ServiceManager {
3
+ private paths;
4
+ install(opts: ServiceInstallOptions): Promise<void>;
5
+ uninstall(): Promise<void>;
6
+ start(): Promise<void>;
7
+ stop(): Promise<void>;
8
+ restart(): Promise<void>;
9
+ status(): Promise<ServiceStatus>;
10
+ }
11
+ //# sourceMappingURL=systemd.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"systemd.d.ts","sourceRoot":"","sources":["../../src/service/systemd.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAE,cAAc,EAAE,qBAAqB,EAAE,aAAa,EAAE,MAAM,gBAAgB,CAAA;AA6B1F,qBAAa,qBAAsB,YAAW,cAAc;IAC1D,OAAO,CAAC,KAAK,CAAoB;IAE3B,OAAO,CAAC,IAAI,EAAE,qBAAqB,GAAG,OAAO,CAAC,IAAI,CAAC;IAcnD,SAAS,IAAI,OAAO,CAAC,IAAI,CAAC;IAa1B,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC;IAQtB,IAAI,IAAI,OAAO,CAAC,IAAI,CAAC;IAIrB,OAAO,IAAI,OAAO,CAAC,IAAI,CAAC;IAIxB,MAAM,IAAI,OAAO,CAAC,aAAa,CAAC;CAyBvC"}
@@ -0,0 +1,86 @@
1
+ // packages/cli/src/service/systemd.ts
2
+ import { existsSync, writeFileSync, mkdirSync, unlinkSync } from 'fs';
3
+ import { execFileSync } from 'child_process';
4
+ import { dirname } from 'path';
5
+ import { getServicePaths } from './paths.js';
6
+ const SYSTEMD_UNIT = 'taskcast';
7
+ function generateUnitFile(opts) {
8
+ const args = [opts.entryPoint, 'start', '--port', String(opts.port)];
9
+ if (opts.config)
10
+ args.push('--config', opts.config);
11
+ if (opts.storage)
12
+ args.push('--storage', opts.storage);
13
+ if (opts.dbPath)
14
+ args.push('--db-path', opts.dbPath);
15
+ // Quote any argument containing spaces so systemd parses them correctly
16
+ const quote = (s) => (s.includes(' ') ? `"${s}"` : s);
17
+ const execStart = [opts.nodePath, ...args].map(quote).join(' ');
18
+ return `[Unit]
19
+ Description=Taskcast — unified task tracking and streaming service
20
+ After=network.target
21
+
22
+ [Service]
23
+ Type=simple
24
+ ExecStart=${execStart}
25
+ Restart=no
26
+
27
+ [Install]
28
+ WantedBy=default.target
29
+ `;
30
+ }
31
+ export class SystemdServiceManager {
32
+ paths = getServicePaths();
33
+ async install(opts) {
34
+ if (existsSync(this.paths.plistOrUnitPath)) {
35
+ throw new Error(`Taskcast service is already installed. Run \`taskcast service uninstall\` first.`);
36
+ }
37
+ mkdirSync(dirname(this.paths.plistOrUnitPath), { recursive: true });
38
+ const unit = generateUnitFile(opts);
39
+ writeFileSync(this.paths.plistOrUnitPath, unit);
40
+ execFileSync('systemctl', ['--user', 'daemon-reload'], { stdio: 'pipe' });
41
+ execFileSync('systemctl', ['--user', 'enable', SYSTEMD_UNIT], { stdio: 'pipe' });
42
+ }
43
+ async uninstall() {
44
+ if (!existsSync(this.paths.plistOrUnitPath))
45
+ return;
46
+ const st = await this.status();
47
+ if (st.state === 'running') {
48
+ await this.stop();
49
+ }
50
+ execFileSync('systemctl', ['--user', 'disable', SYSTEMD_UNIT], { stdio: 'pipe' });
51
+ execFileSync('systemctl', ['--user', 'daemon-reload'], { stdio: 'pipe' });
52
+ unlinkSync(this.paths.plistOrUnitPath);
53
+ }
54
+ async start() {
55
+ if (!existsSync(this.paths.plistOrUnitPath)) {
56
+ throw new Error(`Taskcast service is not installed. Run \`taskcast service install\` first.`);
57
+ }
58
+ execFileSync('systemctl', ['--user', 'start', SYSTEMD_UNIT], { stdio: 'pipe' });
59
+ }
60
+ async stop() {
61
+ execFileSync('systemctl', ['--user', 'stop', SYSTEMD_UNIT], { stdio: 'pipe' });
62
+ }
63
+ async restart() {
64
+ execFileSync('systemctl', ['--user', 'restart', SYSTEMD_UNIT], { stdio: 'pipe' });
65
+ }
66
+ async status() {
67
+ if (!existsSync(this.paths.plistOrUnitPath)) {
68
+ return { state: 'not-installed' };
69
+ }
70
+ try {
71
+ const output = execFileSync('systemctl', ['--user', 'show', SYSTEMD_UNIT, '--property=ActiveState,MainPID'], { stdio: 'pipe' }).toString();
72
+ const activeMatch = output.match(/ActiveState=(\w+)/);
73
+ const pidMatch = output.match(/MainPID=(\d+)/);
74
+ if (activeMatch?.[1] === 'active' && pidMatch) {
75
+ const pid = Number(pidMatch[1]);
76
+ if (pid > 0)
77
+ return { state: 'running', pid };
78
+ }
79
+ return { state: 'stopped' };
80
+ }
81
+ catch {
82
+ return { state: 'stopped' };
83
+ }
84
+ }
85
+ }
86
+ //# sourceMappingURL=systemd.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"systemd.js","sourceRoot":"","sources":["../../src/service/systemd.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@taskcast/cli",
3
- "version": "1.2.1",
3
+ "version": "1.3.0",
4
4
  "description": "Standalone Taskcast server CLI — run with npx taskcast.",
5
5
  "repository": {
6
6
  "type": "git",
@@ -37,14 +37,14 @@
37
37
  "commander": "^12.1.0",
38
38
  "ioredis": "^5.4.0",
39
39
  "postgres": "^3.4.5",
40
- "@taskcast/core": "1.2.1",
41
- "@taskcast/dashboard-web": "0.3.4",
42
- "@taskcast/postgres": "1.2.1",
43
- "@taskcast/redis": "1.2.1",
44
- "@taskcast/playground": "0.3.4",
45
- "@taskcast/server-sdk": "1.2.1",
46
- "@taskcast/sqlite": "1.2.1",
47
- "@taskcast/server": "1.2.1"
40
+ "@taskcast/core": "1.3.0",
41
+ "@taskcast/playground": "0.3.5",
42
+ "@taskcast/postgres": "1.3.0",
43
+ "@taskcast/redis": "1.3.0",
44
+ "@taskcast/sqlite": "1.3.0",
45
+ "@taskcast/server": "1.3.0",
46
+ "@taskcast/server-sdk": "1.3.0",
47
+ "@taskcast/dashboard-web": "0.3.5"
48
48
  },
49
49
  "devDependencies": {
50
50
  "typescript": "^5.7.0",