@xdxer/dingtalk-agent 0.1.4-beta.7 → 0.1.4-beta.9
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/CHANGELOG.md +35 -0
- package/README.en.md +395 -0
- package/README.md +466 -36
- package/dist/bin/dingtalk-agent.js +1071 -340
- package/dist/bin/dingtalk-agent.js.map +1 -1
- package/dist/src/actions.js +98 -14
- package/dist/src/actions.js.map +1 -1
- package/dist/src/agent-audit.js +460 -0
- package/dist/src/agent-audit.js.map +1 -0
- package/dist/src/agent-bindings.js +132 -0
- package/dist/src/agent-bindings.js.map +1 -0
- package/dist/src/agent-definition.js +182 -0
- package/dist/src/agent-definition.js.map +1 -0
- package/dist/src/agent-enhance.js +678 -0
- package/dist/src/agent-enhance.js.map +1 -0
- package/dist/src/bootstrap.js +125 -17
- package/dist/src/bootstrap.js.map +1 -1
- package/dist/src/development-workspace.js +729 -0
- package/dist/src/development-workspace.js.map +1 -0
- package/dist/src/dws.js +145 -0
- package/dist/src/dws.js.map +1 -1
- package/dist/src/eval-evidence.js +193 -0
- package/dist/src/eval-evidence.js.map +1 -0
- package/dist/src/init.js +1 -1
- package/dist/src/init.js.map +1 -1
- package/dist/src/invocation.js +36 -0
- package/dist/src/invocation.js.map +1 -0
- package/dist/src/lab.js +679 -0
- package/dist/src/lab.js.map +1 -0
- package/dist/src/lease.js +100 -0
- package/dist/src/lease.js.map +1 -0
- package/dist/src/memory/candidates.js +451 -0
- package/dist/src/memory/candidates.js.map +1 -0
- package/dist/src/memory/completion-evidence.js +536 -0
- package/dist/src/memory/completion-evidence.js.map +1 -0
- package/dist/src/memory/operational.js +263 -0
- package/dist/src/memory/operational.js.map +1 -0
- package/dist/src/memory/remote-state.js +478 -0
- package/dist/src/memory/remote-state.js.map +1 -0
- package/dist/src/memory/task-checkpoints.js +204 -0
- package/dist/src/memory/task-checkpoints.js.map +1 -0
- package/dist/src/multica-deploy.js +1480 -0
- package/dist/src/multica-deploy.js.map +1 -0
- package/dist/src/multica-provider.js +685 -0
- package/dist/src/multica-provider.js.map +1 -0
- package/dist/src/opencode-evals.js +1062 -0
- package/dist/src/opencode-evals.js.map +1 -0
- package/dist/src/opencode-provider.js +531 -0
- package/dist/src/opencode-provider.js.map +1 -0
- package/dist/src/opencode-workspace.js +197 -0
- package/dist/src/opencode-workspace.js.map +1 -0
- package/dist/src/perception.js +225 -0
- package/dist/src/perception.js.map +1 -0
- package/dist/src/personal-event-evals.js +595 -0
- package/dist/src/personal-event-evals.js.map +1 -0
- package/dist/src/promotion.js +786 -0
- package/dist/src/promotion.js.map +1 -0
- package/dist/src/remote-semantic-state-live-evals.js +888 -0
- package/dist/src/remote-semantic-state-live-evals.js.map +1 -0
- package/dist/src/remote-semantic-state-worker.js +38 -0
- package/dist/src/remote-semantic-state-worker.js.map +1 -0
- package/dist/src/remote-state-evals.js +501 -0
- package/dist/src/remote-state-evals.js.map +1 -0
- package/dist/src/response-gate.js +51 -0
- package/dist/src/response-gate.js.map +1 -0
- package/dist/src/robot-evals.js +770 -0
- package/dist/src/robot-evals.js.map +1 -0
- package/dist/src/sessions.js +66 -105
- package/dist/src/sessions.js.map +1 -1
- package/dist/src/skill-manager.js +25 -16
- package/dist/src/skill-manager.js.map +1 -1
- package/dist/src/skills.js.map +1 -1
- package/dist/src/storage-evals.js +26 -0
- package/dist/src/storage-evals.js.map +1 -0
- package/dist/src/types.js.map +1 -1
- package/dist/src/waits.js +5 -1
- package/dist/src/waits.js.map +1 -1
- package/dist/src/workspace.js +28 -3
- package/dist/src/workspace.js.map +1 -1
- package/docs/INSTALLATION.md +47 -0
- package/docs/SECOND-AGENT-ACCEPTANCE.md +62 -0
- package/docs/architecture/agent-memory-topology.png +0 -0
- package/docs/architecture/agent-memory-topology.svg +132 -0
- package/docs/architecture/general-agent-kernel-topology.png +0 -0
- package/docs/architecture/general-agent-kernel-topology.svg +149 -0
- package/docs/architecture/provider-bound-development-workspace.png +0 -0
- package/docs/architecture/provider-bound-development-workspace.svg +141 -0
- package/docs/architecture/task-completion-gate.png +0 -0
- package/docs/architecture/task-completion-gate.svg +191 -0
- package/docs/schemas/agent-audit-load-evidence.schema.json +14 -0
- package/docs/schemas/agent-audit.schema.json +92 -0
- package/docs/schemas/agent-bindings.schema.json +54 -0
- package/docs/schemas/agent-definition.schema.json +78 -0
- package/docs/schemas/agent-enhancement-plan.schema.json +88 -0
- package/docs/schemas/agent-enhancement-receipt.schema.json +37 -0
- package/docs/schemas/enriched-invocation.schema.json +46 -0
- package/docs/schemas/eval-candidate-plan.schema.json +28 -0
- package/docs/schemas/eval-candidate-result.schema.json +20 -0
- package/docs/schemas/eval-candidate.schema.json +30 -0
- package/docs/schemas/invocation.schema.json +19 -0
- package/docs/schemas/memory-candidate-proposal.schema.json +18 -0
- package/docs/schemas/memory-candidate.schema.json +76 -0
- package/docs/schemas/memory-publish-target.schema.json +25 -0
- package/docs/schemas/multica-deployment-list.schema.json +29 -0
- package/docs/schemas/multica-deployment-operation.schema.json +51 -0
- package/docs/schemas/multica-deployment-plan.schema.json +70 -0
- package/docs/schemas/multica-deployment-receipt.schema.json +87 -0
- package/docs/schemas/multica-deployment-status.schema.json +23 -0
- package/docs/schemas/multica-workspace-inspection.schema.json +77 -0
- package/docs/schemas/multica-workspace-plan.schema.json +68 -0
- package/docs/schemas/multica-workspace-resource-list.schema.json +27 -0
- package/docs/schemas/multica-workspace-status.schema.json +34 -0
- package/docs/schemas/observation.schema.json +21 -0
- package/docs/schemas/operational-memory-provider.schema.json +36 -0
- package/docs/schemas/operational-memory-record.schema.json +24 -0
- package/docs/schemas/perception-input.schema.json +56 -0
- package/docs/schemas/project.schema.json +112 -0
- package/docs/schemas/promotion-list.schema.json +36 -0
- package/docs/schemas/promotion-plan.schema.json +60 -0
- package/docs/schemas/promotion-policy.schema.json +29 -0
- package/docs/schemas/promotion-receipt.schema.json +43 -0
- package/docs/schemas/promotion-status.schema.json +23 -0
- package/docs/schemas/release-readiness.schema.json +65 -0
- package/docs/schemas/remote-semantic-state-live-eval.schema.json +60 -0
- package/docs/schemas/remote-semantic-state-manifest.schema.json +79 -0
- package/docs/schemas/remote-semantic-state-provider.schema.json +98 -0
- package/docs/schemas/response-gate.schema.json +20 -0
- package/docs/schemas/task-checkpoint.schema.json +71 -0
- package/docs/schemas/task-completion-evidence.schema.json +154 -0
- package/docs/schemas/workspace-doctor.schema.json +56 -0
- package/docs/schemas/workspace-state.schema.json +39 -0
- package/evals/baselines/2026-07-16/opencode-basic-010-completion-summary.json +123 -0
- package/evals/baselines/2026-07-16/opencode-basic-skill-required-summary.json +69 -0
- package/evals/baselines/2026-07-16/opencode-multi-surface-summary.json +63 -0
- package/evals/baselines/2026-07-16/remote-state-live-summary.json +70 -0
- package/evals/baselines/2026-07-17/agent-enhance-opencode-dogfood-summary.json +98 -0
- package/evals/baselines/2026-07-17/personal-event-live-readiness-summary.json +68 -0
- package/examples/agents/fde-coach/AGENTS.md +26 -0
- package/examples/agents/fde-coach/MEMORY.md +3 -0
- package/examples/agents/fde-coach/fields/default/field.json +24 -0
- package/examples/agents/fde-coach/knowledge/INDEX.md +4 -0
- package/examples/agents/fde-coach/skills/fde-coach/SKILL.md +13 -0
- package/examples/agents/release-manager/AGENTS.md +26 -0
- package/examples/agents/release-manager/MEMORY.md +3 -0
- package/examples/agents/release-manager/fields/default/field.json +24 -0
- package/examples/agents/release-manager/knowledge/INDEX.md +4 -0
- package/examples/agents/release-manager/skills/release-manager/SKILL.md +13 -0
- package/lab/README.md +109 -0
- package/lab/agent-eval/catalog.json +91 -0
- package/lab/agent-eval/classic-failures.json +177 -0
- package/lab/agent-eval/completion-gate-regression.json +99 -0
- package/lab/agent-eval/personal-event-live.example.json +94 -0
- package/lab/agent-eval/remote-semantic-state-live.example.json +70 -0
- package/lab/agent-eval/remote-semantic-state-provider.fixture.json +47 -0
- package/lab/agent-eval/remote-state-workspace/AGENTS.md +8 -0
- package/lab/agent-eval/remote-state-workspace/opencode.json +7 -0
- package/lab/agent-eval/remote-state-workspace/skills/remote-state-operator/SKILL.md +13 -0
- package/lab/agent-eval/remote-state.example.json +31 -0
- package/lab/agent-eval/workspace/AGENTS.md +7 -0
- package/lab/agent-eval/workspace/MEMORY.md +4 -0
- package/lab/agent-eval/workspace/artifacts/pending-review.md +3 -0
- package/lab/agent-eval/workspace/knowledge/INDEX.md +4 -0
- package/lab/agent-eval/workspace/opencode.json +20 -0
- package/lab/manifest.example.json +27 -0
- package/lab/manifest.personal-event.example.json +27 -0
- package/lab/project-workspace/README.md +11 -0
- package/lab/project-workspace/fake-multica-provider.mjs +266 -0
- package/lab/project-workspace/multica-deploy.fixture.json +29 -0
- package/lab/project-workspace/multica-readonly.fixture.json +69 -0
- package/lab/project-workspace/observation.fixture.json +14 -0
- package/lab/project-workspace/opencode-provider-suite.json +65 -0
- package/lab/project-workspace/project.fixture.json +44 -0
- package/lab/project-workspace/promotion-policy.fixture.json +15 -0
- package/lab/robot-eval/pool.example.json +30 -0
- package/lab/robot-eval/suite.json +123 -0
- package/lab/robot-eval/workspace/AGENTS.md +21 -0
- package/lab/robot-eval/workspace/MEMORY.md +3 -0
- package/lab/robot-eval/workspace/knowledge/INDEX.md +5 -0
- package/lab/robot-eval/workspace/opencode.json +22 -0
- package/lab/schemas/agent-eval-catalog.schema.json +47 -0
- package/lab/schemas/lab-manifest.schema.json +70 -0
- package/lab/schemas/personal-event-eval.schema.json +91 -0
- package/lab/schemas/remote-state-eval.schema.json +66 -0
- package/lab/schemas/robot-eval-suite.schema.json +184 -0
- package/lab/schemas/robot-pool.schema.json +56 -0
- package/package.json +30 -14
- package/skills/dingtalk-agent-boot-multica/SKILL.md +40 -0
- package/skills/dingtalk-agent-compose/SKILL.md +110 -0
- package/skills/dingtalk-agent-compose/assets/AGENTS.template.md +26 -0
- package/skills/dingtalk-agent-compose/assets/agent.bindings.dingtalk-doc.template.json +13 -0
- package/skills/dingtalk-agent-compose/assets/agent.bindings.local.template.json +13 -0
- package/skills/dingtalk-agent-compose/assets/opencode.template.json +12 -0
- package/skills/dingtalk-agent-compose/assets/role-skill.template.md +24 -0
- package/skills/dingtalk-agent-compose/evals/evals.json +94 -0
- package/skills/dingtalk-agent-compose/references/agent-definition-contract.md +55 -0
- package/skills/dingtalk-agent-compose/references/opencode-host-contract.md +65 -0
- package/skills/dingtalk-agent-compose/references/storage-routing.md +20 -0
- package/skills/dingtalk-agent-deploy/SKILL.md +60 -0
- package/skills/dingtalk-agent-deploy/references/multica-deployment-contract.md +49 -0
- package/skills/dingtalk-agent-deploy/references/promotion-observation-contract.md +49 -0
- package/skills/dingtalk-agent-eval/SKILL.md +116 -0
- package/skills/dingtalk-agent-eval/assets/eval-catalog.template.json +18 -0
- package/skills/dingtalk-agent-eval/evals/evals.json +61 -0
- package/skills/dingtalk-agent-eval/references/eval-topology.md +34 -0
- package/skills/dingtalk-agent-eval/references/evidence-contract.md +31 -0
- package/skills/dingtalk-agent-eval/references/scenario-taxonomy.md +25 -0
- package/skills/dingtalk-agent-eval/references/storage-modes.md +75 -0
- package/skills/dingtalk-basic-behavior/SKILL.md +63 -3
- package/skills/dingtalk-basic-behavior/assets/memory-candidate-proposal.json +10 -0
- package/skills/dingtalk-basic-behavior/assets/{task-checkpoint.md → task-checkpoint.json} +2 -21
- package/skills/dingtalk-basic-behavior/references/action-contract.md +2 -0
- package/skills/dingtalk-basic-behavior/references/memory-and-evolution.md +15 -1
- package/skills/dingtalk-basic-behavior/references/perception-and-gates.md +28 -0
- package/skills/dingtalk-basic-behavior/references/task-lifecycle.md +32 -7
- package/dist/src/boot.js +0 -70
- package/dist/src/boot.js.map +0 -1
- package/dist/src/duty.js +0 -74
- package/dist/src/duty.js.map +0 -1
- package/dist/src/kb.js +0 -240
- package/dist/src/kb.js.map +0 -1
- package/dist/src/runs.js +0 -79
- package/dist/src/runs.js.map +0 -1
- package/docs/ARCHITECTURE.md +0 -219
- package/docs/MINIMAL-WORKSPACE-V1.md +0 -172
- package/docs/OPEN-SOURCE-REFERENCES.md +0 -107
- package/docs/SELF-TEST.md +0 -252
- package/docs//345/206/205/347/275/221/345/256/236/347/233/270.md +0 -77
- package/evals/baselines/2026-07-14/behavior-summary.json +0 -28
- package/evals/baselines/2026-07-14/contract-summary.json +0 -18
- package/evals/baselines/2026-07-14/live-canary-summary.json +0 -25
- package/evals/baselines/2026-07-15/dingtalk-basic-behavior-0.3.0/SKILL.md +0 -72
- package/evals/baselines/2026-07-15/dingtalk-basic-behavior-0.3.0/references/action-contract.md +0 -31
- package/evals/baselines/2026-07-15/dingtalk-basic-behavior-0.3.0/references/event-to-behavior.md +0 -22
- package/evals/baselines/2026-07-15/dingtalk-basic-behavior-0.3.0/references/memory-and-evolution.md +0 -25
- package/evals/baselines/2026-07-15/dingtalk-basic-behavior-0.3.0/references/runtime-modes.md +0 -34
- package/evals/baselines/2026-07-15/task-lifecycle-summary.json +0 -50
- package/evals/evals.json +0 -339
- package/evals/fixtures/dm-ambiguous-send.json +0 -4
- package/evals/fixtures/dm-blocked.json +0 -4
- package/evals/fixtures/dm-clear.json +0 -4
- package/evals/fixtures/dm-discussion.json +0 -4
- package/evals/fixtures/dm-doc-write-no-tool.json +0 -4
- package/evals/fixtures/dm-long-task-ack.json +0 -4
- package/evals/fixtures/dm-nonblocking-gap.json +0 -4
- package/evals/fixtures/dm-structured-task.json +0 -4
- package/evals/fixtures/group.json +0 -10
- package/evals/fixtures/mentioned.json +0 -3
- package/evals/run-contract-evals.mjs +0 -1169
- package/evals/run-shadow-evals.mjs +0 -267
- package/evals/runners/README.md +0 -66
- package/evals/runners/claude-shadow.mjs +0 -533
- package/evals/schemas/action-request.schema.json +0 -77
- package/evals/shadow-evals.json +0 -133
- package/skills/AGENTS.md +0 -104
- package/skills//344/273/273/345/212/241.md +0 -48
- package/skills//345/237/272/347/241/200/350/241/214/344/270/272.md +0 -44
- package/skills//345/277/203/350/267/263.md +0 -79
- package/skills//346/266/210/346/201/257.md +0 -50
- package/skills//347/237/245/350/257/206.md +0 -55
- package/skills//350/257/204/346/265/213.md +0 -62
- package/skills//351/222/211/351/222/211.md +0 -64
- package/templates/ontology/index.md +0 -24
- package/templates/ontology/self/access.md +0 -38
- package/templates/ontology/self/role-spec.md +0 -34
- package/templates/ontology/self/workspace.md +0 -41
|
@@ -0,0 +1,193 @@
|
|
|
1
|
+
import { copyFileSync, existsSync, lstatSync, mkdirSync, readFileSync, realpathSync, } from 'node:fs';
|
|
2
|
+
import { createHash } from 'node:crypto';
|
|
3
|
+
import { basename, dirname, isAbsolute, join, relative, resolve } from 'node:path';
|
|
4
|
+
import { bootstrap } from './bootstrap.js';
|
|
5
|
+
/**
|
|
6
|
+
* Canonicalize an evidence/tool path even when the final file does not exist yet.
|
|
7
|
+
* Resolving the nearest existing ancestor also normalizes macOS /var -> /private/var
|
|
8
|
+
* aliases, which prevents a valid system-temp sandbox path from being misclassified.
|
|
9
|
+
*/
|
|
10
|
+
export function canonicalEvalPath(input) {
|
|
11
|
+
let cursor = resolve(input);
|
|
12
|
+
const missing = [];
|
|
13
|
+
while (!existsSync(cursor)) {
|
|
14
|
+
const parent = dirname(cursor);
|
|
15
|
+
if (parent === cursor)
|
|
16
|
+
break;
|
|
17
|
+
missing.unshift(basename(cursor));
|
|
18
|
+
cursor = parent;
|
|
19
|
+
}
|
|
20
|
+
const existing = existsSync(cursor) ? realpathSync(cursor) : cursor;
|
|
21
|
+
return resolve(existing, ...missing);
|
|
22
|
+
}
|
|
23
|
+
export function isWorkspacePathInside(workspace, input) {
|
|
24
|
+
const rel = relative(canonicalEvalPath(workspace), canonicalEvalPath(input));
|
|
25
|
+
return rel === '' ||
|
|
26
|
+
(rel !== '..' && !rel.startsWith(`..${process.platform === 'win32' ? '\\' : '/'}`));
|
|
27
|
+
}
|
|
28
|
+
export function relativeWorkspacePath(workspace, input) {
|
|
29
|
+
return relative(canonicalEvalPath(workspace), canonicalEvalPath(input))
|
|
30
|
+
.split('\\').join('/') || '.';
|
|
31
|
+
}
|
|
32
|
+
export function evaluateWorkspaceEvidence(workspace, expectations = []) {
|
|
33
|
+
const root = realpathSync(resolve(workspace));
|
|
34
|
+
return expectations.map((expectation) => {
|
|
35
|
+
try {
|
|
36
|
+
if (expectation.type === 'agentDefinition') {
|
|
37
|
+
const definition = bootstrap(root).definition;
|
|
38
|
+
const skills = definition.skills.map((item) => item.name);
|
|
39
|
+
const missing = expectation.requiredSkills.filter((name) => !skills.includes(name));
|
|
40
|
+
const passed = definition.status === expectation.status && missing.length === 0;
|
|
41
|
+
return {
|
|
42
|
+
id: expectation.id,
|
|
43
|
+
surface: expectation.surface,
|
|
44
|
+
type: expectation.type,
|
|
45
|
+
passed,
|
|
46
|
+
detail: `status=${definition.status}; skills=${skills.join(',')}; missing=${missing.join(',') || '-'}`,
|
|
47
|
+
hash: definition.hash,
|
|
48
|
+
};
|
|
49
|
+
}
|
|
50
|
+
const path = safeEvidencePath(root, expectation.path);
|
|
51
|
+
const rel = relative(root, path).split('\\').join('/');
|
|
52
|
+
if (expectation.type === 'pathAbsent') {
|
|
53
|
+
return {
|
|
54
|
+
id: expectation.id, surface: expectation.surface, type: expectation.type,
|
|
55
|
+
passed: !existsSync(path), path: rel,
|
|
56
|
+
detail: existsSync(path) ? `unexpected path exists: ${rel}` : `absent: ${rel}`,
|
|
57
|
+
};
|
|
58
|
+
}
|
|
59
|
+
if (!existsSync(path)) {
|
|
60
|
+
return {
|
|
61
|
+
id: expectation.id, surface: expectation.surface, type: expectation.type,
|
|
62
|
+
passed: false, path: rel, detail: `missing: ${rel}`,
|
|
63
|
+
};
|
|
64
|
+
}
|
|
65
|
+
// Existing symlinks are resolved after the lexical check so they cannot escape the sandbox.
|
|
66
|
+
safeEvidencePath(root, expectation.path, true);
|
|
67
|
+
const stat = lstatSync(path);
|
|
68
|
+
if (stat.isSymbolicLink())
|
|
69
|
+
throw new Error(`不接受符号链接证据: ${rel}`);
|
|
70
|
+
if (expectation.type === 'pathExists') {
|
|
71
|
+
const kindMatched = expectation.kind === undefined ||
|
|
72
|
+
(expectation.kind === 'file' ? stat.isFile() : stat.isDirectory());
|
|
73
|
+
const bytes = stat.isFile() ? stat.size : 0;
|
|
74
|
+
const sizeMatched = expectation.minBytes === undefined || bytes >= expectation.minBytes;
|
|
75
|
+
return {
|
|
76
|
+
id: expectation.id, surface: expectation.surface, type: expectation.type,
|
|
77
|
+
passed: kindMatched && sizeMatched, path: rel,
|
|
78
|
+
detail: `kind=${stat.isFile() ? 'file' : stat.isDirectory() ? 'directory' : 'other'}; bytes=${bytes}`,
|
|
79
|
+
hash: stat.isFile() ? sha256(readFileSync(path)) : undefined,
|
|
80
|
+
};
|
|
81
|
+
}
|
|
82
|
+
if (!stat.isFile())
|
|
83
|
+
throw new Error(`文本/JSON 证据必须是文件: ${rel}`);
|
|
84
|
+
const body = readFileSync(path, 'utf8');
|
|
85
|
+
if (expectation.type === 'textIncludesAll' || expectation.type === 'textExcludesAll') {
|
|
86
|
+
const matches = expectation.values.filter((value) => body.includes(value));
|
|
87
|
+
const passed = expectation.type === 'textIncludesAll'
|
|
88
|
+
? matches.length === expectation.values.length
|
|
89
|
+
: matches.length === 0;
|
|
90
|
+
return {
|
|
91
|
+
id: expectation.id, surface: expectation.surface, type: expectation.type,
|
|
92
|
+
passed, path: rel, hash: sha256(body),
|
|
93
|
+
detail: `matched=${JSON.stringify(matches)}; expected=${JSON.stringify(expectation.values)}`,
|
|
94
|
+
};
|
|
95
|
+
}
|
|
96
|
+
if (expectation.type !== 'jsonEquals')
|
|
97
|
+
throw new Error(`未知证据断言: ${expectation.type}`);
|
|
98
|
+
const parsed = JSON.parse(body);
|
|
99
|
+
const actual = jsonPointer(parsed, expectation.pointer);
|
|
100
|
+
const passed = stable(actual) === stable(expectation.value);
|
|
101
|
+
return {
|
|
102
|
+
id: expectation.id, surface: expectation.surface, type: expectation.type,
|
|
103
|
+
passed, path: rel, hash: sha256(body),
|
|
104
|
+
detail: `pointer=${expectation.pointer}; actual=${stable(actual)}; expected=${stable(expectation.value)}`,
|
|
105
|
+
};
|
|
106
|
+
}
|
|
107
|
+
catch (error) {
|
|
108
|
+
return {
|
|
109
|
+
id: expectation.id,
|
|
110
|
+
surface: expectation.surface,
|
|
111
|
+
type: expectation.type,
|
|
112
|
+
passed: false,
|
|
113
|
+
detail: error.message,
|
|
114
|
+
...('path' in expectation ? { path: expectation.path } : {}),
|
|
115
|
+
};
|
|
116
|
+
}
|
|
117
|
+
});
|
|
118
|
+
}
|
|
119
|
+
export function snapshotWorkspaceEvidence(workspace, output, expectations = []) {
|
|
120
|
+
const root = realpathSync(resolve(workspace));
|
|
121
|
+
const snapshots = [];
|
|
122
|
+
const seen = new Set();
|
|
123
|
+
for (const expectation of expectations) {
|
|
124
|
+
if (!('path' in expectation) || expectation.type === 'pathAbsent')
|
|
125
|
+
continue;
|
|
126
|
+
const source = safeEvidencePath(root, expectation.path, true);
|
|
127
|
+
if (!existsSync(source))
|
|
128
|
+
continue;
|
|
129
|
+
const stat = lstatSync(source);
|
|
130
|
+
if (!stat.isFile() || stat.isSymbolicLink())
|
|
131
|
+
continue;
|
|
132
|
+
const rel = relative(root, source).split('\\').join('/');
|
|
133
|
+
const key = `${expectation.surface}:${rel}`;
|
|
134
|
+
if (seen.has(key))
|
|
135
|
+
continue;
|
|
136
|
+
seen.add(key);
|
|
137
|
+
const destination = join(output, expectation.surface, rel);
|
|
138
|
+
mkdirSync(dirname(destination), { recursive: true });
|
|
139
|
+
copyFileSync(source, destination);
|
|
140
|
+
const body = readFileSync(source);
|
|
141
|
+
snapshots.push({
|
|
142
|
+
surface: expectation.surface,
|
|
143
|
+
path: `${expectation.surface}/${rel}`,
|
|
144
|
+
hash: sha256(body),
|
|
145
|
+
bytes: body.byteLength,
|
|
146
|
+
});
|
|
147
|
+
}
|
|
148
|
+
return snapshots;
|
|
149
|
+
}
|
|
150
|
+
function safeEvidencePath(root, input, resolveExisting = false) {
|
|
151
|
+
if (!input || isAbsolute(input) || input.split(/[\\/]/).includes('..')) {
|
|
152
|
+
throw new Error(`证据路径必须是 Workspace 内相对路径: ${input}`);
|
|
153
|
+
}
|
|
154
|
+
const candidate = resolve(root, input);
|
|
155
|
+
const lexical = relative(root, candidate);
|
|
156
|
+
if (lexical === '..' || lexical.startsWith(`..${process.platform === 'win32' ? '\\' : '/'}`)) {
|
|
157
|
+
throw new Error(`证据路径越界: ${input}`);
|
|
158
|
+
}
|
|
159
|
+
if (resolveExisting && existsSync(candidate)) {
|
|
160
|
+
const actual = realpathSync(candidate);
|
|
161
|
+
const rel = relative(root, actual);
|
|
162
|
+
if (rel === '..' || rel.startsWith(`..${process.platform === 'win32' ? '\\' : '/'}`)) {
|
|
163
|
+
throw new Error(`证据路径通过链接越界: ${input}`);
|
|
164
|
+
}
|
|
165
|
+
}
|
|
166
|
+
return candidate;
|
|
167
|
+
}
|
|
168
|
+
function jsonPointer(value, pointer) {
|
|
169
|
+
if (pointer === '')
|
|
170
|
+
return value;
|
|
171
|
+
if (!pointer.startsWith('/'))
|
|
172
|
+
throw new Error(`JSON pointer 必须以 / 开头: ${pointer}`);
|
|
173
|
+
return pointer.slice(1).split('/').reduce((current, token) => {
|
|
174
|
+
const key = token.replace(/~1/g, '/').replace(/~0/g, '~');
|
|
175
|
+
if (current === null || current === undefined || typeof current !== 'object' || !(key in current)) {
|
|
176
|
+
throw new Error(`JSON pointer 不存在: ${pointer}`);
|
|
177
|
+
}
|
|
178
|
+
return current[key];
|
|
179
|
+
}, value);
|
|
180
|
+
}
|
|
181
|
+
function stable(value) {
|
|
182
|
+
if (Array.isArray(value))
|
|
183
|
+
return `[${value.map(stable).join(',')}]`;
|
|
184
|
+
if (value && typeof value === 'object') {
|
|
185
|
+
return `{${Object.entries(value).sort(([a], [b]) => a.localeCompare(b))
|
|
186
|
+
.map(([key, item]) => `${JSON.stringify(key)}:${stable(item)}`).join(',')}}`;
|
|
187
|
+
}
|
|
188
|
+
return JSON.stringify(value) ?? 'undefined';
|
|
189
|
+
}
|
|
190
|
+
function sha256(value) {
|
|
191
|
+
return createHash('sha256').update(value).digest('hex');
|
|
192
|
+
}
|
|
193
|
+
//# sourceMappingURL=eval-evidence.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"eval-evidence.js","sourceRoot":"","sources":["../../src/eval-evidence.ts"],"names":[],"mappings":"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","sourcesContent":["import {\n copyFileSync, existsSync, lstatSync, mkdirSync, readFileSync, realpathSync,\n} from 'node:fs'\nimport { createHash } from 'node:crypto'\nimport { basename, dirname, isAbsolute, join, relative, resolve } from 'node:path'\nimport { bootstrap } from './bootstrap.js'\n\nexport type EvalEvidenceSurface = 'filesystem' | 'workspace' | 'artifact'\n\ntype PathExpectation = {\n id: string\n surface: EvalEvidenceSurface\n type: 'pathExists'\n path: string\n kind?: 'file' | 'directory'\n minBytes?: number\n}\n\ntype AbsentExpectation = {\n id: string\n surface: EvalEvidenceSurface\n type: 'pathAbsent'\n path: string\n}\n\ntype TextExpectation = {\n id: string\n surface: EvalEvidenceSurface\n type: 'textIncludesAll' | 'textExcludesAll'\n path: string\n values: string[]\n}\n\ntype JsonExpectation = {\n id: string\n surface: EvalEvidenceSurface\n type: 'jsonEquals'\n path: string\n pointer: string\n value: unknown\n}\n\ntype DefinitionExpectation = {\n id: string\n surface: 'workspace'\n type: 'agentDefinition'\n status: 'ready' | 'partial'\n requiredSkills: string[]\n}\n\nexport type EvalEvidenceExpectation = PathExpectation | AbsentExpectation |\n TextExpectation | JsonExpectation | DefinitionExpectation\n\nexport interface EvalEvidenceResult {\n id: string\n surface: EvalEvidenceSurface\n type: EvalEvidenceExpectation['type']\n passed: boolean\n detail: string\n path?: string\n hash?: string\n}\n\n/**\n * Canonicalize an evidence/tool path even when the final file does not exist yet.\n * Resolving the nearest existing ancestor also normalizes macOS /var -> /private/var\n * aliases, which prevents a valid system-temp sandbox path from being misclassified.\n */\nexport function canonicalEvalPath(input: string): string {\n let cursor = resolve(input)\n const missing: string[] = []\n while (!existsSync(cursor)) {\n const parent = dirname(cursor)\n if (parent === cursor) break\n missing.unshift(basename(cursor))\n cursor = parent\n }\n const existing = existsSync(cursor) ? realpathSync(cursor) : cursor\n return resolve(existing, ...missing)\n}\n\nexport function isWorkspacePathInside(workspace: string, input: string): boolean {\n const rel = relative(canonicalEvalPath(workspace), canonicalEvalPath(input))\n return rel === '' ||\n (rel !== '..' && !rel.startsWith(`..${process.platform === 'win32' ? '\\\\' : '/'}`))\n}\n\nexport function relativeWorkspacePath(workspace: string, input: string): string {\n return relative(canonicalEvalPath(workspace), canonicalEvalPath(input))\n .split('\\\\').join('/') || '.'\n}\n\nexport function evaluateWorkspaceEvidence(\n workspace: string,\n expectations: EvalEvidenceExpectation[] = [],\n): EvalEvidenceResult[] {\n const root = realpathSync(resolve(workspace))\n return expectations.map((expectation) => {\n try {\n if (expectation.type === 'agentDefinition') {\n const definition = bootstrap(root).definition\n const skills = definition.skills.map((item) => item.name)\n const missing = expectation.requiredSkills.filter((name) => !skills.includes(name))\n const passed = definition.status === expectation.status && missing.length === 0\n return {\n id: expectation.id,\n surface: expectation.surface,\n type: expectation.type,\n passed,\n detail: `status=${definition.status}; skills=${skills.join(',')}; missing=${missing.join(',') || '-'}`,\n hash: definition.hash,\n }\n }\n\n const path = safeEvidencePath(root, expectation.path)\n const rel = relative(root, path).split('\\\\').join('/')\n if (expectation.type === 'pathAbsent') {\n return {\n id: expectation.id, surface: expectation.surface, type: expectation.type,\n passed: !existsSync(path), path: rel,\n detail: existsSync(path) ? `unexpected path exists: ${rel}` : `absent: ${rel}`,\n }\n }\n if (!existsSync(path)) {\n return {\n id: expectation.id, surface: expectation.surface, type: expectation.type,\n passed: false, path: rel, detail: `missing: ${rel}`,\n }\n }\n\n // Existing symlinks are resolved after the lexical check so they cannot escape the sandbox.\n safeEvidencePath(root, expectation.path, true)\n const stat = lstatSync(path)\n if (stat.isSymbolicLink()) throw new Error(`不接受符号链接证据: ${rel}`)\n if (expectation.type === 'pathExists') {\n const kindMatched = expectation.kind === undefined ||\n (expectation.kind === 'file' ? stat.isFile() : stat.isDirectory())\n const bytes = stat.isFile() ? stat.size : 0\n const sizeMatched = expectation.minBytes === undefined || bytes >= expectation.minBytes\n return {\n id: expectation.id, surface: expectation.surface, type: expectation.type,\n passed: kindMatched && sizeMatched, path: rel,\n detail: `kind=${stat.isFile() ? 'file' : stat.isDirectory() ? 'directory' : 'other'}; bytes=${bytes}`,\n hash: stat.isFile() ? sha256(readFileSync(path)) : undefined,\n }\n }\n if (!stat.isFile()) throw new Error(`文本/JSON 证据必须是文件: ${rel}`)\n const body = readFileSync(path, 'utf8')\n if (expectation.type === 'textIncludesAll' || expectation.type === 'textExcludesAll') {\n const matches = expectation.values.filter((value) => body.includes(value))\n const passed = expectation.type === 'textIncludesAll'\n ? matches.length === expectation.values.length\n : matches.length === 0\n return {\n id: expectation.id, surface: expectation.surface, type: expectation.type,\n passed, path: rel, hash: sha256(body),\n detail: `matched=${JSON.stringify(matches)}; expected=${JSON.stringify(expectation.values)}`,\n }\n }\n if (expectation.type !== 'jsonEquals') throw new Error(`未知证据断言: ${expectation.type}`)\n const parsed = JSON.parse(body) as unknown\n const actual = jsonPointer(parsed, expectation.pointer)\n const passed = stable(actual) === stable(expectation.value)\n return {\n id: expectation.id, surface: expectation.surface, type: expectation.type,\n passed, path: rel, hash: sha256(body),\n detail: `pointer=${expectation.pointer}; actual=${stable(actual)}; expected=${stable(expectation.value)}`,\n }\n } catch (error) {\n return {\n id: expectation.id,\n surface: expectation.surface,\n type: expectation.type,\n passed: false,\n detail: (error as Error).message,\n ...('path' in expectation ? { path: expectation.path } : {}),\n }\n }\n })\n}\n\nexport function snapshotWorkspaceEvidence(\n workspace: string,\n output: string,\n expectations: EvalEvidenceExpectation[] = [],\n): Array<{ surface: EvalEvidenceSurface; path: string; hash: string; bytes: number }> {\n const root = realpathSync(resolve(workspace))\n const snapshots: Array<{\n surface: EvalEvidenceSurface\n path: string\n hash: string\n bytes: number\n }> = []\n const seen = new Set<string>()\n for (const expectation of expectations) {\n if (!('path' in expectation) || expectation.type === 'pathAbsent') continue\n const source = safeEvidencePath(root, expectation.path, true)\n if (!existsSync(source)) continue\n const stat = lstatSync(source)\n if (!stat.isFile() || stat.isSymbolicLink()) continue\n const rel = relative(root, source).split('\\\\').join('/')\n const key = `${expectation.surface}:${rel}`\n if (seen.has(key)) continue\n seen.add(key)\n const destination = join(output, expectation.surface, rel)\n mkdirSync(dirname(destination), { recursive: true })\n copyFileSync(source, destination)\n const body = readFileSync(source)\n snapshots.push({\n surface: expectation.surface,\n path: `${expectation.surface}/${rel}`,\n hash: sha256(body),\n bytes: body.byteLength,\n })\n }\n return snapshots\n}\n\nfunction safeEvidencePath(root: string, input: string, resolveExisting = false): string {\n if (!input || isAbsolute(input) || input.split(/[\\\\/]/).includes('..')) {\n throw new Error(`证据路径必须是 Workspace 内相对路径: ${input}`)\n }\n const candidate = resolve(root, input)\n const lexical = relative(root, candidate)\n if (lexical === '..' || lexical.startsWith(`..${process.platform === 'win32' ? '\\\\' : '/'}`)) {\n throw new Error(`证据路径越界: ${input}`)\n }\n if (resolveExisting && existsSync(candidate)) {\n const actual = realpathSync(candidate)\n const rel = relative(root, actual)\n if (rel === '..' || rel.startsWith(`..${process.platform === 'win32' ? '\\\\' : '/'}`)) {\n throw new Error(`证据路径通过链接越界: ${input}`)\n }\n }\n return candidate\n}\n\nfunction jsonPointer(value: unknown, pointer: string): unknown {\n if (pointer === '') return value\n if (!pointer.startsWith('/')) throw new Error(`JSON pointer 必须以 / 开头: ${pointer}`)\n return pointer.slice(1).split('/').reduce((current: any, token) => {\n const key = token.replace(/~1/g, '/').replace(/~0/g, '~')\n if (current === null || current === undefined || typeof current !== 'object' || !(key in current)) {\n throw new Error(`JSON pointer 不存在: ${pointer}`)\n }\n return current[key]\n }, value as any)\n}\n\nfunction stable(value: unknown): string {\n if (Array.isArray(value)) return `[${value.map(stable).join(',')}]`\n if (value && typeof value === 'object') {\n return `{${Object.entries(value as Record<string, unknown>).sort(([a], [b]) => a.localeCompare(b))\n .map(([key, item]) => `${JSON.stringify(key)}:${stable(item)}`).join(',')}}`\n }\n return JSON.stringify(value) ?? 'undefined'\n}\n\nfunction sha256(value: string | Buffer): string {\n return createHash('sha256').update(value).digest('hex')\n}\n"]}
|
package/dist/src/init.js
CHANGED
package/dist/src/init.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"init.js","sourceRoot":"","sources":["../../src/init.ts"],"names":[],"mappings":"AAAA,2DAA2D;AAC3D,gEAAgE;AAEhE,OAAO,EAAE,MAAM,EAAE,UAAU,EAAE,SAAS,EAAE,MAAM,SAAS,CAAA;AACvD,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAA;AAChC,OAAO,KAAK,GAAG,MAAM,aAAa,CAAA;AAClC,OAAO,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAA;AACtD,OAAO,EACL,eAAe,EAAE,aAAa,GAC/B,MAAM,gBAAgB,CAAA;AAEvB,MAAM,GAAG,GAAG,kBAAkB,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAA;AAE/C,MAAM,UAAU,IAAI,CAAC,IAAY,EAAE,UAAgC,EAAE;IACnE,MAAM,cAAc,GAAG,UAAU,CAAC,aAAa,CAAC,IAAI,CAAC,CAAC,CAAA;IACtD,MAAM,cAAc,GAAG,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,CAAA;IACrC,MAAM,SAAS,GAAG,eAAe,CAAC,IAAI,EAAE,OAAO,CAAC,CAAA;IAEhD,kDAAkD;IAClD,8CAA8C;IAC9C,WAAW,CAAC,IAAI,CAAC,GAAG,EAAE,WAAW,EAAE,WAAW,CAAC,EAAE,IAAI,CAAC,IAAI,EAAE,WAAW,CAAC,CAAC,CAAA;IACzE,WAAW,CAAC,IAAI,CAAC,GAAG,EAAE,WAAW,EAAE,QAAQ,CAAC,EAAE,IAAI,CAAC,IAAI,EAAE,QAAQ,CAAC,CAAC,CAAA;IACnE,KAAK,MAAM,GAAG,IAAI;QAChB,0BAA0B,EAAE,6BAA6B;QACzD,uBAAuB,EAAE,uBAAuB;KACjD;QAAE,SAAS,CAAC,IAAI,CAAC,IAAI,EAAE,GAAG,CAAC,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAA;IAClD,IAAI,CAAC,cAAc;QAAE,GAAG,CAAC,IAAI,CAAC,IAAI,EAAE,GAAG,CAAC,OAAO,CAAC,CAAA;IAEhD,OAAO,CAAC,GAAG,CAAC,GAAG,cAAc,CAAC,CAAC,CAAC,6BAA6B,CAAC,CAAC,CAAC,0BAA0B;;aAE/E,SAAS,CAAC,SAAS;;aAEnB,SAAS,CAAC,MAAM,CAAC,MAAM,MAAM,SAAS,CAAC,MAAM,CAAC,SAAS;aACvD,SAAS,CAAC,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC;;;;
|
|
1
|
+
{"version":3,"file":"init.js","sourceRoot":"","sources":["../../src/init.ts"],"names":[],"mappings":"AAAA,2DAA2D;AAC3D,gEAAgE;AAEhE,OAAO,EAAE,MAAM,EAAE,UAAU,EAAE,SAAS,EAAE,MAAM,SAAS,CAAA;AACvD,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAA;AAChC,OAAO,KAAK,GAAG,MAAM,aAAa,CAAA;AAClC,OAAO,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAA;AACtD,OAAO,EACL,eAAe,EAAE,aAAa,GAC/B,MAAM,gBAAgB,CAAA;AAEvB,MAAM,GAAG,GAAG,kBAAkB,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAA;AAE/C,MAAM,UAAU,IAAI,CAAC,IAAY,EAAE,UAAgC,EAAE;IACnE,MAAM,cAAc,GAAG,UAAU,CAAC,aAAa,CAAC,IAAI,CAAC,CAAC,CAAA;IACtD,MAAM,cAAc,GAAG,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,CAAA;IACrC,MAAM,SAAS,GAAG,eAAe,CAAC,IAAI,EAAE,OAAO,CAAC,CAAA;IAEhD,kDAAkD;IAClD,8CAA8C;IAC9C,WAAW,CAAC,IAAI,CAAC,GAAG,EAAE,WAAW,EAAE,WAAW,CAAC,EAAE,IAAI,CAAC,IAAI,EAAE,WAAW,CAAC,CAAC,CAAA;IACzE,WAAW,CAAC,IAAI,CAAC,GAAG,EAAE,WAAW,EAAE,QAAQ,CAAC,EAAE,IAAI,CAAC,IAAI,EAAE,QAAQ,CAAC,CAAC,CAAA;IACnE,KAAK,MAAM,GAAG,IAAI;QAChB,0BAA0B,EAAE,6BAA6B;QACzD,uBAAuB,EAAE,uBAAuB;KACjD;QAAE,SAAS,CAAC,IAAI,CAAC,IAAI,EAAE,GAAG,CAAC,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAA;IAClD,IAAI,CAAC,cAAc;QAAE,GAAG,CAAC,IAAI,CAAC,IAAI,EAAE,GAAG,CAAC,OAAO,CAAC,CAAA;IAEhD,OAAO,CAAC,GAAG,CAAC,GAAG,cAAc,CAAC,CAAC,CAAC,6BAA6B,CAAC,CAAC,CAAC,0BAA0B;;aAE/E,SAAS,CAAC,SAAS;;aAEnB,SAAS,CAAC,MAAM,CAAC,MAAM,MAAM,SAAS,CAAC,MAAM,CAAC,SAAS;aACvD,SAAS,CAAC,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC;;;;mBAIrB,CAAC,CAAA;IAClB,OAAO,SAAS,CAAA;AAClB,CAAC;AAED,SAAS,WAAW,CAAC,IAAY,EAAE,EAAU;IAC3C,IAAI,CAAC,UAAU,CAAC,IAAI,CAAC;QAAE,OAAM;IAC7B,MAAM,CAAC,IAAI,EAAE,EAAE,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,KAAK,EAAE,KAAK,EAAE,YAAY,EAAE,KAAK,EAAE,CAAC,CAAA;AAC1E,CAAC","sourcesContent":["// init 只为“需要持久 Workspace / Prepared Run runtime”的目录建立最小骨架。\n// 普通 Claude Code/Codex Session 只需全局 Skill + bootstrap,不需要 init。\n\nimport { cpSync, existsSync, mkdirSync } from 'node:fs'\nimport { join } from 'node:path'\nimport * as cfg from './config.js'\nimport { resolvePackageRoot } from './package-root.js'\nimport {\n ensureWorkspace, workspacePath, type WorkspaceInitOptions,\n} from './workspace.js'\n\nconst PKG = resolvePackageRoot(import.meta.url)\n\nexport function init(root: string, options: WorkspaceInitOptions = {}) {\n const wasInitialized = existsSync(workspacePath(root))\n const existingConfig = cfg.load(root)\n const workspace = ensureWorkspace(root, options)\n\n // Runtime 的机器策略仍需本地存在;只补缺失项,不复制全局 Skill、Ontology,\n // 也不修改项目的 AGENTS.md / CLAUDE.md / .gitignore。\n copyMissing(join(PKG, 'templates', 'behaviors'), join(root, 'behaviors'))\n copyMissing(join(PKG, 'templates', 'fields'), join(root, 'fields'))\n for (const dir of [\n '.dingtalk-agent/sessions', '.dingtalk-agent/event-index',\n '.dingtalk-agent/waits', '.dingtalk-agent/cache',\n ]) mkdirSync(join(root, dir), { recursive: true })\n if (!existingConfig) cfg.save(root, cfg.DEFAULT)\n\n console.log(`${wasInitialized ? '✅ Workspace 已存在;检查完成,未重新初始化' : '✅ 已初始化最小 Agent Workspace'}\n\n Context: ${workspace.contextId}(未显式指定时由目录名稳定派生)\n 配置: .dingtalk-agent/workspace.json\n Storage: ${workspace.mounts.memory} / ${workspace.mounts.knowledge}\n Skill: ${workspace.skills.join(', ')}(按名称解析;不复制进当前项目)\n\n 会话水合: dingtalk-agent bootstrap\n 事件运行时: dingtalk-agent prepare --event-file <event.json>\n 环境检查: dta doctor`)\n return workspace\n}\n\nfunction copyMissing(from: string, to: string): void {\n if (!existsSync(from)) return\n cpSync(from, to, { recursive: true, force: false, errorOnExist: false })\n}\n"]}
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
export function directInvocation(sessionKey = '') {
|
|
2
|
+
return {
|
|
3
|
+
$schema: 'dingtalk-agent/invocation@1',
|
|
4
|
+
mode: 'direct',
|
|
5
|
+
authority: 'default',
|
|
6
|
+
eventId: '',
|
|
7
|
+
sessionKey,
|
|
8
|
+
occurredAt: null,
|
|
9
|
+
actor: null,
|
|
10
|
+
target: null,
|
|
11
|
+
conversation: null,
|
|
12
|
+
};
|
|
13
|
+
}
|
|
14
|
+
export function eventInvocation(event, resume = { mode: 'start' }, sessionKey = '', continued = false) {
|
|
15
|
+
return {
|
|
16
|
+
$schema: 'dingtalk-agent/invocation@1',
|
|
17
|
+
mode: resume.mode === 'start' && !continued ? eventMode(event.kind) : 'continuation',
|
|
18
|
+
authority: 'event',
|
|
19
|
+
eventId: event.id,
|
|
20
|
+
sessionKey,
|
|
21
|
+
occurredAt: event.occurredAt,
|
|
22
|
+
actor: event.actor,
|
|
23
|
+
target: event.replyTarget,
|
|
24
|
+
conversation: event.conversation,
|
|
25
|
+
};
|
|
26
|
+
}
|
|
27
|
+
function eventMode(kind) {
|
|
28
|
+
if (kind === 'im.message.mentioned')
|
|
29
|
+
return 'mention';
|
|
30
|
+
if (kind === 'im.message.dm')
|
|
31
|
+
return 'dm';
|
|
32
|
+
if (kind === 'agent.heartbeat')
|
|
33
|
+
return 'heartbeat';
|
|
34
|
+
return 'ambient';
|
|
35
|
+
}
|
|
36
|
+
//# sourceMappingURL=invocation.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"invocation.js","sourceRoot":"","sources":["../../src/invocation.ts"],"names":[],"mappings":"AAIA,MAAM,UAAU,gBAAgB,CAAC,UAAU,GAAG,EAAE;IAC9C,OAAO;QACL,OAAO,EAAE,6BAA6B;QACtC,IAAI,EAAE,QAAQ;QACd,SAAS,EAAE,SAAS;QACpB,OAAO,EAAE,EAAE;QACX,UAAU;QACV,UAAU,EAAE,IAAI;QAChB,KAAK,EAAE,IAAI;QACX,MAAM,EAAE,IAAI;QACZ,YAAY,EAAE,IAAI;KACnB,CAAA;AACH,CAAC;AAED,MAAM,UAAU,eAAe,CAC7B,KAAsB,EACtB,SAAwB,EAAE,IAAI,EAAE,OAAO,EAAE,EACzC,UAAU,GAAG,EAAE,EACf,SAAS,GAAG,KAAK;IAEjB,OAAO;QACL,OAAO,EAAE,6BAA6B;QACtC,IAAI,EAAE,MAAM,CAAC,IAAI,KAAK,OAAO,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC,SAAS,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,cAAc;QACpF,SAAS,EAAE,OAAO;QAClB,OAAO,EAAE,KAAK,CAAC,EAAE;QACjB,UAAU;QACV,UAAU,EAAE,KAAK,CAAC,UAAU;QAC5B,KAAK,EAAE,KAAK,CAAC,KAAK;QAClB,MAAM,EAAE,KAAK,CAAC,WAAW;QACzB,YAAY,EAAE,KAAK,CAAC,YAAY;KACjC,CAAA;AACH,CAAC;AAED,SAAS,SAAS,CAAC,IAAY;IAC7B,IAAI,IAAI,KAAK,sBAAsB;QAAE,OAAO,SAAS,CAAA;IACrD,IAAI,IAAI,KAAK,eAAe;QAAE,OAAO,IAAI,CAAA;IACzC,IAAI,IAAI,KAAK,iBAAiB;QAAE,OAAO,WAAW,CAAA;IAClD,OAAO,SAAS,CAAA;AAClB,CAAC","sourcesContent":["import type {\n InvocationContext, InvocationMode, NormalizedEvent, ResumeContext,\n} from './types.js'\n\nexport function directInvocation(sessionKey = ''): InvocationContext {\n return {\n $schema: 'dingtalk-agent/invocation@1',\n mode: 'direct',\n authority: 'default',\n eventId: '',\n sessionKey,\n occurredAt: null,\n actor: null,\n target: null,\n conversation: null,\n }\n}\n\nexport function eventInvocation(\n event: NormalizedEvent,\n resume: ResumeContext = { mode: 'start' },\n sessionKey = '',\n continued = false,\n): InvocationContext {\n return {\n $schema: 'dingtalk-agent/invocation@1',\n mode: resume.mode === 'start' && !continued ? eventMode(event.kind) : 'continuation',\n authority: 'event',\n eventId: event.id,\n sessionKey,\n occurredAt: event.occurredAt,\n actor: event.actor,\n target: event.replyTarget,\n conversation: event.conversation,\n }\n}\n\nfunction eventMode(kind: string): InvocationMode {\n if (kind === 'im.message.mentioned') return 'mention'\n if (kind === 'im.message.dm') return 'dm'\n if (kind === 'agent.heartbeat') return 'heartbeat'\n return 'ambient'\n}\n"]}
|