@soederpop/luca 0.0.3 → 0.0.4
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/AGENTS.md +98 -0
- package/CLAUDE.md +27 -0
- package/SPEC.md +304 -0
- package/bun.lock +110 -265
- package/docs/CLI.md +1 -1
- package/docs/apis/features/node/content-db.md +16 -0
- package/docs/apis/features/node/fs.md +24 -0
- package/docs/apis/features/node/ipc-socket.md +0 -1
- package/docs/apis/features/node/package-finder.md +1 -11
- package/docs/apis/features/node/proc.md +0 -41
- package/docs/apis/features/node/ui.md +0 -2
- package/package.json +12 -8
- package/src/agi/container.server.ts +16 -3
- package/src/agi/features/assistant.ts +3 -7
- package/src/agi/features/assistants-manager.ts +3 -7
- package/src/agi/features/claude-code.ts +3 -7
- package/src/agi/features/conversation-history.ts +3 -7
- package/src/agi/features/conversation.ts +4 -8
- package/src/agi/features/openai-codex.ts +3 -7
- package/src/agi/features/openapi.ts +4 -2
- package/src/agi/features/skills-library.ts +4 -8
- package/src/cli/cli.ts +22 -0
- package/src/client.ts +69 -26
- package/src/clients/civitai/index.ts +3 -7
- package/src/clients/comfyui/index.ts +5 -9
- package/src/clients/elevenlabs/index.ts +39 -19
- package/src/clients/openai/index.ts +3 -7
- package/src/clients/supabase/index.ts +4 -13
- package/src/commands/console.ts +0 -3
- package/src/commands/eval.ts +1 -1
- package/src/commands/index.ts +1 -0
- package/src/commands/introspect.ts +128 -0
- package/src/commands/prompt.ts +1 -4
- package/src/commands/run.ts +6 -13
- package/src/commands/sandbox-mcp.ts +1 -13
- package/src/feature.ts +45 -2
- package/src/introspection/generated.agi.ts +175 -101
- package/src/introspection/generated.node.ts +175 -101
- package/src/introspection/generated.web.ts +113 -29
- package/src/introspection/index.ts +1 -1
- package/src/introspection/scan.ts +3 -1
- package/src/node/features/container-link.ts +3 -2
- package/src/node/features/content-db.ts +10 -2
- package/src/node/features/disk-cache.ts +3 -4
- package/src/node/features/dns.ts +3 -2
- package/src/node/features/docker.ts +3 -2
- package/src/node/features/downloader.ts +3 -16
- package/src/node/features/esbuild.ts +3 -12
- package/src/node/features/file-manager.ts +3 -2
- package/src/node/features/fs.ts +12 -3
- package/src/node/features/git.ts +3 -2
- package/src/node/features/google-auth.ts +3 -2
- package/src/node/features/google-calendar.ts +3 -2
- package/src/node/features/google-docs.ts +3 -2
- package/src/node/features/google-drive.ts +3 -2
- package/src/node/features/google-sheets.ts +3 -2
- package/src/node/features/grep.ts +3 -2
- package/src/node/features/helpers.ts +13 -2
- package/src/node/features/ink.ts +3 -3
- package/src/node/features/ipc-socket.ts +3 -3
- package/src/node/features/json-tree.ts +3 -21
- package/src/node/features/launcher-app-command-listener.ts +3 -2
- package/src/node/features/networking.ts +3 -2
- package/src/node/features/nlp.ts +3 -2
- package/src/node/features/opener.ts +8 -7
- package/src/node/features/os.ts +3 -2
- package/src/node/features/package-finder.ts +3 -2
- package/src/node/features/port-exposer.ts +3 -4
- package/src/node/features/postgres.ts +3 -3
- package/src/node/features/proc.ts +37 -64
- package/src/node/features/process-manager.ts +3 -2
- package/src/node/features/python.ts +3 -3
- package/src/node/features/repl.ts +3 -2
- package/src/node/features/runpod.ts +3 -3
- package/src/node/features/secure-shell.ts +3 -2
- package/src/node/features/semantic-search.ts +4 -6
- package/src/node/features/sqlite.ts +3 -3
- package/src/node/features/telegram.ts +3 -2
- package/src/node/features/tts.ts +3 -2
- package/src/node/features/ui.ts +3 -3
- package/src/node/features/vault.ts +3 -14
- package/src/node/features/vm.ts +41 -3
- package/src/node/features/window-manager.ts +165 -22
- package/src/node/features/yaml-tree.ts +3 -4
- package/src/node/features/yaml.ts +3 -2
- package/src/registry.ts +1 -1
- package/src/scaffolds/generated.ts +1 -1
- package/src/server.ts +43 -0
- package/src/servers/express.ts +24 -8
- package/src/servers/mcp.ts +2 -6
- package/src/servers/socket.ts +22 -7
- package/src/web/clients/socket.ts +3 -5
- package/src/web/features/asset-loader.ts +20 -12
- package/src/web/features/container-link.ts +3 -6
- package/src/web/features/esbuild.ts +21 -7
- package/src/web/features/helpers.ts +4 -2
- package/src/web/features/network.ts +24 -7
- package/src/web/features/speech.ts +24 -7
- package/src/web/features/vault.ts +21 -3
- package/src/web/features/vm.ts +20 -13
- package/src/web/features/voice-recognition.ts +26 -9
- package/commands/update-introspection.ts +0 -67
- package/docs/ideas/class-registration-refactor-possibilities.md +0 -197
- package/docs/ideas/container-use-api.md +0 -9
- package/docs/ideas/easy-auth-for-express-servers-and-luca-serve.md +0 -0
- package/docs/ideas/feature-stacks.md +0 -22
- package/docs/ideas/luca-cli-self-sufficiency-demo.md +0 -23
- package/docs/ideas/mcp-design.md +0 -9
- package/docs/ideas/web-container-debugging-feature.md +0 -13
- package/scripts/animations/chrome-glitch.ts +0 -55
- package/scripts/animations/index.ts +0 -16
- package/scripts/animations/neon-pulse.ts +0 -64
- package/scripts/animations/types.ts +0 -6
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { z } from 'zod'
|
|
2
2
|
import { FeatureStateSchema, FeatureOptionsSchema, FeatureEventsSchema } from '../../schemas/base.js'
|
|
3
|
-
import { Feature
|
|
3
|
+
import { Feature } from '../feature.js'
|
|
4
4
|
import { google, type calendar_v3 } from 'googleapis'
|
|
5
5
|
import type { GoogleAuth } from './google-auth.js'
|
|
6
6
|
|
|
@@ -104,6 +104,7 @@ export class GoogleCalendar extends Feature<GoogleCalendarState, GoogleCalendarO
|
|
|
104
104
|
static override stateSchema = GoogleCalendarStateSchema
|
|
105
105
|
static override optionsSchema = GoogleCalendarOptionsSchema
|
|
106
106
|
static override eventsSchema = GoogleCalendarEventsSchema
|
|
107
|
+
static { Feature.register(this, 'googleCalendar') }
|
|
107
108
|
|
|
108
109
|
private _calendar?: calendar_v3.Calendar
|
|
109
110
|
|
|
@@ -297,4 +298,4 @@ declare module '../../feature' {
|
|
|
297
298
|
}
|
|
298
299
|
}
|
|
299
300
|
|
|
300
|
-
export default
|
|
301
|
+
export default GoogleCalendar
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { z } from 'zod'
|
|
2
2
|
import { FeatureStateSchema, FeatureOptionsSchema, FeatureEventsSchema } from '../../schemas/base.js'
|
|
3
|
-
import { Feature
|
|
3
|
+
import { Feature } from '../feature.js'
|
|
4
4
|
import { google, type docs_v1 } from 'googleapis'
|
|
5
5
|
import type { GoogleAuth } from './google-auth.js'
|
|
6
6
|
import type { GoogleDrive, DriveFile } from './google-drive.js'
|
|
@@ -55,6 +55,7 @@ export class GoogleDocs extends Feature<GoogleDocsState, GoogleDocsOptions> {
|
|
|
55
55
|
static override stateSchema = GoogleDocsStateSchema
|
|
56
56
|
static override optionsSchema = GoogleDocsOptionsSchema
|
|
57
57
|
static override eventsSchema = GoogleDocsEventsSchema
|
|
58
|
+
static { Feature.register(this, 'googleDocs') }
|
|
58
59
|
|
|
59
60
|
private _docs?: docs_v1.Docs
|
|
60
61
|
|
|
@@ -401,4 +402,4 @@ declare module '../../feature' {
|
|
|
401
402
|
}
|
|
402
403
|
}
|
|
403
404
|
|
|
404
|
-
export default
|
|
405
|
+
export default GoogleDocs
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { z } from 'zod'
|
|
2
2
|
import { FeatureStateSchema, FeatureOptionsSchema, FeatureEventsSchema } from '../../schemas/base.js'
|
|
3
|
-
import { Feature
|
|
3
|
+
import { Feature } from '../feature.js'
|
|
4
4
|
import { google, type drive_v3 } from 'googleapis'
|
|
5
5
|
import type { GoogleAuth } from './google-auth.js'
|
|
6
6
|
|
|
@@ -104,6 +104,7 @@ export class GoogleDrive extends Feature<GoogleDriveState, GoogleDriveOptions> {
|
|
|
104
104
|
static override stateSchema = GoogleDriveStateSchema
|
|
105
105
|
static override optionsSchema = GoogleDriveOptionsSchema
|
|
106
106
|
static override eventsSchema = GoogleDriveEventsSchema
|
|
107
|
+
static { Feature.register(this, 'googleDrive') }
|
|
107
108
|
|
|
108
109
|
private _drive?: drive_v3.Drive
|
|
109
110
|
|
|
@@ -336,4 +337,4 @@ declare module '../../feature' {
|
|
|
336
337
|
}
|
|
337
338
|
}
|
|
338
339
|
|
|
339
|
-
export default
|
|
340
|
+
export default GoogleDrive
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { z } from 'zod'
|
|
2
2
|
import { FeatureStateSchema, FeatureOptionsSchema, FeatureEventsSchema } from '../../schemas/base.js'
|
|
3
|
-
import { Feature
|
|
3
|
+
import { Feature } from '../feature.js'
|
|
4
4
|
import { google, type sheets_v4 } from 'googleapis'
|
|
5
5
|
import type { GoogleAuth } from './google-auth.js'
|
|
6
6
|
|
|
@@ -74,6 +74,7 @@ export class GoogleSheets extends Feature<GoogleSheetsState, GoogleSheetsOptions
|
|
|
74
74
|
static override stateSchema = GoogleSheetsStateSchema
|
|
75
75
|
static override optionsSchema = GoogleSheetsOptionsSchema
|
|
76
76
|
static override eventsSchema = GoogleSheetsEventsSchema
|
|
77
|
+
static { Feature.register(this, 'googleSheets') }
|
|
77
78
|
|
|
78
79
|
private _sheets?: sheets_v4.Sheets
|
|
79
80
|
|
|
@@ -276,4 +277,4 @@ declare module '../../feature' {
|
|
|
276
277
|
}
|
|
277
278
|
}
|
|
278
279
|
|
|
279
|
-
export default
|
|
280
|
+
export default GoogleSheets
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { Feature } from '../feature.js'
|
|
2
2
|
import { FeatureStateSchema, FeatureOptionsSchema } from '../../schemas/base.js'
|
|
3
3
|
|
|
4
4
|
/** Shell-escape a string using single quotes (safe for all characters) */
|
|
@@ -77,6 +77,7 @@ export class Grep extends Feature {
|
|
|
77
77
|
static override shortcut = 'features.grep' as const
|
|
78
78
|
static override stateSchema = FeatureStateSchema
|
|
79
79
|
static override optionsSchema = FeatureOptionsSchema
|
|
80
|
+
static { Feature.register(this, 'grep') }
|
|
80
81
|
|
|
81
82
|
private _hasRipgrep: boolean | null = null
|
|
82
83
|
|
|
@@ -403,4 +404,4 @@ export class Grep extends Feature {
|
|
|
403
404
|
}
|
|
404
405
|
}
|
|
405
406
|
|
|
406
|
-
export default
|
|
407
|
+
export default Grep
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { z } from 'zod'
|
|
2
2
|
import { FeatureStateSchema, FeatureOptionsSchema, FeatureEventsSchema } from '../../schemas/base.js'
|
|
3
|
-
import { Feature
|
|
3
|
+
import { Feature } from '../feature.js'
|
|
4
4
|
import { Feature as UniversalFeature } from '../../feature.js'
|
|
5
5
|
import { Client, clients } from '../../client.js'
|
|
6
6
|
import { Server, servers } from '../../server.js'
|
|
@@ -69,6 +69,7 @@ export class Helpers extends Feature<HelpersState, HelpersOptions> {
|
|
|
69
69
|
static override stateSchema = HelpersStateSchema
|
|
70
70
|
static override optionsSchema = HelpersOptionsSchema
|
|
71
71
|
static override eventsSchema = HelpersEventsSchema
|
|
72
|
+
static { Feature.register(this, 'helpers') }
|
|
72
73
|
|
|
73
74
|
/**
|
|
74
75
|
* Returns a mapping from registry type name to its registry singleton, base class, and conventional folder candidates.
|
|
@@ -251,6 +252,16 @@ export class Helpers extends Feature<HelpersState, HelpersOptions> {
|
|
|
251
252
|
const fm = await this.ensureFileManager()
|
|
252
253
|
const discovered: string[] = []
|
|
253
254
|
|
|
255
|
+
// Load build-time introspection data before importing helpers so that
|
|
256
|
+
// interceptRegistration() can merge JSDoc descriptions from the generated file.
|
|
257
|
+
const introspectionFile = resolve(dir, 'introspection.generated.ts')
|
|
258
|
+
try {
|
|
259
|
+
const { existsSync } = await import('fs')
|
|
260
|
+
if (existsSync(introspectionFile)) {
|
|
261
|
+
await import(introspectionFile)
|
|
262
|
+
}
|
|
263
|
+
} catch {}
|
|
264
|
+
|
|
254
265
|
const tests = [`${type}/*/*.ts`, `${type}/*.ts`]
|
|
255
266
|
const files = fm.match(tests)
|
|
256
267
|
|
|
@@ -371,4 +382,4 @@ export class Helpers extends Feature<HelpersState, HelpersOptions> {
|
|
|
371
382
|
}
|
|
372
383
|
}
|
|
373
384
|
|
|
374
|
-
export default
|
|
385
|
+
export default Helpers
|
package/src/node/features/ink.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { z } from 'zod'
|
|
2
2
|
import { FeatureStateSchema, FeatureOptionsSchema, FeatureEventsSchema } from '../../schemas/base.js'
|
|
3
|
-
import {
|
|
3
|
+
import { Feature } from '../feature.js'
|
|
4
4
|
|
|
5
5
|
// ─── Schemas ────────────────────────────────────────────────────────────────
|
|
6
6
|
|
|
@@ -84,6 +84,7 @@ export class Ink extends Feature<InkState, InkOptions> {
|
|
|
84
84
|
static override stateSchema = InkStateSchema
|
|
85
85
|
static override optionsSchema = InkOptionsSchema
|
|
86
86
|
static override eventsSchema = InkEventsSchema
|
|
87
|
+
static { Feature.register(this, 'ink') }
|
|
87
88
|
|
|
88
89
|
private _instance: any | null = null
|
|
89
90
|
private _inkModule: typeof import('ink') | null = null
|
|
@@ -481,8 +482,7 @@ export class Ink extends Feature<InkState, InkOptions> {
|
|
|
481
482
|
}
|
|
482
483
|
}
|
|
483
484
|
|
|
484
|
-
export default
|
|
485
|
-
|
|
485
|
+
export default Ink
|
|
486
486
|
declare module '../../feature' {
|
|
487
487
|
interface AvailableFeatures {
|
|
488
488
|
ink: typeof Ink
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { z } from 'zod'
|
|
2
2
|
import { FeatureStateSchema, FeatureEventsSchema } from '../../schemas/base.js'
|
|
3
|
-
import { Feature
|
|
3
|
+
import { Feature } from "../feature.js";
|
|
4
4
|
import { NodeContainer } from "../container.js";
|
|
5
5
|
import { Server, Socket } from "net";
|
|
6
6
|
|
|
@@ -84,6 +84,7 @@ export const IpcEventsSchema = FeatureEventsSchema.extend({
|
|
|
84
84
|
* @extends {Feature<T>}
|
|
85
85
|
*/
|
|
86
86
|
export class IpcSocket<T extends IpcState = IpcState> extends Feature<T> {
|
|
87
|
+
static { Feature.register(this, 'ipcSocket') }
|
|
87
88
|
/** The shortcut path for accessing this feature */
|
|
88
89
|
static override shortcut = "features.ipcSocket" as const
|
|
89
90
|
static override stateSchema = IpcStateSchema
|
|
@@ -106,7 +107,6 @@ export class IpcSocket<T extends IpcState = IpcState> extends Feature<T> {
|
|
|
106
107
|
* @returns The container for method chaining
|
|
107
108
|
*/
|
|
108
109
|
static attach(container: NodeContainer & { ipcSocket?: IpcSocket }) {
|
|
109
|
-
container.features.register("ipcSocket", IpcSocket);
|
|
110
110
|
container.ipcSocket = container.feature("ipcSocket", { enable: true });
|
|
111
111
|
}
|
|
112
112
|
|
|
@@ -456,4 +456,4 @@ export class IpcSocket<T extends IpcState = IpcState> extends Feature<T> {
|
|
|
456
456
|
}
|
|
457
457
|
}
|
|
458
458
|
|
|
459
|
-
export default
|
|
459
|
+
export default IpcSocket
|
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
import { z } from 'zod'
|
|
2
2
|
import { FeatureStateSchema, FeatureOptionsSchema } from '../../schemas/base.js'
|
|
3
|
-
import { Feature
|
|
4
|
-
import { NodeContainer } from "../container.js";
|
|
3
|
+
import { Feature } from "../feature.js";
|
|
5
4
|
import { camelCase, omit, set } from 'lodash-es';
|
|
6
5
|
|
|
7
6
|
/**
|
|
@@ -52,29 +51,12 @@ export type JsonTreeState = z.infer<typeof JsonTreeStateSchema>
|
|
|
52
51
|
* @extends {Feature<T>}
|
|
53
52
|
*/
|
|
54
53
|
export class JsonTree<T extends JsonTreeState = JsonTreeState> extends Feature<T> {
|
|
54
|
+
static { Feature.register(this, 'jsonTree') }
|
|
55
55
|
/** The shortcut path for accessing this feature */
|
|
56
56
|
static override shortcut = "features.jsonTree" as const
|
|
57
57
|
static override stateSchema = JsonTreeStateSchema
|
|
58
58
|
static override optionsSchema = FeatureOptionsSchema
|
|
59
59
|
|
|
60
|
-
/**
|
|
61
|
-
* Attaches the JsonTree feature to a NodeContainer instance.
|
|
62
|
-
* Registers the feature in the container's feature registry for later use.
|
|
63
|
-
*
|
|
64
|
-
* @param container - The NodeContainer to attach to
|
|
65
|
-
* @returns The container for method chaining
|
|
66
|
-
*
|
|
67
|
-
* @example
|
|
68
|
-
* ```typescript
|
|
69
|
-
* // Typically called during container setup:
|
|
70
|
-
* JsonTree.attach(container)
|
|
71
|
-
* const jsonTree = container.feature('jsonTree')
|
|
72
|
-
* ```
|
|
73
|
-
*/
|
|
74
|
-
static attach(container: NodeContainer & { jsonTree?: JsonTree }) {
|
|
75
|
-
container.features.register("jsonTree", JsonTree);
|
|
76
|
-
}
|
|
77
|
-
|
|
78
60
|
/**
|
|
79
61
|
* Loads a tree of JSON files from the specified base path and stores them in state.
|
|
80
62
|
*
|
|
@@ -185,4 +167,4 @@ export class JsonTree<T extends JsonTreeState = JsonTreeState> extends Feature<T
|
|
|
185
167
|
}
|
|
186
168
|
}
|
|
187
169
|
|
|
188
|
-
export default
|
|
170
|
+
export default JsonTree
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { z } from 'zod'
|
|
2
2
|
import { FeatureStateSchema, FeatureOptionsSchema, FeatureEventsSchema } from '../../schemas/base.js'
|
|
3
|
-
import { Feature
|
|
3
|
+
import { Feature } from '../feature.js'
|
|
4
4
|
import { Server as NetServer, Socket } from 'net'
|
|
5
5
|
import { homedir } from 'os'
|
|
6
6
|
import { join, dirname } from 'path'
|
|
@@ -201,6 +201,7 @@ export class LauncherAppCommandListener extends Feature<LauncherAppCommandListen
|
|
|
201
201
|
static override stateSchema = LauncherAppCommandListenerStateSchema
|
|
202
202
|
static override optionsSchema = LauncherAppCommandListenerOptionsSchema
|
|
203
203
|
static override eventsSchema = LauncherAppCommandListenerEventsSchema
|
|
204
|
+
static { Feature.register(this, 'launcherAppCommandListener') }
|
|
204
205
|
|
|
205
206
|
private _server?: NetServer
|
|
206
207
|
private _client?: ClientConnection
|
|
@@ -385,4 +386,4 @@ export class LauncherAppCommandListener extends Feature<LauncherAppCommandListen
|
|
|
385
386
|
}
|
|
386
387
|
}
|
|
387
388
|
|
|
388
|
-
export default
|
|
389
|
+
export default LauncherAppCommandListener
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { z } from 'zod'
|
|
2
2
|
import net from 'net'
|
|
3
3
|
import detectPort from 'detect-port'
|
|
4
|
-
import { Feature
|
|
4
|
+
import { Feature } from '../feature.js'
|
|
5
5
|
import { FeatureStateSchema, FeatureOptionsSchema } from '../../schemas/base.js'
|
|
6
6
|
|
|
7
7
|
const MAX_CIDR_HOSTS = 65536
|
|
@@ -204,6 +204,7 @@ export class Networking extends Feature<NetworkingState, NetworkingOptions> {
|
|
|
204
204
|
static override shortcut = 'features.networking' as const
|
|
205
205
|
static override stateSchema = NetworkingStateSchema
|
|
206
206
|
static override optionsSchema = NetworkingOptionsSchema
|
|
207
|
+
static { Feature.register(this, 'networking') }
|
|
207
208
|
|
|
208
209
|
override get initialState(): NetworkingState {
|
|
209
210
|
return {
|
|
@@ -922,4 +923,4 @@ export class Networking extends Feature<NetworkingState, NetworkingOptions> {
|
|
|
922
923
|
}
|
|
923
924
|
}
|
|
924
925
|
|
|
925
|
-
export default
|
|
926
|
+
export default Networking
|
package/src/node/features/nlp.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { z } from 'zod'
|
|
2
|
-
import { Feature
|
|
2
|
+
import { Feature } from '../feature.js'
|
|
3
3
|
import { FeatureStateSchema, FeatureOptionsSchema } from '../../schemas/base.js'
|
|
4
4
|
import compromise from 'compromise'
|
|
5
5
|
import winkNLP from 'wink-nlp'
|
|
@@ -65,6 +65,7 @@ export class NLP extends Feature<z.infer<typeof NLPStateSchema>, z.infer<typeof
|
|
|
65
65
|
static override shortcut = 'features.nlp' as const
|
|
66
66
|
static override stateSchema = NLPStateSchema
|
|
67
67
|
static override optionsSchema = NLPOptionsSchema
|
|
68
|
+
static { Feature.register(this, 'nlp') }
|
|
68
69
|
|
|
69
70
|
private _wink?: ReturnType<typeof winkNLP>
|
|
70
71
|
|
|
@@ -208,4 +209,4 @@ export class NLP extends Feature<z.infer<typeof NLPStateSchema>, z.infer<typeof
|
|
|
208
209
|
}
|
|
209
210
|
}
|
|
210
211
|
|
|
211
|
-
export default
|
|
212
|
+
export default NLP
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { Feature } from "../feature.js";
|
|
2
2
|
import { FeatureStateSchema, FeatureOptionsSchema } from '../../schemas/base.js'
|
|
3
3
|
|
|
4
4
|
/**
|
|
@@ -35,6 +35,7 @@ export class Opener extends Feature {
|
|
|
35
35
|
static override description = "Opens files, URLs, desktop apps, and code editors"
|
|
36
36
|
static override stateSchema = FeatureStateSchema
|
|
37
37
|
static override optionsSchema = FeatureOptionsSchema
|
|
38
|
+
static { Feature.register(this, 'opener') }
|
|
38
39
|
|
|
39
40
|
/**
|
|
40
41
|
* Opens a path or URL with the appropriate application.
|
|
@@ -47,7 +48,7 @@ export class Opener extends Feature {
|
|
|
47
48
|
*/
|
|
48
49
|
async open(target: string): Promise<void> {
|
|
49
50
|
const isUrl = /^https?:\/\//i.test(target)
|
|
50
|
-
const platform =
|
|
51
|
+
const platform = this.container.os.platform
|
|
51
52
|
|
|
52
53
|
if (isUrl) {
|
|
53
54
|
console.log(`Opening ${target} in Chrome`)
|
|
@@ -57,7 +58,7 @@ export class Opener extends Feature {
|
|
|
57
58
|
}
|
|
58
59
|
}
|
|
59
60
|
|
|
60
|
-
private async openInChrome(url: string, platform: string): Promise<void> {
|
|
61
|
+
private async openInChrome(url: string, platform: string = this.container.os.platform): Promise<void> {
|
|
61
62
|
const proc = this.container.proc
|
|
62
63
|
|
|
63
64
|
if (platform === 'darwin') {
|
|
@@ -88,7 +89,7 @@ export class Opener extends Feature {
|
|
|
88
89
|
* @returns {Promise<void>}
|
|
89
90
|
*/
|
|
90
91
|
async app(name: string): Promise<void> {
|
|
91
|
-
const platform =
|
|
92
|
+
const platform = this.container.os.platform
|
|
92
93
|
const proc = this.container.proc
|
|
93
94
|
|
|
94
95
|
if (platform === 'darwin') {
|
|
@@ -114,7 +115,7 @@ export class Opener extends Feature {
|
|
|
114
115
|
try {
|
|
115
116
|
await proc.spawnAndCapture('code', [path])
|
|
116
117
|
} catch {
|
|
117
|
-
if (
|
|
118
|
+
if (this.container.os.platform === 'darwin') {
|
|
118
119
|
await proc.spawnAndCapture('open', ['-a', 'Visual Studio Code', path])
|
|
119
120
|
} else {
|
|
120
121
|
throw new Error('VS Code CLI (code) not found. Install it from VS Code: Command Palette > "Shell Command: Install code command in PATH"')
|
|
@@ -136,7 +137,7 @@ export class Opener extends Feature {
|
|
|
136
137
|
try {
|
|
137
138
|
await proc.spawnAndCapture('cursor', [path])
|
|
138
139
|
} catch {
|
|
139
|
-
if (
|
|
140
|
+
if (this.container.os.platform === 'darwin') {
|
|
140
141
|
await proc.spawnAndCapture('open', ['-a', 'Cursor', path])
|
|
141
142
|
} else {
|
|
142
143
|
throw new Error('Cursor CLI (cursor) not found. Install it from Cursor: Command Palette > "Shell Command: Install cursor command in PATH"')
|
|
@@ -163,4 +164,4 @@ declare module '../../feature' {
|
|
|
163
164
|
}
|
|
164
165
|
}
|
|
165
166
|
|
|
166
|
-
export default
|
|
167
|
+
export default Opener
|
package/src/node/features/os.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { Feature
|
|
1
|
+
import { Feature } from '../feature.js'
|
|
2
2
|
import { FeatureStateSchema, FeatureOptionsSchema } from '../../schemas/base.js'
|
|
3
3
|
import os from 'os'
|
|
4
4
|
|
|
@@ -25,6 +25,7 @@ export class OS extends Feature {
|
|
|
25
25
|
static override shortcut = 'features.os' as const
|
|
26
26
|
static override stateSchema = FeatureStateSchema
|
|
27
27
|
static override optionsSchema = FeatureOptionsSchema
|
|
28
|
+
static { Feature.register(this, 'os') }
|
|
28
29
|
|
|
29
30
|
/**
|
|
30
31
|
* Gets the operating system CPU architecture.
|
|
@@ -154,4 +155,4 @@ export class OS extends Feature {
|
|
|
154
155
|
}
|
|
155
156
|
}
|
|
156
157
|
|
|
157
|
-
export default
|
|
158
|
+
export default OS
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { z } from 'zod'
|
|
2
2
|
import { FeatureStateSchema, FeatureOptionsSchema } from '../../schemas/base.js'
|
|
3
|
-
import { Feature
|
|
3
|
+
import { Feature } from "../feature.js";
|
|
4
4
|
import { readdir, readFile } from 'fs/promises'
|
|
5
5
|
import { resolve, join, basename } from 'path'
|
|
6
6
|
import { mapValues, pickBy, uniqBy } from 'lodash-es'
|
|
@@ -111,6 +111,7 @@ export class PackageFinder<
|
|
|
111
111
|
T extends PackageFinderState = PackageFinderState,
|
|
112
112
|
K extends PackageFinderOptions = PackageFinderOptions
|
|
113
113
|
> extends Feature<T, K> {
|
|
114
|
+
static { Feature.register(this, 'packageFinder') }
|
|
114
115
|
|
|
115
116
|
/** The shortcut path for accessing this feature */
|
|
116
117
|
static override shortcut = "features.packageFinder" as const
|
|
@@ -536,4 +537,4 @@ export class PackageFinder<
|
|
|
536
537
|
|
|
537
538
|
}
|
|
538
539
|
|
|
539
|
-
export default
|
|
540
|
+
export default PackageFinder
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { z } from 'zod'
|
|
2
2
|
import { FeatureStateSchema, FeatureOptionsSchema } from '../../schemas/base.js'
|
|
3
3
|
import * as ngrok from '@ngrok/ngrok'
|
|
4
|
-
import { Feature
|
|
4
|
+
import { Feature } from '../../feature.js'
|
|
5
5
|
|
|
6
6
|
/**
|
|
7
7
|
* Zod schema for the Port Exposer feature state
|
|
@@ -81,6 +81,7 @@ export class PortExposer extends Feature<PortExposerState, PortExposerOptions> {
|
|
|
81
81
|
static override shortcut = 'portExposer' as const
|
|
82
82
|
static override stateSchema = PortExposerStateSchema
|
|
83
83
|
static override optionsSchema = PortExposerOptionsSchema
|
|
84
|
+
static { Feature.register(this, 'portExposer') }
|
|
84
85
|
|
|
85
86
|
private ngrokListener?: ngrok.Listener
|
|
86
87
|
|
|
@@ -330,9 +331,7 @@ export class PortExposer extends Feature<PortExposerState, PortExposerOptions> {
|
|
|
330
331
|
}
|
|
331
332
|
}
|
|
332
333
|
|
|
333
|
-
|
|
334
|
-
export default features.register('portExposer', PortExposer)
|
|
335
|
-
|
|
334
|
+
export default PortExposer
|
|
336
335
|
// Module augmentation for type safety
|
|
337
336
|
declare module '../../feature.js' {
|
|
338
337
|
interface AvailableFeatures {
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { z } from 'zod'
|
|
2
2
|
import { SQL } from 'bun'
|
|
3
|
-
import { Feature
|
|
3
|
+
import { Feature } from '../feature.js'
|
|
4
4
|
import { FeatureStateSchema, FeatureOptionsSchema } from '../../schemas/base.js'
|
|
5
5
|
import type { ContainerContext } from '../../container.js'
|
|
6
6
|
|
|
@@ -46,6 +46,7 @@ export class Postgres extends Feature<PostgresState, PostgresOptions> {
|
|
|
46
46
|
static override shortcut = 'features.postgres' as const
|
|
47
47
|
static override stateSchema = PostgresStateSchema
|
|
48
48
|
static override optionsSchema = PostgresOptionsSchema
|
|
49
|
+
static { Feature.register(this, 'postgres') }
|
|
49
50
|
|
|
50
51
|
private _client: SQL
|
|
51
52
|
|
|
@@ -224,8 +225,7 @@ export class Postgres extends Feature<PostgresState, PostgresOptions> {
|
|
|
224
225
|
}
|
|
225
226
|
}
|
|
226
227
|
|
|
227
|
-
export default
|
|
228
|
-
|
|
228
|
+
export default Postgres
|
|
229
229
|
declare module '../../feature.js' {
|
|
230
230
|
interface AvailableFeatures {
|
|
231
231
|
postgres: typeof Postgres
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { Feature } from "../feature.js";
|
|
2
2
|
import { FeatureStateSchema, FeatureOptionsSchema } from '../../schemas/base.js'
|
|
3
3
|
import { execSync, spawn as nodeSpawn } from "child_process";
|
|
4
4
|
import { existsSync, mkdirSync, readFileSync, writeFileSync, unlinkSync } from "fs";
|
|
@@ -69,6 +69,7 @@ export class ChildProcess extends Feature {
|
|
|
69
69
|
static override shortcut = "features.proc" as const
|
|
70
70
|
static override stateSchema = FeatureStateSchema
|
|
71
71
|
static override optionsSchema = FeatureOptionsSchema
|
|
72
|
+
static { Feature.register(this, 'proc') }
|
|
72
73
|
|
|
73
74
|
/**
|
|
74
75
|
* Executes a command string and captures its output asynchronously.
|
|
@@ -182,6 +183,10 @@ export class ChildProcess extends Feature {
|
|
|
182
183
|
|
|
183
184
|
const childProcess = proc.childProcess!;
|
|
184
185
|
|
|
186
|
+
if (typeof options?.onStart === 'function') {
|
|
187
|
+
options.onStart(childProcess)
|
|
188
|
+
}
|
|
189
|
+
|
|
185
190
|
if (childProcess.stdout && childProcess.stderr) {
|
|
186
191
|
childProcess.stdout.on("data", (buf: Buffer) => {
|
|
187
192
|
stdout = stdout + buf.toString();
|
|
@@ -243,69 +248,7 @@ export class ChildProcess extends Feature {
|
|
|
243
248
|
return child
|
|
244
249
|
}
|
|
245
250
|
|
|
246
|
-
/**
|
|
247
|
-
* Runs a script file with Bun, inheriting stdout for full TTY passthrough
|
|
248
|
-
* (animations, colors, cursor movement) while capturing stderr in a rolling buffer.
|
|
249
|
-
*
|
|
250
|
-
* @param {string} scriptPath - Absolute path to the script file
|
|
251
|
-
* @param {object} [options] - Options
|
|
252
|
-
* @param {string} [options.cwd] - Working directory
|
|
253
|
-
* @param {number} [options.maxLines=100] - Max stderr lines to keep
|
|
254
|
-
* @param {Record<string, string>} [options.env] - Extra environment variables
|
|
255
|
-
* @returns {Promise<{ exitCode: number, stderr: string[] }>}
|
|
256
|
-
*
|
|
257
|
-
* @example
|
|
258
|
-
* ```typescript
|
|
259
|
-
* const { exitCode, stderr } = await proc.runScript('/path/to/script.ts')
|
|
260
|
-
* if (exitCode !== 0) {
|
|
261
|
-
* console.log('Error:', stderr.join('\n'))
|
|
262
|
-
* }
|
|
263
|
-
* ```
|
|
264
|
-
*/
|
|
265
|
-
async runScript(
|
|
266
|
-
scriptPath: string,
|
|
267
|
-
options?: { cwd?: string; maxLines?: number; env?: Record<string, string> }
|
|
268
|
-
): Promise<{ exitCode: number; stderr: string[] }> {
|
|
269
|
-
const cwd = options?.cwd ?? this.container.cwd
|
|
270
|
-
const maxLines = options?.maxLines ?? 100
|
|
271
|
-
|
|
272
|
-
const proc = Bun.spawn(['bun', 'run', scriptPath], {
|
|
273
|
-
cwd,
|
|
274
|
-
stdout: 'inherit',
|
|
275
|
-
stderr: 'pipe',
|
|
276
|
-
env: { ...process.env, ...options?.env },
|
|
277
|
-
})
|
|
278
|
-
|
|
279
|
-
const stderrLines: string[] = []
|
|
280
|
-
|
|
281
|
-
const reader = proc.stderr.getReader()
|
|
282
|
-
const decoder = new TextDecoder()
|
|
283
|
-
let partial = ''
|
|
284
|
-
|
|
285
|
-
while (true) {
|
|
286
|
-
const { done, value } = await reader.read()
|
|
287
|
-
if (done) break
|
|
288
|
-
const text = partial + decoder.decode(value, { stream: true })
|
|
289
|
-
const lines = text.split('\n')
|
|
290
|
-
partial = lines.pop() || ''
|
|
291
|
-
|
|
292
|
-
for (const line of lines) {
|
|
293
|
-
process.stderr.write(line + '\n')
|
|
294
|
-
stderrLines.push(line)
|
|
295
|
-
if (stderrLines.length > maxLines) stderrLines.shift()
|
|
296
|
-
}
|
|
297
|
-
}
|
|
298
|
-
|
|
299
|
-
if (partial) {
|
|
300
|
-
process.stderr.write(partial + '\n')
|
|
301
|
-
stderrLines.push(partial)
|
|
302
|
-
if (stderrLines.length > maxLines) stderrLines.shift()
|
|
303
|
-
}
|
|
304
|
-
|
|
305
|
-
const exitCode = await proc.exited
|
|
306
251
|
|
|
307
|
-
return { exitCode, stderr: stderrLines }
|
|
308
|
-
}
|
|
309
252
|
|
|
310
253
|
/**
|
|
311
254
|
* Execute a command synchronously and return its output.
|
|
@@ -333,6 +276,10 @@ export class ChildProcess extends Feature {
|
|
|
333
276
|
.trim();
|
|
334
277
|
}
|
|
335
278
|
|
|
279
|
+
execSync(command: string, options?: any): string {
|
|
280
|
+
return this.exec(command,options)
|
|
281
|
+
}
|
|
282
|
+
|
|
336
283
|
/**
|
|
337
284
|
* Establishes a PID-file lock to prevent duplicate process instances.
|
|
338
285
|
*
|
|
@@ -493,10 +440,36 @@ export class ChildProcess extends Feature {
|
|
|
493
440
|
* off()
|
|
494
441
|
* ```
|
|
495
442
|
*/
|
|
443
|
+
/**
|
|
444
|
+
* Checks whether any process matching a given name is currently running.
|
|
445
|
+
*
|
|
446
|
+
* Uses `pgrep -x` for an exact match against process names.
|
|
447
|
+
*
|
|
448
|
+
* @param {string} name - The process name to look for (e.g. 'afplay', 'node', 'nginx')
|
|
449
|
+
* @returns {boolean} True if at least one matching process is running
|
|
450
|
+
*
|
|
451
|
+
* @example
|
|
452
|
+
* ```typescript
|
|
453
|
+
* if (proc.isProcessRunning('afplay')) {
|
|
454
|
+
* console.log('Audio is currently playing')
|
|
455
|
+
* }
|
|
456
|
+
* ```
|
|
457
|
+
*/
|
|
458
|
+
isProcessRunning(name: string): boolean {
|
|
459
|
+
try {
|
|
460
|
+
const output = execSync(`pgrep -x ${name}`, { stdio: ['pipe', 'pipe', 'pipe'] })
|
|
461
|
+
.toString()
|
|
462
|
+
.trim()
|
|
463
|
+
return output.length > 0
|
|
464
|
+
} catch {
|
|
465
|
+
return false
|
|
466
|
+
}
|
|
467
|
+
}
|
|
468
|
+
|
|
496
469
|
onSignal(signal: NodeJS.Signals, handler: () => void): () => void {
|
|
497
470
|
process.on(signal, handler)
|
|
498
471
|
return () => process.removeListener(signal, handler)
|
|
499
472
|
}
|
|
500
473
|
}
|
|
501
474
|
|
|
502
|
-
export default
|
|
475
|
+
export default ChildProcess
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { z } from 'zod'
|
|
2
2
|
import { FeatureStateSchema, FeatureOptionsSchema, FeatureEventsSchema } from '../../schemas/base.js'
|
|
3
|
-
import { Feature
|
|
3
|
+
import { Feature } from '../feature.js'
|
|
4
4
|
import { State } from '../../state.js'
|
|
5
5
|
import { Bus, type EventMap } from '../../bus.js'
|
|
6
6
|
|
|
@@ -335,6 +335,7 @@ export class ProcessManager extends Feature {
|
|
|
335
335
|
static override stateSchema = ProcessManagerStateSchema
|
|
336
336
|
static override optionsSchema = ProcessManagerOptionsSchema
|
|
337
337
|
static override eventsSchema = ProcessManagerEventsSchema
|
|
338
|
+
static { Feature.register(this, 'processManager') }
|
|
338
339
|
|
|
339
340
|
private _handlers = new Map<string, SpawnHandler>()
|
|
340
341
|
private _cleanupRegistered = false
|
|
@@ -539,4 +540,4 @@ export class ProcessManager extends Feature {
|
|
|
539
540
|
}
|
|
540
541
|
}
|
|
541
542
|
|
|
542
|
-
export default
|
|
543
|
+
export default ProcessManager
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { z } from 'zod'
|
|
2
2
|
import { FeatureStateSchema, FeatureOptionsSchema } from '../../schemas/base.js'
|
|
3
|
-
import {
|
|
3
|
+
import { Feature } from "../feature.js";
|
|
4
4
|
import { existsSync } from 'fs';
|
|
5
5
|
import { join, resolve } from 'path';
|
|
6
6
|
|
|
@@ -64,6 +64,7 @@ export class Python<
|
|
|
64
64
|
static override shortcut = "features.python" as const
|
|
65
65
|
static override stateSchema = PythonStateSchema
|
|
66
66
|
static override optionsSchema = PythonOptionsSchema
|
|
67
|
+
static { Feature.register(this, 'python') }
|
|
67
68
|
|
|
68
69
|
override get initialState(): T {
|
|
69
70
|
return {
|
|
@@ -434,8 +435,7 @@ export class Python<
|
|
|
434
435
|
}
|
|
435
436
|
}
|
|
436
437
|
|
|
437
|
-
export default
|
|
438
|
-
|
|
438
|
+
export default Python
|
|
439
439
|
// Module augmentation for type safety
|
|
440
440
|
declare module '../feature.js' {
|
|
441
441
|
interface AvailableFeatures {
|