@sema-agent/core 7.51.2 → 7.52.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/CHANGELOG.md +504 -2
- package/dist/agents/agent-transcript-tool.d.ts +1 -1
- package/dist/agents/cascade.js +4 -0
- package/dist/agents/cumulative-stats.d.ts +3 -0
- package/dist/agents/cumulative-stats.js +3 -0
- package/dist/agents/list-agents-tool.d.ts +1 -1
- package/dist/agents/read-inbox-tool.d.ts +1 -1
- package/dist/agents/repair-loop.js +4 -0
- package/dist/agents/send-message-tool.d.ts +11 -16
- package/dist/agents/send-message-tool.js +11 -13
- package/dist/agents/subagent.js +6 -4
- package/dist/agents/tool-filter.d.ts +40 -13
- package/dist/agents/tool-filter.js +28 -14
- package/dist/bench/metrics.d.ts +1 -0
- package/dist/brain/anthropic.js +16 -12
- package/dist/brain/model-presets.d.ts +4 -5
- package/dist/brain/model-presets.js +4 -4
- package/dist/brain/open-responses.js +16 -12
- package/dist/brain/openai.js +16 -12
- package/dist/brain/request-params.d.ts +12 -33
- package/dist/brain/request-params.js +5 -2
- package/dist/brain/request-route.d.ts +9 -8
- package/dist/brain/request-route.js +1 -0
- package/dist/brain/route-adjudicator.d.ts +117 -47
- package/dist/brain/route-adjudicator.js +171 -42
- package/dist/brain/route-conformance.js +2 -2
- package/dist/brain/status-sink.d.ts +18 -0
- package/dist/brain/status-sink.js +7 -0
- package/dist/core/allow-entry.d.ts +40 -8
- package/dist/core/allow-entry.js +23 -16
- package/dist/core/auto-compaction.d.ts +23 -20
- package/dist/core/auto-compaction.js +37 -16
- package/dist/core/auto-promote.d.ts +2 -1
- package/dist/core/auto-promote.js +2 -2
- package/dist/core/caller-tool-name.d.ts +9 -0
- package/dist/core/caller-tool-name.js +13 -0
- package/dist/core/checkpoint-requirements.d.ts +7 -1
- package/dist/core/checkpoint-requirements.js +2 -0
- package/dist/core/checkpoint-store.d.ts +36 -12
- package/dist/core/checkpoint-store.js +1 -1
- package/dist/core/child-clamp-seats.d.ts +6 -0
- package/dist/core/child-clamp-seats.js +2 -1
- package/dist/core/credential-vocabulary.d.ts +33 -8
- package/dist/core/credential-vocabulary.js +32 -7
- package/dist/core/decision-receipt.d.ts +2 -2
- package/dist/core/delegation-frames.d.ts +9 -2
- package/dist/core/delegation-name.d.ts +18 -0
- package/dist/core/delegation-name.js +47 -0
- package/dist/core/engine-capabilities.d.ts +8 -1
- package/dist/core/engine-capabilities.js +1 -1
- package/dist/core/engine-notice.d.ts +36 -19
- package/dist/core/frontmatter-fence.d.ts +10 -0
- package/dist/core/frontmatter-fence.js +6 -0
- package/dist/core/gate-fold.js +5 -23
- package/dist/core/gate-lanes.js +356 -270
- package/dist/core/governance-codes.d.ts +9 -4
- package/dist/core/governance-codes.js +9 -3
- package/dist/core/hooks.d.ts +276 -734
- package/dist/core/hooks.js +97 -192
- package/dist/{tools/fs → core}/image-admission.d.ts +21 -3
- package/dist/{tools/fs → core}/image-admission.js +24 -6
- package/dist/core/mcp-connection-pool.d.ts +4 -1
- package/dist/core/mcp-connection-pool.js +7 -2
- package/dist/core/mcp-probe.d.ts +12 -9
- package/dist/core/mcp-probe.js +2 -2
- package/dist/core/mcp-server-spec.d.ts +16 -0
- package/dist/core/mcp.d.ts +11 -7
- package/dist/core/mcp.js +11 -5
- package/dist/core/memory-engine/data-plane.js +5 -1
- package/dist/core/memory-engine/distiller.js +16 -2
- package/dist/core/memory-engine/engine.d.ts +8 -11
- package/dist/core/memory-engine/engine.js +9 -5
- package/dist/core/memory-engine/frontmatter.d.ts +6 -0
- package/dist/core/memory-engine/frontmatter.js +19 -16
- package/dist/core/memory.d.ts +2 -2
- package/dist/core/mode-policy.d.ts +4 -0
- package/dist/core/mode-policy.js +7 -5
- package/dist/core/model-seat.d.ts +4 -1
- package/dist/core/mods/dollar.d.ts +109 -0
- package/dist/core/mods/dollar.js +154 -0
- package/dist/core/mods/host.d.ts +23 -0
- package/dist/core/mods/host.js +21 -0
- package/dist/core/mods/kernel/budget.d.ts +43 -0
- package/dist/core/mods/kernel/budget.js +83 -0
- package/dist/core/mods/kernel/dispatch.d.ts +100 -0
- package/dist/core/mods/kernel/dispatch.js +701 -0
- package/dist/core/mods/kernel/events.d.ts +242 -0
- package/dist/core/mods/kernel/events.js +210 -0
- package/dist/core/mods/kernel/index.d.ts +6 -0
- package/dist/core/mods/kernel/index.js +5 -0
- package/dist/core/mods/kernel/receive.d.ts +65 -0
- package/dist/core/mods/kernel/receive.js +123 -0
- package/dist/core/mods/kernel/registration.d.ts +131 -0
- package/dist/core/mods/kernel/registration.js +102 -0
- package/dist/core/mods/kernel/site-rules.d.ts +84 -0
- package/dist/core/mods/kernel/site-rules.js +104 -0
- package/dist/core/mods/stations.d.ts +350 -0
- package/dist/core/mods/stations.js +444 -0
- package/dist/core/own-property-receipt.js +11 -23
- package/dist/core/parent-spec-seat.d.ts +18 -7
- package/dist/core/parent-spec-seat.js +6 -2
- package/dist/core/path-identity.js +2 -1
- package/dist/core/permission-rule-syntax.d.ts +15 -0
- package/dist/core/permission-rule-syntax.js +24 -16
- package/dist/core/permission-rules.d.ts +7 -1
- package/dist/core/permission-rules.js +26 -15
- package/dist/core/prompt-section-seat.d.ts +15 -27
- package/dist/core/prompt-section-seat.js +73 -40
- package/dist/core/protocol-http-auth.d.ts +3 -1
- package/dist/core/protocol-http-auth.js +2 -0
- package/dist/core/reminder-mint.d.ts +2 -2
- package/dist/core/remote-env.d.ts +24 -12
- package/dist/core/remote-env.js +1 -0
- package/dist/core/resume-startup-cause.d.ts +16 -1
- package/dist/core/resume-startup-cause.js +4 -1
- package/dist/core/retired-keys.d.ts +4 -0
- package/dist/core/retired-keys.js +3 -0
- package/dist/core/runner/announce-once-ledger.d.ts +31 -1
- package/dist/core/runner/announce-once-ledger.js +22 -0
- package/dist/core/runner/assemble-result.d.ts +9 -0
- package/dist/core/runner/assemble-result.js +3 -1
- package/dist/core/runner/call-hook-stations.d.ts +23 -27
- package/dist/core/runner/call-hook-stations.js +58 -42
- package/dist/core/runner/caller-stop-gate.d.ts +25 -0
- package/dist/core/runner/caller-stop-gate.js +7 -0
- package/dist/core/runner/compaction-seams.d.ts +8 -22
- package/dist/core/runner/compaction-seams.js +28 -53
- package/dist/core/runner/construction-doors.js +11 -1
- package/dist/core/runner/contracts.d.ts +85 -83
- package/dist/core/runner/credential-origin-seat.d.ts +2 -0
- package/dist/core/runner/credential-origin-seat.js +19 -0
- package/dist/core/runner/extra-body-dropped-seat.d.ts +2 -6
- package/dist/core/runner/gate-exit.d.ts +47 -36
- package/dist/core/runner/gate-exit.js +8 -2
- package/dist/core/runner/image.js +1 -2
- package/dist/core/runner/inline-image.js +1 -1
- package/dist/core/runner/notice-seat-input.d.ts +11 -0
- package/dist/core/runner/notice-seat-input.js +1 -0
- package/dist/core/runner/person-path-rows.js +1 -0
- package/dist/core/runner/prepare-acquire-reconcile.js +5 -1
- package/dist/core/runner/prepare-ask-lane.d.ts +5 -7
- package/dist/core/runner/prepare-ask-lane.js +6 -15
- package/dist/core/runner/prepare-caps-and-workflow.d.ts +4 -2
- package/dist/core/runner/prepare-caps-and-workflow.js +25 -8
- package/dist/core/runner/prepare-config-doors.d.ts +5 -0
- package/dist/core/runner/prepare-config-doors.js +9 -0
- package/dist/core/runner/prepare-defer-classify.js +3 -4
- package/dist/core/runner/prepare-gate-stations.d.ts +8 -11
- package/dist/core/runner/prepare-gate-stations.js +11 -10
- package/dist/core/runner/prepare-inherited-gate.d.ts +8 -12
- package/dist/core/runner/prepare-inherited-gate.js +8 -21
- package/dist/core/runner/prepare-memory-engine-session.js +1 -1
- package/dist/core/runner/prepare-park-ask.js +10 -14
- package/dist/core/runner/prepare-policy-chain.d.ts +17 -15
- package/dist/core/runner/prepare-policy-chain.js +95 -100
- package/dist/core/runner/prepare-project-context.js +7 -10
- package/dist/core/runner/prepare-prompt-assembly.d.ts +45 -40
- package/dist/core/runner/prepare-prompt-assembly.js +134 -101
- package/dist/core/runner/prepare-prompt-inputs.d.ts +18 -19
- package/dist/core/runner/prepare-prompt-inputs.js +5 -7
- package/dist/core/runner/prepare-protocol-tools.d.ts +6 -4
- package/dist/core/runner/prepare-protocol-tools.js +2 -2
- package/dist/core/runner/prepare-safety-scan.js +6 -10
- package/dist/core/runner/prepare-suspend-saga.d.ts +6 -0
- package/dist/core/runner/prepare-suspend-saga.js +7 -5
- package/dist/core/runner/prepare-task.js +33 -15
- package/dist/core/runner/prepare-turn-wiring.d.ts +13 -15
- package/dist/core/runner/prepare-turn-wiring.js +29 -27
- package/dist/core/runner/prepare-wiring-manifest.d.ts +5 -6
- package/dist/core/runner/prepare-wiring-manifest.js +7 -7
- package/dist/core/runner/resume-apply.d.ts +5 -2
- package/dist/core/runner/resume-apply.js +24 -42
- package/dist/core/runner/resume-checkpoint-screen.d.ts +1 -0
- package/dist/core/runner/resume-checkpoint-screen.js +9 -1
- package/dist/core/runner/resume-preflight.js +38 -16
- package/dist/core/runner/retired-runner-deps.js +3 -1
- package/dist/core/runner/run-brain-sinks.d.ts +3 -2
- package/dist/core/runner/run-brain-sinks.js +5 -1
- package/dist/core/runner/run-compaction-machinery.d.ts +7 -1
- package/dist/core/runner/run-compaction-machinery.js +7 -33
- package/dist/core/runner/run-harness-handlers.js +4 -2
- package/dist/core/runner/run-identity-wiring.d.ts +3 -1
- package/dist/core/runner/run-identity-wiring.js +3 -2
- package/dist/core/runner/run-leg.js +62 -84
- package/dist/core/runner/run-notification-lane.js +1 -0
- package/dist/core/runner/run-recovery-lanes.d.ts +3 -0
- package/dist/core/runner/run-recovery-lanes.js +11 -10
- package/dist/core/runner/run-settle-and-teardown.js +9 -28
- package/dist/core/runner/run-stop-and-final-verify.js +18 -25
- package/dist/core/runner/run-terminal-adoption.d.ts +3 -0
- package/dist/core/runner/run-terminal-adoption.js +33 -22
- package/dist/core/runner/run-tool-mount-facts.js +5 -3
- package/dist/core/runner/run-turn-boundary.js +23 -34
- package/dist/core/runner/runtask.d.ts +6 -7
- package/dist/core/runner/runtask.js +14 -72
- package/dist/core/runner/session-rule-policy.d.ts +5 -5
- package/dist/core/runner/session-rule-policy.js +13 -8
- package/dist/core/runner/side-call-account.d.ts +68 -0
- package/dist/core/runner/side-call-account.js +61 -0
- package/dist/core/runner/stream-halt-verbs.js +12 -17
- package/dist/core/runner/stream-lifecycle-verbs.js +8 -5
- package/dist/core/runner/stream-steer-verb.d.ts +1 -1
- package/dist/core/runner/stream-steer-verb.js +20 -38
- package/dist/core/runner/sub-agent-deny-lists.d.ts +121 -22
- package/dist/core/runner/sub-agent-deny-lists.js +228 -71
- package/dist/core/runner/tool-end-body.d.ts +5 -6
- package/dist/core/runner/tool-end-body.js +6 -4
- package/dist/core/runner/tool-not-executed.d.ts +15 -0
- package/dist/core/runner/tool-not-executed.js +30 -0
- package/dist/core/runner/tool-occurrence.d.ts +8 -7
- package/dist/core/runner/tool-occurrence.js +5 -5
- package/dist/core/runner/tool-result-media-seat.d.ts +1 -1
- package/dist/core/runner-deps.d.ts +20 -28
- package/dist/core/safety-merge-corpus.js +18 -2
- package/dist/core/secret-env.d.ts +88 -20
- package/dist/core/secret-env.js +192 -38
- package/dist/core/session-policy-store.d.ts +52 -16
- package/dist/core/session-policy-store.js +118 -28
- package/dist/core/session-reconcile.d.ts +4 -0
- package/dist/core/session-reconcile.js +2 -1
- package/dist/core/shell-read-silence.js +3 -32
- package/dist/core/side-query.d.ts +5 -3
- package/dist/core/skill-grant.d.ts +3 -2
- package/dist/core/skill-grant.js +17 -9
- package/dist/core/skills-directory.d.ts +31 -11
- package/dist/core/skills-directory.js +655 -104
- package/dist/core/task-event.d.ts +13 -3
- package/dist/core/task-result.d.ts +8 -0
- package/dist/core/task-spec.d.ts +20 -19
- package/dist/core/task-stream.d.ts +14 -4
- package/dist/core/tighten-task-spec.d.ts +4 -3
- package/dist/core/tighten-task-spec.js +2 -4
- package/dist/core/tool-check-reading.d.ts +74 -0
- package/dist/core/tool-check-reading.js +80 -0
- package/dist/core/tool-policy.d.ts +59 -18
- package/dist/core/tool-policy.js +77 -12
- package/dist/core/tool-registry.d.ts +20 -0
- package/dist/core/tool-registry.js +4 -0
- package/dist/core/tool-spec.d.ts +10 -6
- package/dist/core/tools.js +2 -0
- package/dist/core/trace.d.ts +51 -32
- package/dist/core/unc-spelling.d.ts +10 -0
- package/dist/core/unc-spelling.js +3 -0
- package/dist/core/untrusted-egress.d.ts +8 -0
- package/dist/core/untrusted-egress.js +4 -1
- package/dist/core/user-attachment.d.ts +12 -2
- package/dist/core/user-attachment.js +17 -2
- package/dist/core/wiring-manifest.d.ts +14 -13
- package/dist/core/wiring-manifest.js +2 -2
- package/dist/engine/compaction/utils.js +1 -2
- package/dist/engine/execution-env/node-execution-env.d.ts +4 -3
- package/dist/engine/execution-env/symlink-chain.js +1 -1
- package/dist/engine/harness/agent-harness.d.ts +1 -1
- package/dist/engine/harness/agent-harness.js +3 -3
- package/dist/engine/harness/types.d.ts +17 -16
- package/dist/engine/harness/types.js +7 -1
- package/dist/engine/llm/types.d.ts +12 -7
- package/dist/engine/loop/agent-loop.js +1 -1
- package/dist/engine/loop/types.d.ts +1 -1
- package/dist/engine/lsp/node-lsp-manager.d.ts +2 -2
- package/dist/engine/session/import-validate.js +3 -10
- package/dist/engine/session/session.d.ts +4 -4
- package/dist/engine/session/session.js +4 -4
- package/dist/index.d.ts +20 -16
- package/dist/index.js +13 -11
- package/dist/internal/harness.d.ts +1 -1
- package/dist/internal/harness.js +1 -1
- package/dist/orchestration/run-spec.d.ts +4 -6
- package/dist/orchestration/run-spec.js +39 -63
- package/dist/orchestration/run-workflow-tool.js +1 -2
- package/dist/orchestration/workflow.d.ts +11 -3
- package/dist/orchestration/workflow.js +11 -2
- package/dist/prompt-assembly/artifact-store.d.ts +37 -56
- package/dist/prompt-assembly/artifact-store.js +31 -49
- package/dist/prompt-assembly/artifact.d.ts +89 -76
- package/dist/prompt-assembly/artifact.js +167 -146
- package/dist/prompt-assembly/assemble.d.ts +34 -29
- package/dist/prompt-assembly/assemble.js +33 -220
- package/dist/prompt-assembly/bands.d.ts +20 -0
- package/dist/prompt-assembly/bands.js +18 -0
- package/dist/prompt-assembly/catalog/constitution.d.ts +23 -0
- package/dist/prompt-assembly/catalog/constitution.js +69 -0
- package/dist/prompt-assembly/catalog/core-behavior.d.ts +9 -0
- package/dist/prompt-assembly/catalog/core-behavior.js +85 -0
- package/dist/prompt-assembly/catalog/index.d.ts +11 -0
- package/dist/prompt-assembly/catalog/index.js +59 -0
- package/dist/prompt-assembly/catalog/modes.d.ts +15 -0
- package/dist/prompt-assembly/catalog/modes.js +137 -0
- package/dist/prompt-assembly/catalog/role.d.ts +10 -0
- package/dist/prompt-assembly/catalog/role.js +157 -0
- package/dist/prompt-assembly/catalog/schema.d.ts +124 -0
- package/dist/prompt-assembly/catalog/schema.js +25 -0
- package/dist/prompt-assembly/catalog/sections.d.ts +9 -0
- package/dist/prompt-assembly/catalog/sections.js +98 -0
- package/dist/prompt-assembly/catalog/team.d.ts +4 -0
- package/dist/prompt-assembly/catalog/team.js +258 -0
- package/dist/prompt-assembly/composer.d.ts +24 -28
- package/dist/prompt-assembly/composer.js +124 -46
- package/dist/prompt-assembly/epoch.d.ts +89 -79
- package/dist/prompt-assembly/epoch.js +115 -142
- package/dist/prompt-assembly/explain.d.ts +58 -34
- package/dist/prompt-assembly/explain.js +21 -24
- package/dist/prompt-assembly/overlay.d.ts +127 -0
- package/dist/prompt-assembly/overlay.js +301 -0
- package/dist/prompt-assembly/renderers.d.ts +21 -0
- package/dist/prompt-assembly/renderers.js +39 -0
- package/dist/prompt-assembly/section-usage.d.ts +3 -3
- package/dist/prompt-assembly/section-usage.js +1 -1
- package/dist/prompt-assembly/select.d.ts +56 -0
- package/dist/prompt-assembly/select.js +69 -0
- package/dist/prompt-assembly/sugar.d.ts +31 -0
- package/dist/prompt-assembly/sugar.js +20 -0
- package/dist/prompt-assembly/turn-snapshot.d.ts +3 -2
- package/dist/prompt-assembly/types.d.ts +45 -148
- package/dist/prompts/coordinator.d.ts +2 -21
- package/dist/prompts/coordinator.js +3 -255
- package/dist/prompts/cowork.d.ts +27 -16
- package/dist/prompts/cowork.js +2 -23
- package/dist/prompts/default.d.ts +38 -500
- package/dist/prompts/default.js +20 -285
- package/dist/prompts/supervisor.d.ts +6 -71
- package/dist/prompts/supervisor.js +6 -117
- package/dist/tools/fs/bash-readonly-classifier.d.ts +6 -5
- package/dist/tools/fs/dir-entries.d.ts +4 -2
- package/dist/tools/fs/dir-entries.js +16 -4
- package/dist/tools/fs/fs-bash.d.ts +1 -1
- package/dist/tools/fs/fs-bash.js +22 -11
- package/dist/tools/fs/fs-pdf.js +17 -13
- package/dist/tools/fs/fs-read.js +4 -3
- package/dist/tools/fs/fs-shared.d.ts +1 -10
- package/dist/tools/fs/fs-shared.js +3 -4
- package/dist/tools/fs/fs-write.js +2 -1
- package/dist/tools/fs/notebook.js +1 -1
- package/dist/tools/fs/pdf.d.ts +20 -10
- package/dist/tools/fs/pdf.js +19 -10
- package/dist/tools/fs/program-read-model.d.ts +68 -8
- package/dist/tools/fs/program-read-model.js +112 -33
- package/dist/tools/fs/program-read-model.rows.js +30 -10
- package/dist/tools/fs/read-deny-home.d.ts +25 -9
- package/dist/tools/fs/read-deny-home.js +28 -27
- package/dist/tools/fs/read-deny.d.ts +41 -11
- package/dist/tools/fs/read-deny.js +51 -5
- package/dist/tools/fs/safety.d.ts +4 -26
- package/dist/tools/fs/safety.js +10 -32
- package/dist/tools/fs/search.js +15 -10
- package/dist/tools/fs/shell-read-argv.d.ts +3 -2
- package/dist/tools/fs/shell-read-argv.js +118 -38
- package/dist/tools/fs/shell-read-establish.d.ts +5 -5
- package/dist/tools/fs/shell-read-establish.js +11 -61
- package/dist/tools/fs/shell-read-identity.js +6 -3
- package/dist/tools/fs/shell-read-judge.d.ts +13 -15
- package/dist/tools/fs/shell-read-judge.js +18 -4
- package/dist/tools/fs/shell-read-plan.d.ts +2 -2
- package/dist/tools/web.js +1 -1
- package/package.json +13 -1
- package/test/export-surface.snapshot.json +242 -99
- package/wire-changes/core@7.52.0.json +5859 -0
- package/dist/core/hook-seats.d.ts +0 -66
- package/dist/core/hook-seats.js +0 -37
- package/dist/prompt-assembly/packs/sema-default.d.ts +0 -2
- package/dist/prompt-assembly/packs/sema-default.js +0 -147
- package/dist/prompts/simple-sections.d.ts +0 -58
- package/dist/prompts/simple-sections.js +0 -43
|
@@ -2,12 +2,84 @@ import { literalTildeSpelling } from "../../shell/lex.js";
|
|
|
2
2
|
import { expandsOf, partPattern, readOfText, rewritten } from "./shell-read-word.js";
|
|
3
3
|
import { arithmeticSubstitutions } from "./shell-read-bindings.js";
|
|
4
4
|
import { argvProgramOf, attachedOptionPayloads, isPathShapedToken } from "./bash-readonly-classifier.js";
|
|
5
|
-
import { assignmentArgumentsAreNotPaths, evaluatesOperands, messageWords, moduleTailOf, objectPathsOf, opensNoOperand, programRow, programTextMayOpen, programTextOpensOf, readArgs, selectsContentsTraversal, slotValueCandidates, subcommandOf, valuesAreLiteral, walksCwdWithoutOperand, wordsReadBySomeImplementations, } from "./program-read-model.js";
|
|
5
|
+
import { assignmentArgumentsAreNotPaths, deliversOperands, evaluatesOperands, messageWords, moduleTailOf, objectPathsOf, opensNoOperand, programRow, programTextMayOpen, programTextOpensOf, readArgs, readOptionSlot, selectsContentsTraversal, slotValueCandidates, subcommandOf, valuesAreLiteral, walksCwdWithoutOperand, wordsReadBySomeImplementations, } from "./program-read-model.js";
|
|
6
6
|
export function pathSubcommandOf(row, args) {
|
|
7
7
|
const sub = subcommandOf(row, args);
|
|
8
8
|
return sub !== undefined && (sub.row.operands !== undefined || sub.row.traversal !== undefined) ? sub : undefined;
|
|
9
9
|
}
|
|
10
|
+
function slotOperandAt(row, words) {
|
|
11
|
+
for (const e of readArgs(row, words, { firstOperandSlot: true }))
|
|
12
|
+
if (e.kind === "operand" && e.slot !== undefined)
|
|
13
|
+
return e.at;
|
|
14
|
+
return undefined;
|
|
15
|
+
}
|
|
16
|
+
function mayOwnNextWord(row, tok) {
|
|
17
|
+
if (tok.startsWith("--"))
|
|
18
|
+
return !tok.includes("=");
|
|
19
|
+
for (let k = 2; k <= tok.length; k++)
|
|
20
|
+
if (readOptionSlot(row, tok.slice(0, k)).form === "unexplained")
|
|
21
|
+
return k === tok.length;
|
|
22
|
+
return false;
|
|
23
|
+
}
|
|
24
|
+
const rootValue = (spec) => spec?.walks === true || spec?.delivers === "operands";
|
|
25
|
+
class RootsGathered {
|
|
26
|
+
positional = [];
|
|
27
|
+
places = [];
|
|
28
|
+
maybeValues = new Set();
|
|
29
|
+
stdinOperands = 0;
|
|
30
|
+
slotOwned = false;
|
|
31
|
+
unsettled = false;
|
|
32
|
+
slotWord;
|
|
33
|
+
value(r, e, namesPath) {
|
|
34
|
+
if (!e.consumed) {
|
|
35
|
+
this.maybeValues.add(r);
|
|
36
|
+
if (e.unsettled === true)
|
|
37
|
+
this.unsettled = true;
|
|
38
|
+
}
|
|
39
|
+
else if (namesPath && rootValue(e.spec))
|
|
40
|
+
this.positional.push(r);
|
|
41
|
+
}
|
|
42
|
+
attached(named, spec) {
|
|
43
|
+
if (rootValue(spec))
|
|
44
|
+
for (const c of named)
|
|
45
|
+
if (c.denyOnly !== true)
|
|
46
|
+
this.places.push({ ...c, provenance: "traversal_root" });
|
|
47
|
+
}
|
|
48
|
+
slot(r) {
|
|
49
|
+
this.slotWord = r;
|
|
50
|
+
if (this.maybeValues.has(r))
|
|
51
|
+
this.slotOwned = true;
|
|
52
|
+
}
|
|
53
|
+
operand(r, namesPath, stdin) {
|
|
54
|
+
if (stdin) {
|
|
55
|
+
if (!this.maybeValues.has(r))
|
|
56
|
+
this.stdinOperands++;
|
|
57
|
+
}
|
|
58
|
+
else if (namesPath)
|
|
59
|
+
this.positional.push(r);
|
|
60
|
+
}
|
|
61
|
+
restart() {
|
|
62
|
+
this.positional.length = 0;
|
|
63
|
+
this.places.length = 0;
|
|
64
|
+
this.stdinOperands = 0;
|
|
65
|
+
this.slotOwned = false;
|
|
66
|
+
this.unsettled = false;
|
|
67
|
+
this.slotWord = undefined;
|
|
68
|
+
}
|
|
69
|
+
roots(row) {
|
|
70
|
+
const leftOver = this.positional.filter((r) => !this.maybeValues.has(r)).length + this.places.length + this.stdinOperands;
|
|
71
|
+
const reads = this.unsettled
|
|
72
|
+
? [...this.positional, ...(this.slotWord !== undefined ? [this.slotWord] : []), ...(walksCwdWithoutOperand(row) ? [readOfText(".")] : [])]
|
|
73
|
+
: walksCwdWithoutOperand(row) && leftOver <= (this.slotOwned ? 1 : 0) ? [...this.positional, readOfText(".")] : [...this.positional];
|
|
74
|
+
return [...reads.map((r) => bare(r, "traversal_root")), ...this.places];
|
|
75
|
+
}
|
|
76
|
+
}
|
|
10
77
|
export const programTextSentence = (language) => `runs inline ${language} program text, which may open files this station does not read`;
|
|
78
|
+
const deliveredOperandsSentence = "takes the files it works on from a list file, whose names this station does not read";
|
|
79
|
+
function noteDeliveredOperands(row, words, ctx) {
|
|
80
|
+
if (deliversOperands(row, words))
|
|
81
|
+
ctx.programText ??= deliveredOperandsSentence;
|
|
82
|
+
}
|
|
11
83
|
export function bare(r, provenance, spelled = r.folded) {
|
|
12
84
|
const whole = spelled === r.folded;
|
|
13
85
|
const pattern = whole ? r.pattern : partPattern(r, spelled);
|
|
@@ -105,9 +177,9 @@ export function unlistedWords(reads, toks, from, launcherIndices, provenance, ct
|
|
|
105
177
|
else if (j > argvStart && !declaredNotPaths)
|
|
106
178
|
pushAssignment(reads, toks[j].word, provenance);
|
|
107
179
|
}
|
|
108
|
-
const
|
|
180
|
+
const gathered = new RootsGathered();
|
|
181
|
+
let slotWord;
|
|
109
182
|
const pastOperand = new Set();
|
|
110
|
-
let stdinOperand = false;
|
|
111
183
|
let globs = "expanded";
|
|
112
184
|
let walkRow = slotRow;
|
|
113
185
|
let walkFrom = argvStart + 1;
|
|
@@ -159,8 +231,11 @@ export function unlistedWords(reads, toks, from, launcherIndices, provenance, ct
|
|
|
159
231
|
const at = (k) => first + k;
|
|
160
232
|
const words = toks.slice(first, last).map((r, k) => ({ folded: r.folded, skip: skipped(at(k)) }));
|
|
161
233
|
globs = valuesAreLiteral(row, words.map((w) => w.folded)) ? "literal" : "expanded";
|
|
234
|
+
noteDeliveredOperands(row, words.map((w) => w.folded), ctx);
|
|
162
235
|
const someRead = wordsReadBySomeImplementations(row, words.map((w) => w.folded));
|
|
163
|
-
|
|
236
|
+
const slotAt = slotOperandAt(row, words);
|
|
237
|
+
slotWord = slotAt === undefined ? undefined : at(slotAt);
|
|
238
|
+
for (const e of readArgs(row, words, { firstOperandSlot: slotKind, ownedValues: true })) {
|
|
164
239
|
const start = reads.length;
|
|
165
240
|
handleUnlistedEvent(e, at(e.at));
|
|
166
241
|
if (someRead.has(e.at))
|
|
@@ -175,8 +250,7 @@ export function unlistedWords(reads, toks, from, launcherIndices, provenance, ct
|
|
|
175
250
|
walkRow = sub.row;
|
|
176
251
|
walkFrom = argvStart + 2 + sub.at;
|
|
177
252
|
relocated = sub.relocated;
|
|
178
|
-
|
|
179
|
-
stdinOperand = false;
|
|
253
|
+
gathered.restart();
|
|
180
254
|
walk(sub.row, walkFrom, toks.length, true);
|
|
181
255
|
}
|
|
182
256
|
else
|
|
@@ -199,6 +273,7 @@ export function unlistedWords(reads, toks, from, launcherIndices, provenance, ct
|
|
|
199
273
|
return;
|
|
200
274
|
case "value": {
|
|
201
275
|
if (!e.consumed) {
|
|
276
|
+
gathered.value(r, e, false);
|
|
202
277
|
if (r.expands !== "unresolvable")
|
|
203
278
|
reads.push(...roleReads(r, "option_value", r.folded, e.role, globs, ctx, true));
|
|
204
279
|
return;
|
|
@@ -207,8 +282,7 @@ export function unlistedWords(reads, toks, from, launcherIndices, provenance, ct
|
|
|
207
282
|
return;
|
|
208
283
|
const named = roleReads(r, "option_value", r.folded, e.role, globs, ctx);
|
|
209
284
|
reads.push(...named);
|
|
210
|
-
|
|
211
|
-
positional.push(r);
|
|
285
|
+
gathered.value(r, e, named.some((c) => c.denyOnly !== true));
|
|
212
286
|
return;
|
|
213
287
|
}
|
|
214
288
|
case "option":
|
|
@@ -224,15 +298,20 @@ export function unlistedWords(reads, toks, from, launcherIndices, provenance, ct
|
|
|
224
298
|
speculate(whole, "whole");
|
|
225
299
|
return;
|
|
226
300
|
}
|
|
227
|
-
|
|
301
|
+
{
|
|
302
|
+
const named = roleReads(r, "option_value", literalTildeSpelling(e.reading.attached), e.reading.role, globs, ctx, pastOperand.has(j));
|
|
303
|
+
reads.push(...named);
|
|
304
|
+
gathered.attached(named, e.reading.spec);
|
|
305
|
+
}
|
|
228
306
|
return;
|
|
229
307
|
case "operand": {
|
|
230
308
|
const role = e.dash === undefined ? (e.slot ?? e.role) : undefined;
|
|
231
309
|
const named = role !== undefined ? roleReads(r, provenance, r.folded, role, globs, ctx) : [bare(r, provenance)];
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
310
|
+
const inSlot = j === slotWord;
|
|
311
|
+
if (inSlot)
|
|
312
|
+
gathered.slot(r);
|
|
313
|
+
else
|
|
314
|
+
gathered.operand(r, named.some((c) => c.denyOnly !== true), e.dash === "stdin");
|
|
236
315
|
reads.push(...named);
|
|
237
316
|
speculate(start, r.word.assignment !== undefined ? "whole" : "containment");
|
|
238
317
|
const values = reads.length;
|
|
@@ -244,9 +323,8 @@ export function unlistedWords(reads, toks, from, launcherIndices, provenance, ct
|
|
|
244
323
|
}
|
|
245
324
|
}
|
|
246
325
|
if (walkRow !== undefined && argv !== undefined && selectsContentsTraversal(walkRow, toks.slice(walkFrom).map((x) => x.folded))) {
|
|
247
|
-
const
|
|
248
|
-
|
|
249
|
-
reads.push(relocated ? { ...bare(root, "traversal_root"), expands: "unresolvable" } : bare(root, "traversal_root"));
|
|
326
|
+
for (const root of gathered.roots(walkRow))
|
|
327
|
+
reads.push(relocated ? { ...root, expands: "unresolvable" } : root);
|
|
250
328
|
}
|
|
251
329
|
for (let j = from; j < toks.length; j++) {
|
|
252
330
|
if (launcherIndices.has(j) || j === argvStart)
|
|
@@ -293,17 +371,19 @@ export function listedVerbCandidates(name, argReads, reads, ctx) {
|
|
|
293
371
|
function walkListed(row, argReads, first, last, expanding, reads, ctx, relocated) {
|
|
294
372
|
const slice = argReads.slice(first, last);
|
|
295
373
|
const args = slice.map((r) => r.folded);
|
|
296
|
-
const
|
|
297
|
-
let
|
|
374
|
+
const gathered = new RootsGathered();
|
|
375
|
+
let unexplained = false;
|
|
298
376
|
const globs = valuesAreLiteral(row, args) ? "literal" : "expanded";
|
|
377
|
+
noteDeliveredOperands(row, args, ctx);
|
|
299
378
|
const someRead = wordsReadBySomeImplementations(row, args);
|
|
300
379
|
const pastOperand = new Set();
|
|
301
380
|
const offer = (k, value, role, provenance, alsoOperand = false) => {
|
|
302
381
|
const named = roleReads(slice[k], provenance, value, role, globs, ctx, alsoOperand);
|
|
303
382
|
reads.push(...named);
|
|
304
|
-
return named
|
|
383
|
+
return named;
|
|
305
384
|
};
|
|
306
|
-
|
|
385
|
+
const opensPath = (named) => named.some((c) => c.denyOnly !== true);
|
|
386
|
+
for (const e of readArgs(row, args.map((folded, k) => ({ folded, skip: expanding.has(first + k) })), { firstOperandSlot: true, ownedValues: true })) {
|
|
307
387
|
const t = args[e.at];
|
|
308
388
|
const start = reads.length;
|
|
309
389
|
switch (e.kind) {
|
|
@@ -316,42 +396,43 @@ function walkListed(row, argReads, first, last, expanding, reads, ctx, relocated
|
|
|
316
396
|
case "value": {
|
|
317
397
|
if (expanding.has(first + e.at))
|
|
318
398
|
break;
|
|
319
|
-
|
|
320
|
-
positional.push(slice[e.at]);
|
|
399
|
+
gathered.value(slice[e.at], e, opensPath(offer(e.at, t, e.role, "option_value", !e.consumed)));
|
|
321
400
|
break;
|
|
322
401
|
}
|
|
323
402
|
case "option":
|
|
324
403
|
if (e.reading === "no-value")
|
|
325
404
|
break;
|
|
326
405
|
if (e.reading === "speculative") {
|
|
406
|
+
if (row === undefined || mayOwnNextWord(row, t))
|
|
407
|
+
unexplained = true;
|
|
327
408
|
for (const payload of attachedOptionPayloads(t))
|
|
328
409
|
reads.push(bare(slice[e.at], "option_value", payload));
|
|
329
410
|
break;
|
|
330
411
|
}
|
|
331
|
-
offer(e.at, literalTildeSpelling(e.reading.attached), e.reading.role, "option_value", pastOperand.has(e.at));
|
|
412
|
+
gathered.attached(offer(e.at, literalTildeSpelling(e.reading.attached), e.reading.role, "option_value", pastOperand.has(e.at)), e.reading.spec);
|
|
332
413
|
break;
|
|
333
414
|
case "operand": {
|
|
334
415
|
if (e.dash !== undefined) {
|
|
335
|
-
if (e.slot !== undefined)
|
|
416
|
+
if (e.slot !== undefined) {
|
|
417
|
+
gathered.slot(slice[e.at]);
|
|
336
418
|
break;
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
else
|
|
340
|
-
positional.push(slice[e.at]);
|
|
419
|
+
}
|
|
420
|
+
gathered.operand(slice[e.at], true, e.dash === "stdin");
|
|
341
421
|
break;
|
|
342
422
|
}
|
|
343
423
|
if (e.slot !== undefined) {
|
|
344
|
-
|
|
345
|
-
|
|
424
|
+
offer(e.at, t, e.slot, "operand");
|
|
425
|
+
if (unexplained && e.slot.kind === "datum" && e.slot.form === "pattern")
|
|
426
|
+
reads.push(bare(slice[e.at], "operand"));
|
|
427
|
+
gathered.slot(slice[e.at]);
|
|
346
428
|
break;
|
|
347
429
|
}
|
|
348
|
-
let
|
|
430
|
+
let opens = true;
|
|
349
431
|
if (e.role !== undefined)
|
|
350
|
-
|
|
432
|
+
opens = opensPath(offer(e.at, t, e.role, "operand"));
|
|
351
433
|
else
|
|
352
434
|
reads.push(bare(slice[e.at], "operand"));
|
|
353
|
-
|
|
354
|
-
positional.push(slice[e.at]);
|
|
435
|
+
gathered.operand(slice[e.at], opens, false);
|
|
355
436
|
if (row?.operands?.assignmentArguments !== "not-paths")
|
|
356
437
|
pushAssignment(reads, slice[e.at].word, "operand");
|
|
357
438
|
break;
|
|
@@ -362,10 +443,9 @@ function walkListed(row, argReads, first, last, expanding, reads, ctx, relocated
|
|
|
362
443
|
if (reads[i].expands !== "unresolvable" && reads[i].denyOnly !== true)
|
|
363
444
|
reads[i] = { ...reads[i], speculative: "containment" };
|
|
364
445
|
}
|
|
365
|
-
if (selectsContentsTraversal(row, args)) {
|
|
366
|
-
const
|
|
367
|
-
|
|
368
|
-
reads.push(relocated ? { ...bare(root, "traversal_root"), expands: "unresolvable" } : bare(root, "traversal_root"));
|
|
446
|
+
if (row !== undefined && selectsContentsTraversal(row, args)) {
|
|
447
|
+
for (const root of gathered.roots(row))
|
|
448
|
+
reads.push(relocated ? { ...root, expands: "unresolvable" } : root);
|
|
369
449
|
}
|
|
370
450
|
}
|
|
371
451
|
export function subscriptOnly(word) {
|
|
@@ -4,8 +4,8 @@
|
|
|
4
4
|
* decides WHICH words a command may read, `shell-read-write-targets.ts` which words it writes and at which seat;
|
|
5
5
|
* this module decides WHERE each of them lands: the canonical
|
|
6
6
|
* target of a spelling (symlinks resolved, a `..` applied the way the kernel applies it), the expansion of
|
|
7
|
-
* a pattern (shell pathname semantics over `env.listDir`),
|
|
8
|
-
*
|
|
7
|
+
* a pattern (shell pathname semantics over `env.listDir`), what a traversal root is (one stat: a recursive read is
|
|
8
|
+
* judged by the root it names, its tree is never enumerated), and the fail-closed arm
|
|
9
9
|
* for what could not be established. The judge (`shell-read-judge.ts`) is downstream; nothing here decides
|
|
10
10
|
* allow/ask/deny.
|
|
11
11
|
*
|
|
@@ -27,9 +27,9 @@
|
|
|
27
27
|
* 4. NO MATCH is not a refusal: an unmatched pattern is handed to the command verbatim, so an empty
|
|
28
28
|
* expansion falls back to the literal spelling.
|
|
29
29
|
* 5. What it cannot enumerate is `unestablishable`, never silently vouched: an unreadable directory, a
|
|
30
|
-
* pattern construct the matcher does not model, an expansion
|
|
30
|
+
* pattern construct the matcher does not model, an expansion past
|
|
31
31
|
* {@link MAX_GLOB_DIRS} / {@link MAX_GLOB_MATCHES}.
|
|
32
|
-
* 6. Cost is paid only by candidates that carry a metacharacter
|
|
32
|
+
* 6. Cost is paid only by candidates that carry a metacharacter, and only past the roots'
|
|
33
33
|
* own spelling. Inside one enumerated directory only the SYMLINK entries need their own `realpath`.
|
|
34
34
|
*
|
|
35
35
|
* NOT cached deliberately: a per-run memo keyed on the spelling would answer from a snapshot of where a
|
|
@@ -44,7 +44,7 @@ import type { ShellReadPlan, ShellReadSegment } from "./shell-read-plan.js";
|
|
|
44
44
|
import type { EstablishedRead, ShellReadBoundary } from "./shell-read-judge.js";
|
|
45
45
|
import type { HomeViewSource } from "./read-deny-home.js";
|
|
46
46
|
/**
|
|
47
|
-
* How many directories one glob operand
|
|
47
|
+
* How many directories one glob operand may enumerate, and how many names it may
|
|
48
48
|
* match, before the leg gives up and answers `unestablishable`.
|
|
49
49
|
*
|
|
50
50
|
* Sized so the everyday shapes never hit them: 256 directories covers a two-level pattern over a source
|
|
@@ -366,54 +366,11 @@ function establishLegOver(seen, readRoots) {
|
|
|
366
366
|
}
|
|
367
367
|
return { paths: frontier, canonical: canonicalOfMatch };
|
|
368
368
|
};
|
|
369
|
-
const
|
|
370
|
-
const
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
const visited = new Set([rootCanonical]);
|
|
375
|
-
let dirsUsed = 0;
|
|
376
|
-
while (stack.length > 0) {
|
|
377
|
-
const { dir, spell } = stack.pop();
|
|
378
|
-
if (++dirsUsed > MAX_GLOB_DIRS)
|
|
379
|
-
return bounded(`"${rootCanonical}" holds more than ${MAX_GLOB_DIRS} directories, too many to enumerate to verify what a recursive read would open`);
|
|
380
|
-
const listed = await env.listDir(dir, signal);
|
|
381
|
-
if (!listed.ok) {
|
|
382
|
-
if (dir === rootCanonical && listed.error.code === "not_directory")
|
|
383
|
-
root = "file";
|
|
384
|
-
if (listed.error.code === "not_directory" || listed.error.code === "not_found")
|
|
385
|
-
continue;
|
|
386
|
-
return { unverifiable: `"${dir}" cannot be enumerated to verify what a recursive read would open (${listed.error.code})` };
|
|
387
|
-
}
|
|
388
|
-
listedDirs.add(dir);
|
|
389
|
-
if (dir === rootCanonical)
|
|
390
|
-
root = "directory";
|
|
391
|
-
for (const entry of listed.value) {
|
|
392
|
-
if (found.length >= MAX_GLOB_MATCHES)
|
|
393
|
-
return bounded(`"${rootCanonical}" holds more than ${MAX_GLOB_MATCHES} entries, too many to enumerate to verify what a recursive read would open`);
|
|
394
|
-
const path = joinUnder(spell, entry.name);
|
|
395
|
-
const canonicalPath = joinUnder(dir, entry.name);
|
|
396
|
-
if (entry.kind === "symlink") {
|
|
397
|
-
const canon = await env.canonicalPath(canonicalPath, signal);
|
|
398
|
-
found.push({ path, ...(canon.ok ? { canonical: canon.value } : {}), symlink: true });
|
|
399
|
-
if (canon.ok && !visited.has(canon.value)) {
|
|
400
|
-
visited.add(canon.value);
|
|
401
|
-
stack.push({ dir: canon.value, spell: path });
|
|
402
|
-
}
|
|
403
|
-
continue;
|
|
404
|
-
}
|
|
405
|
-
if (entry.kind === "directory") {
|
|
406
|
-
if (!visited.has(canonicalPath)) {
|
|
407
|
-
visited.add(canonicalPath);
|
|
408
|
-
stack.push({ dir: canonicalPath, spell: path });
|
|
409
|
-
}
|
|
410
|
-
continue;
|
|
411
|
-
}
|
|
412
|
-
found.push({ path, canonical: canonicalPath, symlink: false });
|
|
413
|
-
}
|
|
414
|
-
}
|
|
415
|
-
const members = found.map(({ path, canonical, symlink }) => ({ path, ...(canonical !== undefined ? { canonical } : {}), node: (symlink && canonical !== undefined && listedDirs.has(canonical) ? "directory" : "file") }));
|
|
416
|
-
return { ...(root !== undefined ? { root } : {}), members };
|
|
369
|
+
const rootKindOf = async (rootCanonical, signal) => {
|
|
370
|
+
const info = await env.fileInfo(rootCanonical, signal);
|
|
371
|
+
if (!info.ok)
|
|
372
|
+
return undefined;
|
|
373
|
+
return info.value.kind === "directory" ? "directory" : info.value.kind === "file" ? "file" : undefined;
|
|
417
374
|
};
|
|
418
375
|
const entryOf = async (spelling, signal) => {
|
|
419
376
|
const parts = spelling.split(SEP);
|
|
@@ -554,20 +511,13 @@ function establishLegOver(seen, readRoots) {
|
|
|
554
511
|
}
|
|
555
512
|
return reads;
|
|
556
513
|
};
|
|
557
|
-
const land = async (read
|
|
514
|
+
const land = async (read) => {
|
|
558
515
|
if (!traversal || (read.established !== "canonical" && read.established !== "expansion") || read.target === undefined) {
|
|
559
516
|
out.push(read);
|
|
560
517
|
return;
|
|
561
518
|
}
|
|
562
|
-
const
|
|
563
|
-
|
|
564
|
-
out.push(read);
|
|
565
|
-
out.push({ candidate, established: "unestablishable", spellings, origin: folded, cause: walkedTree.unverifiable });
|
|
566
|
-
return;
|
|
567
|
-
}
|
|
568
|
-
out.push({ ...read, ...(walkedTree.root !== undefined ? { node: walkedTree.root } : {}) });
|
|
569
|
-
for (const m of walkedTree.members)
|
|
570
|
-
out.push({ ...(await canonicalReadOf(candidate, m.path, [m.path], "expansion", folded, m.canonical, signal)), node: m.node, walked: true });
|
|
519
|
+
const node = await rootKindOf(read.target, signal);
|
|
520
|
+
out.push({ ...read, ...(node !== undefined ? { node } : {}) });
|
|
571
521
|
};
|
|
572
522
|
for (const [i, lexical] of lexicalReadsOf(candidate, boundary).entries()) {
|
|
573
523
|
if (lexical.established !== "lexical" || passesUnasked(candidate)) {
|
|
@@ -590,16 +540,16 @@ function establishLegOver(seen, readRoots) {
|
|
|
590
540
|
matched = true;
|
|
591
541
|
for (const t of expanded.paths)
|
|
592
542
|
for (const read of await atSeats(t, [t, folded], "expansion", folded, expanded.canonical.get(t)))
|
|
593
|
-
await land(read
|
|
543
|
+
await land(read);
|
|
594
544
|
}
|
|
595
545
|
}
|
|
596
546
|
if (!matched || candidate.pattern !== undefined)
|
|
597
547
|
for (const read of await atSeats(walked, spellings, "canonical", undefined, undefined))
|
|
598
|
-
await land(read
|
|
548
|
+
await land(read);
|
|
599
549
|
continue;
|
|
600
550
|
}
|
|
601
551
|
for (const read of await atSeats(walked, spellings, "canonical", undefined, undefined))
|
|
602
|
-
await land(read
|
|
552
|
+
await land(read);
|
|
603
553
|
}
|
|
604
554
|
}
|
|
605
555
|
return out;
|
|
@@ -40,14 +40,17 @@ function sameTargets(a, b) {
|
|
|
40
40
|
}
|
|
41
41
|
export async function withHomeViews(door, placed, established, signal) {
|
|
42
42
|
const views = homeViewsOf(door.fs, placed, signal);
|
|
43
|
+
const unread = [];
|
|
43
44
|
const place = async (p) => {
|
|
44
45
|
const reads = new Map();
|
|
45
46
|
for (const [segment, rs] of p.reads) {
|
|
46
47
|
const out = [];
|
|
47
48
|
for (const r of rs) {
|
|
48
49
|
const landed = r.target !== undefined && (r.established === "canonical" || r.established === "expansion");
|
|
49
|
-
const
|
|
50
|
-
|
|
50
|
+
const home = landed ? await views.of(r.target, r.node === "file" ? { leaf: "file" } : undefined) : {};
|
|
51
|
+
if (home.unread !== undefined && !unread.includes(home.unread))
|
|
52
|
+
unread.push(home.unread);
|
|
53
|
+
out.push(home.view === undefined || r.spellings.includes(home.view) ? r : { ...r, spellings: [...r.spellings, home.view] });
|
|
51
54
|
}
|
|
52
55
|
reads.set(segment, out);
|
|
53
56
|
}
|
|
@@ -57,6 +60,6 @@ export async function withHomeViews(door, placed, established, signal) {
|
|
|
57
60
|
return { ...p, reads, nested };
|
|
58
61
|
};
|
|
59
62
|
const withViews = await place(established);
|
|
60
|
-
door.adopt(
|
|
63
|
+
door.adopt(unread.map((p) => ({ op: "fileIdentity", detail: `"${p}" cannot be identified against the home directories` })));
|
|
61
64
|
return withViews;
|
|
62
65
|
}
|
|
@@ -96,7 +96,9 @@ export declare function dispositionOfCell(cell: ShellReadCell, context?: ShellRe
|
|
|
96
96
|
* · `unanswered` — the judge did not FINISH: it threw or timed out, the lookup it stands on was absent, or — recorded at the
|
|
97
97
|
* one door to the environment ({@link import("./shell-read-environment.js").Incomplete}) — an environment lookup gave no
|
|
98
98
|
* answer (an error that is no conclusive "not there"), the station stopped at its own bound (more directories or names than
|
|
99
|
-
* it enumerates, a link chain past its hop bound), or a home view could not be read
|
|
99
|
+
* it enumerates, a link chain past its hop bound), or a home view could not be read — or a recursive read's root may hold a
|
|
100
|
+
* home-anchored deny row that no home places (the environment declares none, or its placement did not answer), a home the
|
|
101
|
+
* station cannot place either. Any one makes the whole command
|
|
100
102
|
* `unanswered`, whatever the other words found. Not a fact about the command but the state of the station, so it is not
|
|
101
103
|
* the `unestablishable` row's question (a text the station cannot place — a word the shell rewrites, a lost working
|
|
102
104
|
* directory, a pattern its matcher does not model). Absence is not
|
|
@@ -239,13 +241,9 @@ export interface EstablishedRead {
|
|
|
239
241
|
readonly spellings: readonly string[];
|
|
240
242
|
/** The pattern or traversal root an `expansion` came from, as folded. */
|
|
241
243
|
readonly origin?: string;
|
|
242
|
-
/** What the environment said the target IS, where a read asked — only a traversal asks (it lists the root
|
|
243
|
-
*
|
|
244
|
+
/** What the environment said the target IS, where a read asked — only a traversal root asks (it lists the root
|
|
245
|
+
* once; a link's answer is its target's). Absent = nothing asked; a plain read never lists. */
|
|
244
246
|
readonly node?: "directory" | "file";
|
|
245
|
-
/** A MEMBER a traversal enumerated below its root — never a spelling of the command. The deny judge reads it
|
|
246
|
-
* ({@link import("./read-deny.js").ReadDenyMatcher.matchPath} `walked`): the segment rows still judge it, a
|
|
247
|
-
* rule-DSL row does not. Absent on the root itself, on a pattern's own matches and on every spelled operand. */
|
|
248
|
-
readonly walked?: true;
|
|
249
247
|
/** Why the candidate could not be established. */
|
|
250
248
|
readonly cause?: string;
|
|
251
249
|
/** The candidate's spelling WAS placed and the environment could not resolve where it leads (the whole chain unanswered by
|
|
@@ -263,12 +261,12 @@ export interface EstablishedRead {
|
|
|
263
261
|
readonly child?: true;
|
|
264
262
|
};
|
|
265
263
|
}
|
|
266
|
-
/** What the judge found about ONE candidate. `kind` is one of the
|
|
267
|
-
*
|
|
268
|
-
*
|
|
264
|
+
/** What the judge found about ONE candidate. `kind` is one of the five candidate-level findings (`declined` is a segment fact,
|
|
265
|
+
* `identity_changed` a re-establishment fact — neither is a candidate's; `unanswered` is a fact of the whole establishment, and
|
|
266
|
+
* a candidate's where a recursive read's root may hold a deny row no home places, {@link judgeRead}). */
|
|
269
267
|
export interface ReadFinding {
|
|
270
268
|
readonly read: EstablishedRead;
|
|
271
|
-
readonly kind: Extract<ShellReadFinding, "deny_hit" | "outside_roots" | "unestablishable" | "none">;
|
|
269
|
+
readonly kind: Extract<ShellReadFinding, "deny_hit" | "outside_roots" | "unestablishable" | "unanswered" | "none">;
|
|
272
270
|
/** The deny row that matched, the view it matched on, and — for a write target — the face (`write`) that refused. */
|
|
273
271
|
readonly deny?: {
|
|
274
272
|
readonly pattern: string;
|
|
@@ -379,10 +377,10 @@ export interface ShellReadFold {
|
|
|
379
377
|
* yields more words, never zero, so an unreadable text is never "no candidates";
|
|
380
378
|
* · a SHELL re-entry segment (`sh -c S`, `eval S`, `env -S 'S'`, a launcher handing text to a shell) is at
|
|
381
379
|
* least `unestablishable` — what runs is text the shell parses, not this plan — and its nested plan may
|
|
382
|
-
* only RAISE that
|
|
383
|
-
* it)
|
|
384
|
-
* outer text). A substitution body (`$(…)`, a backtick, `<(…)`) is nested
|
|
385
|
-
* in full.
|
|
380
|
+
* only RAISE that: the nested text's deny-relation answers count — a deny hit (a refusal is a refusal whatever
|
|
381
|
+
* runs it) and a root that may hold a row no home places — its containment and its other silence do not (an inner
|
|
382
|
+
* `cat inside.txt` vouches nothing about the outer text). A substitution body (`$(…)`, a backtick, `<(…)`) is nested
|
|
383
|
+
* WITHOUT re-entry and folds in full.
|
|
386
384
|
*/
|
|
387
385
|
export declare function foldShellReadFindings(judged: JudgedPlan): ShellReadFold;
|
|
388
386
|
/** Judge every established read of a plan, in place. `establish` runs per segment so a caller can bound it. */
|
|
@@ -46,14 +46,28 @@ export function judgeRead(read, boundary) {
|
|
|
46
46
|
const writeTarget = read.candidate.face === "write";
|
|
47
47
|
const deny = writeTarget ? boundary.writeDenyMatch : boundary.denyMatch;
|
|
48
48
|
if (deny !== undefined) {
|
|
49
|
-
const walked = read.walked === true ? { walked: true } : undefined;
|
|
50
49
|
const views = [...(read.target !== undefined ? [read.target] : []), ...read.spellings];
|
|
51
50
|
for (const view of views) {
|
|
52
51
|
const folded = normalizeAbsPathLexically(view);
|
|
53
|
-
const pattern = writeTarget ? boundary.writeDenyMatch(folded) : boundary.denyMatch(folded
|
|
52
|
+
const pattern = writeTarget ? boundary.writeDenyMatch(folded) : boundary.denyMatch(folded);
|
|
54
53
|
if (pattern !== null)
|
|
55
54
|
return { read, kind: "deny_hit", deny: { pattern, matchedView: folded, ...(writeTarget ? { face: "write" } : {}) }, containment: writeTarget ? writeContainmentOf(read, boundary) : containmentOf(read, boundary) };
|
|
56
55
|
}
|
|
56
|
+
if (!writeTarget && read.candidate.provenance === "traversal_root" && boundary.denyUnder !== undefined) {
|
|
57
|
+
let unplaced;
|
|
58
|
+
for (const view of views) {
|
|
59
|
+
const folded = normalizeAbsPathLexically(view);
|
|
60
|
+
const under = boundary.denyUnder(folded);
|
|
61
|
+
if (typeof under === "string")
|
|
62
|
+
return { read, kind: "deny_hit", deny: { pattern: under, matchedView: folded }, containment: containmentOf(read, boundary) };
|
|
63
|
+
if (under !== null && typeof under === "object")
|
|
64
|
+
unplaced ??= under.unplaced;
|
|
65
|
+
}
|
|
66
|
+
if (unplaced !== undefined) {
|
|
67
|
+
const cause = `the home-anchored deny row "${unplaced}" cannot be placed (no home directory is known for this environment), so "${read.target ?? read.candidate.spelled}" may hold it`;
|
|
68
|
+
return { read: { ...read, cause }, kind: "unanswered", containment: containmentOf(read, boundary) };
|
|
69
|
+
}
|
|
70
|
+
}
|
|
57
71
|
}
|
|
58
72
|
if (writeTarget)
|
|
59
73
|
return judgeWrite(read, boundary);
|
|
@@ -119,7 +133,7 @@ export function foldShellReadFindings(judged) {
|
|
|
119
133
|
let unestablished = false;
|
|
120
134
|
let unplacedRead = false;
|
|
121
135
|
const raise = (next) => {
|
|
122
|
-
if (next.finding === "unestablishable" || next.finding === "declined") {
|
|
136
|
+
if (next.finding === "unestablishable" || next.finding === "declined" || next.finding === "unanswered") {
|
|
123
137
|
const face = next.witness?.read.candidate.face;
|
|
124
138
|
if (!(next.witness === undefined ? judged.guards || judged.writeGuards : face === "write" ? judged.writeGuards : judged.guards))
|
|
125
139
|
return;
|
|
@@ -136,7 +150,7 @@ export function foldShellReadFindings(judged) {
|
|
|
136
150
|
raise({ finding: "unestablishable" });
|
|
137
151
|
for (const s of j.segments) {
|
|
138
152
|
for (const f of s.findings) {
|
|
139
|
-
if (denyOnly && f.kind !== "deny_hit")
|
|
153
|
+
if (denyOnly && f.kind !== "deny_hit" && f.kind !== "unanswered")
|
|
140
154
|
continue;
|
|
141
155
|
if (f.kind !== "none")
|
|
142
156
|
raise({ finding: f.kind, witness: f });
|
|
@@ -119,8 +119,8 @@ export interface ShellReadSegment {
|
|
|
119
119
|
/** `shell` = the program runs its argument as shell text; `argv` = its operands arrive on a stream;
|
|
120
120
|
* `interpreter` = it runs an inline program in a language this parser does not read (a shape fact only). */
|
|
121
121
|
readonly reentry?: "shell" | "argv" | "interpreter";
|
|
122
|
-
/**
|
|
123
|
-
*
|
|
122
|
+
/** Why what this segment reads is not established, as a sentence: program text the station could not read (a script supplied
|
|
123
|
+
* from a file, text not parseable to its end, a program on standard input) or the list file the operands come from. */
|
|
124
124
|
readonly unreadProgramText?: string;
|
|
125
125
|
readonly declines: readonly ShellScanDecline[];
|
|
126
126
|
readonly reads: readonly ReadCandidate[];
|
package/dist/tools/web.js
CHANGED
|
@@ -6,7 +6,7 @@ import { egressThrownText } from "../core/untrusted-egress.js";
|
|
|
6
6
|
import { isPrivateHost } from "../core/runner/image.js";
|
|
7
7
|
import { DEFAULT_CHARS_PER_TOKEN } from "../internal/harness.js";
|
|
8
8
|
import { binaryMagicFormat } from "./fs/safety.js";
|
|
9
|
-
import { pdfMagicMatches } from "
|
|
9
|
+
import { pdfMagicMatches } from "../core/image-admission.js";
|
|
10
10
|
import { toolFace } from "../core/tool-catalog-entries.js";
|
|
11
11
|
import { thrownText } from "../core/thrown-value.js";
|
|
12
12
|
const MAX_REDIRECTS = 10;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@sema-agent/core",
|
|
3
|
-
"version": "7.
|
|
3
|
+
"version": "7.52.0",
|
|
4
4
|
"description": "Stateless, task-oriented AI agent core",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "BUSL-1.1",
|
|
@@ -46,6 +46,9 @@
|
|
|
46
46
|
"engines": {
|
|
47
47
|
"node": ">=20.18.1"
|
|
48
48
|
},
|
|
49
|
+
"workspaces": [
|
|
50
|
+
"packages/*"
|
|
51
|
+
],
|
|
49
52
|
"scripts": {
|
|
50
53
|
"build": "rm -rf dist && tsc -p tsconfig.build.json && tsc -p tsconfig.build.json --emitDeclarationOnly --removeComments false",
|
|
51
54
|
"typecheck": "tsc --noEmit && echo \"typecheck OK (tsc --noEmit clean)\"",
|
|
@@ -78,8 +81,14 @@
|
|
|
78
81
|
"gate:error-surface": "node scripts/verify-error-surface.mjs",
|
|
79
82
|
"gate:criteria": "node scripts/criteria-lint.mjs",
|
|
80
83
|
"gate:reminder-literal": "node scripts/verify-reminder-literal.mjs",
|
|
84
|
+
"gate:catalog-literal": "node scripts/verify-catalog-literal.mjs",
|
|
85
|
+
"gate:sugar-single-site": "node scripts/verify-sugar-single-site.mjs",
|
|
81
86
|
"gate:wire": "node scripts/wire-changes.mjs",
|
|
82
87
|
"gate:layering": "node scripts/verify-layering.mjs",
|
|
88
|
+
"gate:import-cycles": "node scripts/verify-import-cycles.mjs",
|
|
89
|
+
"gate:packages": "node scripts/verify-packages.mjs",
|
|
90
|
+
"gate:packages:pack": "node scripts/verify-packages.mjs --pack",
|
|
91
|
+
"build:packages": "node scripts/verify-packages.mjs --build",
|
|
83
92
|
"gate:phase-api": "node scripts/verify-phase-api.mjs",
|
|
84
93
|
"gate:closed-sets": "node scripts/verify-closed-sets.mjs",
|
|
85
94
|
"gate:agent-returns": "node scripts/verify-agent-returns.mjs",
|
|
@@ -88,7 +97,10 @@
|
|
|
88
97
|
"gate:tool-names": "node scripts/verify-tool-name-tables.mjs",
|
|
89
98
|
"gate:name-readings": "node scripts/verify-name-readings.mjs",
|
|
90
99
|
"gate:tool-docs": "node scripts/gen-tool-spec-fields.mjs --check",
|
|
100
|
+
"gate:prompt-docs": "node scripts/gen-prompt-docs.mjs --check",
|
|
101
|
+
"gen:prompt-docs": "node scripts/gen-prompt-docs.mjs",
|
|
91
102
|
"gate:backlog-ledger": "node scripts/verify-backlog-ledger.mjs",
|
|
103
|
+
"gate:changelog-coverage": "node scripts/verify-changelog-coverage.mjs",
|
|
92
104
|
"gate:child-clamp-seats": "node scripts/verify-child-clamp-seats.mjs",
|
|
93
105
|
"gate:spawn-sites": "node scripts/verify-spawn-sites.mjs",
|
|
94
106
|
"gate:point-free-callbacks": "node scripts/verify-point-free-callbacks.mjs",
|