@worca/app 1.3.0 → 1.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +85 -6
- package/agents/clarify.meta.json +1 -0
- package/agents/memoryDefragmenter.meta.json +2 -1
- package/agents/reviewer.meta.json +60 -0
- package/agents/worca-cc-code-reviewer.md +33 -0
- package/agents/worca-cc-memory-defragmenter.md +5 -3
- package/agents/workspaceScanner.meta.json +1 -0
- package/package.json +14 -10
- package/scripts/git-diff.mjs +25 -0
- package/scripts/gitDiff.meta.json +18 -0
- package/scripts/js-inline.mjs +11 -0
- package/scripts/js.meta.json +22 -0
- package/scripts/py-inline.py +27 -0
- package/scripts/py.meta.json +22 -0
- package/scripts/shell.meta.json +24 -0
- package/skills/worca/SKILL.md +3 -2
- package/src/cli/models.mjs +247 -0
- package/src/cli/render.mjs +72 -4
- package/src/cli/schedule.mjs +494 -0
- package/src/cli/worca-cc.mjs +1001 -22
- package/src/core/agent-registry.mjs +75 -23
- package/src/core/agent-store.mjs +51 -2
- package/src/core/artifacts.mjs +73 -10
- package/src/core/ask/events.mjs +119 -1
- package/src/core/ask/limits.mjs +32 -4
- package/src/core/ask/mcp-stdio.mjs +12 -0
- package/src/core/ask/model-deps.mjs +126 -0
- package/src/core/ask/model-proposal.mjs +370 -0
- package/src/core/ask/models.mjs +12 -0
- package/src/core/ask/policy-deps.mjs +124 -0
- package/src/core/ask/policy-proposal.mjs +363 -0
- package/src/core/ask/prompt.mjs +74 -9
- package/src/core/ask/proposal.mjs +54 -5
- package/src/core/ask/schedule-deps.mjs +83 -0
- package/src/core/ask/schedule-spec.mjs +310 -0
- package/src/core/ask/script-deps.mjs +357 -0
- package/src/core/ask/source-deps.mjs +52 -0
- package/src/core/ask/source-spec.mjs +157 -0
- package/src/core/ask/spawn.mjs +1 -0
- package/src/core/ask/store.mjs +6 -3
- package/src/core/ask/tool-deps.mjs +4 -0
- package/src/core/ask/tools.mjs +657 -37
- package/src/core/ask/turn.mjs +109 -2
- package/src/core/ask-files.mjs +406 -0
- package/src/core/ask-forms.mjs +195 -0
- package/src/core/ask-projection.mjs +72 -0
- package/src/core/bridge/errors.mjs +84 -0
- package/src/core/bridge/provider-ops.mjs +281 -0
- package/src/core/bridge/providers/copilot.mjs +269 -0
- package/src/core/bridge/providers/endpoint.mjs +257 -0
- package/src/core/bridge/registry.mjs +88 -0
- package/src/core/bridge/semaphore.mjs +73 -0
- package/src/core/bridge/server.mjs +184 -0
- package/src/core/bridge/telemetry.mjs +53 -0
- package/src/core/bridge/translate/request.mjs +252 -0
- package/src/core/bridge/translate/response.mjs +82 -0
- package/src/core/bridge/translate/stream.mjs +242 -0
- package/src/core/bridge/upstream.mjs +209 -0
- package/src/core/chat/command-router.mjs +58 -4
- package/src/core/chat/notifier.mjs +14 -1
- package/src/core/chat/renderers.mjs +35 -0
- package/src/core/claude-runner.mjs +126 -19
- package/src/core/config.mjs +212 -31
- package/src/core/cost-budget.mjs +3 -2
- package/src/core/db.mjs +169 -15
- package/src/core/failure-policy.mjs +10 -0
- package/src/core/fs-browse.mjs +16 -4
- package/src/core/git-info.mjs +22 -0
- package/src/core/graph/builtin-workflows.mjs +3 -1
- package/src/core/graph/exec-io.mjs +71 -0
- package/src/core/graph/executor.mjs +139 -70
- package/src/core/graph/human-evidence.mjs +131 -0
- package/src/core/graph/python-probe.mjs +172 -0
- package/src/core/graph/registry-ports.mjs +10 -6
- package/src/core/graph/scheduler.mjs +39 -24
- package/src/core/graph/script-child.mjs +81 -0
- package/src/core/graph/script-runner.mjs +597 -0
- package/src/core/graph/worca_script.py +207 -0
- package/src/core/guardrail-store.mjs +16 -0
- package/src/core/human-backfill.mjs +108 -0
- package/src/core/human-rate.mjs +17 -0
- package/src/core/index-html.mjs +6 -2
- package/src/core/memory-defrag-model.mjs +112 -0
- package/src/core/memory-store.mjs +70 -18
- package/src/core/memory-sync.mjs +22 -11
- package/src/core/metrics/read.mjs +4 -1
- package/src/core/metrics/record.mjs +50 -2
- package/src/core/metrics/sync.mjs +6 -4
- package/src/core/model-env.mjs +149 -0
- package/src/core/model-test.mjs +14 -1
- package/src/core/notifications.mjs +128 -0
- package/src/core/onboarding.mjs +8 -2
- package/src/core/orchestrator.mjs +357 -26
- package/src/core/phases.mjs +95 -6
- package/src/core/plugin-api.mjs +24 -7
- package/src/core/plugin-manifest.mjs +184 -18
- package/src/core/plugin-models.mjs +1 -0
- package/src/core/plugin-script-cases.mjs +118 -0
- package/src/core/plugin-store.mjs +163 -17
- package/src/core/plugin-workflows.mjs +71 -17
- package/src/core/policy/cache.mjs +116 -0
- package/src/core/policy/effective.mjs +175 -0
- package/src/core/policy/gate.mjs +91 -0
- package/src/core/policy/local.mjs +145 -0
- package/src/core/policy/registry.mjs +330 -0
- package/src/core/policy/scope.mjs +61 -0
- package/src/core/policy/state.mjs +79 -0
- package/src/core/policy/sync.mjs +513 -0
- package/src/core/protocol.mjs +43 -0
- package/src/core/run-harness.mjs +421 -72
- package/src/core/scheduler.mjs +980 -0
- package/src/core/script-bench.mjs +628 -0
- package/src/core/script-registry.mjs +116 -0
- package/src/core/script-store.mjs +563 -0
- package/src/core/settings.mjs +489 -14
- package/src/core/stats.mjs +33 -2
- package/src/core/workflow-export.mjs +94 -3
- package/src/core/workflow-share.mjs +67 -18
- package/src/core/workflows.mjs +47 -11
- package/src/core/workspaces.mjs +18 -12
- package/src/shared/forms/answer.mjs +164 -0
- package/src/shared/forms/catalog.mjs +91 -0
- package/src/shared/forms/form-def.mjs +290 -0
- package/src/shared/forms/layout.mjs +67 -0
- package/src/shared/forms/paths.mjs +47 -0
- package/src/shared/forms/project.mjs +309 -0
- package/src/shared/forms/schema.mjs +205 -0
- package/src/shared/graph/agent-meta.mjs +55 -5
- package/src/shared/graph/constants.mjs +14 -2
- package/src/shared/graph/flow-layout.mjs +2 -1
- package/src/shared/graph/isomorphic.mjs +5 -3
- package/src/shared/graph/manifest.mjs +22 -13
- package/src/shared/graph/ports.mjs +45 -19
- package/src/shared/graph/script-cases.mjs +257 -0
- package/src/shared/graph/script-icons.mjs +46 -0
- package/src/shared/graph/script-infer.mjs +259 -0
- package/src/shared/graph/script-meta.mjs +408 -0
- package/src/shared/graph/script-templates.mjs +201 -0
- package/src/shared/graph/template.mjs +4 -4
- package/src/shared/graph/validate.mjs +89 -16
- package/src/shared/human-estimate.mjs +100 -0
- package/src/shared/schedule/recurrence.mjs +353 -0
- package/src/shared/team-metrics/aggregate.mjs +51 -11
- package/{scripts → tools}/install.mjs +3 -3
- package/ui/public/app.js +4390 -683
- package/ui/public/artifact-picker.mjs +189 -0
- package/ui/public/ask/dom.mjs +121 -0
- package/ui/public/ask/form-preview.mjs +55 -0
- package/ui/public/ask/form-renderer.mjs +250 -0
- package/ui/public/ask/registry.mjs +53 -0
- package/ui/public/ask/widgets-display.mjs +370 -0
- package/ui/public/ask/widgets-input.mjs +624 -0
- package/ui/public/ask/widgets-layout.mjs +90 -0
- package/ui/public/ask-panel.mjs +401 -27
- package/ui/public/ask-run-card.mjs +1 -1
- package/ui/public/bridge-view.mjs +694 -0
- package/ui/public/chat-settings-view.mjs +24 -0
- package/ui/public/code-editor.mjs +181 -0
- package/ui/public/getting-started.mjs +34 -7
- package/ui/public/graph/composer.mjs +138 -10
- package/ui/public/graph/inspector.mjs +61 -58
- package/ui/public/graph/palette.mjs +27 -9
- package/ui/public/graph/run-decor.mjs +34 -17
- package/ui/public/graph/run-hosts.mjs +7 -1
- package/ui/public/graph/save-dialog.mjs +3 -0
- package/ui/public/graph/view.mjs +23 -7
- package/ui/public/guardrails-view.mjs +15 -3
- package/ui/public/guide-spot.mjs +87 -9
- package/ui/public/index.html +480 -141
- package/ui/public/memory-view.mjs +22 -4
- package/ui/public/models-view.mjs +162 -17
- package/ui/public/node-tunables.mjs +33 -4
- package/ui/public/plugins-view.mjs +23 -1
- package/ui/public/results-view.mjs +4 -2
- package/ui/public/schedule-sheet.mjs +430 -0
- package/ui/public/schedules-view.mjs +432 -0
- package/ui/public/script-bench-view.mjs +1154 -0
- package/ui/public/script-forms.mjs +282 -0
- package/ui/public/script-wizard.mjs +529 -0
- package/ui/public/scripts-view.mjs +868 -0
- package/ui/public/stats-view.mjs +159 -52
- package/ui/public/style.css +1461 -44
- package/ui/public/team-metrics-surfaces.mjs +77 -16
- package/ui/public/team-metrics-view.mjs +68 -5
- package/ui/public/team-policy-view.mjs +1402 -0
- package/ui/public/ui-level.mjs +237 -0
- package/ui/server.mjs +1827 -73
|
@@ -0,0 +1,116 @@
|
|
|
1
|
+
// src/core/script-registry.mjs
|
|
2
|
+
// Data-driven script registry (spec §8.1): scripts/*.meta.json (built-in) +
|
|
3
|
+
// ~/.worca-cc/scripts (user) + <plugin>/current/scripts (enabled plugins), merged
|
|
4
|
+
// builtin > user > plugin, sorted by `.order`. A sibling of agent-registry.mjs
|
|
5
|
+
// that shares its layer scanner and its plugin-layer walk. D16: keys share ONE
|
|
6
|
+
// namespace with agents — a script whose key an agent holds is dropped here,
|
|
7
|
+
// with a warning, so a log role, a results row and a palette pill are never
|
|
8
|
+
// ambiguous. Read synchronously, no cache: always reloadable.
|
|
9
|
+
import { join, resolve, isAbsolute, sep } from 'node:path';
|
|
10
|
+
import { fileURLToPath } from 'node:url';
|
|
11
|
+
import { worcaHome } from './projects.mjs';
|
|
12
|
+
import { scanMetaLayer, pluginLayers, loadAgentRegistry } from './agent-registry.mjs';
|
|
13
|
+
import { normalizeScriptMeta, resolvePlatformValue } from '../shared/graph/script-meta.mjs';
|
|
14
|
+
|
|
15
|
+
/** The built-in layer: repo `scripts/` (D20), the pair of `agents/`. fileURLToPath, never `.pathname` (Windows). */
|
|
16
|
+
export const DEFAULT_SCRIPTS_DIR = fileURLToPath(new URL('../../scripts/', import.meta.url));
|
|
17
|
+
|
|
18
|
+
/** <worcaHome()>/scripts, resolved fresh; null when the home cannot be resolved (bare node:test). */
|
|
19
|
+
export function userScriptsDir() {
|
|
20
|
+
try { return join(worcaHome(), 'scripts'); } catch { return null; }
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
export function pluginScriptLayers() { return pluginLayers('scripts'); }
|
|
24
|
+
|
|
25
|
+
/** The registry's normalizer: the shared one, with the skip-and-warn contract the loader needs. */
|
|
26
|
+
export function normalizeScript(raw, { warn = console.warn } = {}) {
|
|
27
|
+
const key = typeof raw?.key === 'string' && raw.key.trim() ? raw.key.trim() : '<unkeyed>';
|
|
28
|
+
const { meta, errors } = normalizeScriptMeta(raw, { warn });
|
|
29
|
+
if (errors.length) {
|
|
30
|
+
warn(`[script-registry] sidecar "${key}" is invalid; skipped: ${errors.join('; ')}`);
|
|
31
|
+
return null;
|
|
32
|
+
}
|
|
33
|
+
return meta;
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
/** Stamp the host-platform program path and command. A `file` that resolves
|
|
37
|
+
* outside its layer dir drops the sidecar (belt and braces behind the basename rule). */
|
|
38
|
+
function stampPaths(dir, origin, platform, onDrop) {
|
|
39
|
+
return ({ meta, file }) => {
|
|
40
|
+
const rel = resolvePlatformValue(meta.file, platform);
|
|
41
|
+
if (meta.file && !rel) {
|
|
42
|
+
console.warn(`[script-registry] ${origin}/${file}: file has no entry for ${platform}; skipped`);
|
|
43
|
+
if (onDrop) onDrop({ origin, file, reason: `no file for ${platform}` });
|
|
44
|
+
return null;
|
|
45
|
+
}
|
|
46
|
+
if (rel && (isAbsolute(rel) || !resolve(dir, rel).startsWith(resolve(dir) + sep))) {
|
|
47
|
+
console.warn(`[script-registry] ${origin}/${file}: file "${rel}" resolves outside the scripts dir — ignored`);
|
|
48
|
+
if (onDrop) onDrop({ origin, file, reason: `file "${rel}" resolves outside the scripts dir` });
|
|
49
|
+
return null;
|
|
50
|
+
}
|
|
51
|
+
meta.scriptPath = rel ? join(dir, rel) : null; // computed, never stored
|
|
52
|
+
meta.commandResolved = resolvePlatformValue(meta.command, platform);
|
|
53
|
+
meta.scriptsDir = dir;
|
|
54
|
+
return meta;
|
|
55
|
+
};
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
/**
|
|
59
|
+
* @param {{scriptsDir?:string, userScriptsDir?:string|null, includePlugins?:boolean,
|
|
60
|
+
* agentKeys?:Set<string>|string[]|null, onDrop?:Function, platform?:string}} [opts]
|
|
61
|
+
* agentKeys: the agent registry's keys (D16). Absent => loadAgentRegistry() is
|
|
62
|
+
* consulted; null => no collision check (tests).
|
|
63
|
+
* @returns {Record<string, object>} script key -> meta, sorted by `.order`
|
|
64
|
+
*/
|
|
65
|
+
export function loadScriptRegistry(opts = {}) {
|
|
66
|
+
const platform = opts.platform || process.platform;
|
|
67
|
+
const onDrop = typeof opts.onDrop === 'function' ? opts.onDrop : null;
|
|
68
|
+
const scriptsDir = opts.scriptsDir || DEFAULT_SCRIPTS_DIR;
|
|
69
|
+
const scan = (dir, origin, extra = {}) => scanMetaLayer(dir, origin, { normalize: normalizeScript, tag: 'script-registry', onDrop, ...extra })
|
|
70
|
+
.map(stampPaths(dir, origin, platform, onDrop)).filter(Boolean);
|
|
71
|
+
|
|
72
|
+
const builtins = scan(scriptsDir, 'builtin');
|
|
73
|
+
const taken = new Set(builtins.map((m) => m.key));
|
|
74
|
+
const userDir = opts.userScriptsDir === undefined ? userScriptsDir() : opts.userScriptsDir;
|
|
75
|
+
const users = [];
|
|
76
|
+
if (userDir) {
|
|
77
|
+
for (const m of scan(userDir, 'user')) {
|
|
78
|
+
if (taken.has(m.key)) {
|
|
79
|
+
console.warn(`[script-registry] user script "${m.key}" shadows a built-in and was skipped (built-ins are immutable)`);
|
|
80
|
+
if (onDrop) onDrop({ origin: 'user', file: `${m.key}.meta.json`, reason: 'shadows a built-in script' });
|
|
81
|
+
continue;
|
|
82
|
+
}
|
|
83
|
+
taken.add(m.key);
|
|
84
|
+
users.push(m);
|
|
85
|
+
}
|
|
86
|
+
}
|
|
87
|
+
const plugins = [];
|
|
88
|
+
if (opts.includePlugins !== false) {
|
|
89
|
+
for (const { plugin, dir, builtFor } of pluginScriptLayers()) {
|
|
90
|
+
for (const m of scan(dir, `plugin:${plugin}`, { builtFor })) {
|
|
91
|
+
if (taken.has(m.key)) {
|
|
92
|
+
console.warn(`[script-registry] plugin script "${m.key}" (plugin "${plugin}") collides with an existing script and was skipped`);
|
|
93
|
+
if (onDrop) onDrop({ origin: `plugin:${plugin}`, file: `${m.key}.meta.json`, reason: 'collides with an existing script' });
|
|
94
|
+
continue;
|
|
95
|
+
}
|
|
96
|
+
taken.add(m.key);
|
|
97
|
+
plugins.push(m);
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
}
|
|
101
|
+
// D16: agents win a shared key, deterministically.
|
|
102
|
+
const agentKeys = opts.agentKeys === null ? new Set()
|
|
103
|
+
: opts.agentKeys instanceof Set ? opts.agentKeys
|
|
104
|
+
: Array.isArray(opts.agentKeys) ? new Set(opts.agentKeys)
|
|
105
|
+
: new Set(Object.keys(loadAgentRegistry()));
|
|
106
|
+
const registry = {};
|
|
107
|
+
for (const m of [...builtins, ...users, ...plugins].sort((a, b) => a.order - b.order)) {
|
|
108
|
+
if (agentKeys.has(m.key)) {
|
|
109
|
+
console.warn(`[script-registry] "${m.key}" collides with an agent key; skipped`);
|
|
110
|
+
if (onDrop) onDrop({ origin: m.origin, file: `${m.key}.meta.json`, reason: 'collides with an agent key' });
|
|
111
|
+
continue;
|
|
112
|
+
}
|
|
113
|
+
registry[m.key] = m;
|
|
114
|
+
}
|
|
115
|
+
return registry;
|
|
116
|
+
}
|