arc-1 1.1.2 → 1.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +16 -6
- package/bin/start-cf.sh +32 -0
- package/dist/adt/atc-batch.d.ts +71 -0
- package/dist/adt/atc-batch.d.ts.map +1 -0
- package/dist/adt/atc-batch.js +182 -0
- package/dist/adt/atc-batch.js.map +1 -0
- package/dist/adt/atc.d.ts +34 -0
- package/dist/adt/atc.d.ts.map +1 -1
- package/dist/adt/atc.js +58 -12
- package/dist/adt/atc.js.map +1 -1
- package/dist/adt/aunit.d.ts.map +1 -1
- package/dist/adt/aunit.js +50 -7
- package/dist/adt/aunit.js.map +1 -1
- package/dist/adt/bounded-response.d.ts +12 -0
- package/dist/adt/bounded-response.d.ts.map +1 -0
- package/dist/adt/bounded-response.js +242 -0
- package/dist/adt/bounded-response.js.map +1 -0
- package/dist/adt/ci-quality-xml.d.ts +44 -0
- package/dist/adt/ci-quality-xml.d.ts.map +1 -0
- package/dist/adt/ci-quality-xml.js +98 -0
- package/dist/adt/ci-quality-xml.js.map +1 -0
- package/dist/adt/ci-quality.d.ts +64 -0
- package/dist/adt/ci-quality.d.ts.map +1 -0
- package/dist/adt/ci-quality.js +132 -0
- package/dist/adt/ci-quality.js.map +1 -0
- package/dist/adt/client.d.ts +55 -34
- package/dist/adt/client.d.ts.map +1 -1
- package/dist/adt/client.js +130 -169
- package/dist/adt/client.js.map +1 -1
- package/dist/adt/config.d.ts +6 -0
- package/dist/adt/config.d.ts.map +1 -1
- package/dist/adt/config.js +3 -0
- package/dist/adt/config.js.map +1 -1
- package/dist/adt/data-result-context.d.ts +46 -0
- package/dist/adt/data-result-context.d.ts.map +1 -0
- package/dist/adt/data-result-context.js +118 -0
- package/dist/adt/data-result-context.js.map +1 -0
- package/dist/adt/data-source-name.d.ts +60 -0
- package/dist/adt/data-source-name.d.ts.map +1 -0
- package/dist/adt/data-source-name.js +156 -0
- package/dist/adt/data-source-name.js.map +1 -0
- package/dist/adt/data-source-policy.d.ts +139 -0
- package/dist/adt/data-source-policy.d.ts.map +1 -0
- package/dist/adt/data-source-policy.js +759 -0
- package/dist/adt/data-source-policy.js.map +1 -0
- package/dist/adt/ddic-xml.d.ts +78 -4
- package/dist/adt/ddic-xml.d.ts.map +1 -1
- package/dist/adt/ddic-xml.js +647 -54
- package/dist/adt/ddic-xml.js.map +1 -1
- package/dist/adt/devtools.d.ts +1 -0
- package/dist/adt/devtools.d.ts.map +1 -1
- package/dist/adt/devtools.js +24 -4
- package/dist/adt/devtools.js.map +1 -1
- package/dist/adt/errors.d.ts +10 -0
- package/dist/adt/errors.d.ts.map +1 -1
- package/dist/adt/errors.js +17 -0
- package/dist/adt/errors.js.map +1 -1
- package/dist/adt/http-deadline.d.ts +10 -0
- package/dist/adt/http-deadline.d.ts.map +1 -1
- package/dist/adt/http-deadline.js +7 -0
- package/dist/adt/http-deadline.js.map +1 -1
- package/dist/adt/http.d.ts +6 -3
- package/dist/adt/http.d.ts.map +1 -1
- package/dist/adt/http.js +94 -55
- package/dist/adt/http.js.map +1 -1
- package/dist/adt/internal-data-operations.d.ts +56 -0
- package/dist/adt/internal-data-operations.d.ts.map +1 -0
- package/dist/adt/internal-data-operations.js +99 -0
- package/dist/adt/internal-data-operations.js.map +1 -0
- package/dist/adt/package-contents.d.ts +12 -0
- package/dist/adt/package-contents.d.ts.map +1 -0
- package/dist/adt/package-contents.js +19 -0
- package/dist/adt/package-contents.js.map +1 -0
- package/dist/adt/relation-objects.d.ts +385 -0
- package/dist/adt/relation-objects.d.ts.map +1 -0
- package/dist/adt/relation-objects.js +262 -0
- package/dist/adt/relation-objects.js.map +1 -0
- package/dist/adt/repository-relations.d.ts +41 -0
- package/dist/adt/repository-relations.d.ts.map +1 -0
- package/dist/adt/repository-relations.js +246 -0
- package/dist/adt/repository-relations.js.map +1 -0
- package/dist/adt/request-attempt-budget.d.ts +26 -0
- package/dist/adt/request-attempt-budget.d.ts.map +1 -0
- package/dist/adt/request-attempt-budget.js +63 -0
- package/dist/adt/request-attempt-budget.js.map +1 -0
- package/dist/adt/result-limits.d.ts +3 -0
- package/dist/adt/result-limits.d.ts.map +1 -0
- package/dist/adt/result-limits.js +7 -0
- package/dist/adt/result-limits.js.map +1 -0
- package/dist/adt/safety.d.ts +2 -0
- package/dist/adt/safety.d.ts.map +1 -1
- package/dist/adt/safety.js +6 -0
- package/dist/adt/safety.js.map +1 -1
- package/dist/adt/server-driven.d.ts +6 -1
- package/dist/adt/server-driven.d.ts.map +1 -1
- package/dist/adt/server-driven.js +24 -20
- package/dist/adt/server-driven.js.map +1 -1
- package/dist/adt/sql-source-analyzer.d.ts +12 -0
- package/dist/adt/sql-source-analyzer.d.ts.map +1 -0
- package/dist/adt/sql-source-analyzer.js +158 -0
- package/dist/adt/sql-source-analyzer.js.map +1 -0
- package/dist/adt/table-query.d.ts +43 -0
- package/dist/adt/table-query.d.ts.map +1 -0
- package/dist/adt/table-query.js +160 -0
- package/dist/adt/table-query.js.map +1 -0
- package/dist/adt/text-elements.d.ts +48 -0
- package/dist/adt/text-elements.d.ts.map +1 -0
- package/dist/adt/text-elements.js +116 -0
- package/dist/adt/text-elements.js.map +1 -0
- package/dist/adt/types.d.ts +16 -0
- package/dist/adt/types.d.ts.map +1 -1
- package/dist/adt/uiad.d.ts +19 -0
- package/dist/adt/uiad.d.ts.map +1 -0
- package/dist/adt/uiad.js +173 -0
- package/dist/adt/uiad.js.map +1 -0
- package/dist/adt/xml-parser.d.ts +12 -15
- package/dist/adt/xml-parser.d.ts.map +1 -1
- package/dist/adt/xml-parser.js +44 -12
- package/dist/adt/xml-parser.js.map +1 -1
- package/dist/authz/policy.d.ts.map +1 -1
- package/dist/authz/policy.js +4 -1
- package/dist/authz/policy.js.map +1 -1
- package/dist/cache/cache.d.ts +3 -23
- package/dist/cache/cache.d.ts.map +1 -1
- package/dist/cache/cache.js +2 -3
- package/dist/cache/cache.js.map +1 -1
- package/dist/cache/caching-layer.d.ts +6 -25
- package/dist/cache/caching-layer.d.ts.map +1 -1
- package/dist/cache/caching-layer.js +3 -45
- package/dist/cache/caching-layer.js.map +1 -1
- package/dist/cache/memory.d.ts +1 -4
- package/dist/cache/memory.d.ts.map +1 -1
- package/dist/cache/memory.js +1 -10
- package/dist/cache/memory.js.map +1 -1
- package/dist/cache/sqlite.d.ts +1 -3
- package/dist/cache/sqlite.d.ts.map +1 -1
- package/dist/cache/sqlite.js +2 -17
- package/dist/cache/sqlite.js.map +1 -1
- package/dist/cli-checks.d.ts +3 -0
- package/dist/cli-checks.d.ts.map +1 -1
- package/dist/cli-checks.js +16 -0
- package/dist/cli-checks.js.map +1 -1
- package/dist/cli.d.ts.map +1 -1
- package/dist/cli.js +7 -2
- package/dist/cli.js.map +1 -1
- package/dist/context/compressor.d.ts +2 -3
- package/dist/context/compressor.d.ts.map +1 -1
- package/dist/context/compressor.js +30 -49
- package/dist/context/compressor.js.map +1 -1
- package/dist/context/contract.d.ts +5 -0
- package/dist/context/contract.d.ts.map +1 -1
- package/dist/context/contract.js +2 -2
- package/dist/context/contract.js.map +1 -1
- package/dist/context/deps.d.ts +11 -0
- package/dist/context/deps.d.ts.map +1 -1
- package/dist/context/deps.js +2 -2
- package/dist/context/deps.js.map +1 -1
- package/dist/context/parse-cache.d.ts +23 -0
- package/dist/context/parse-cache.d.ts.map +1 -0
- package/dist/context/parse-cache.js +71 -0
- package/dist/context/parse-cache.js.map +1 -0
- package/dist/context/relation-walk.d.ts +48 -0
- package/dist/context/relation-walk.d.ts.map +1 -0
- package/dist/context/relation-walk.js +137 -0
- package/dist/context/relation-walk.js.map +1 -0
- package/dist/context/types.d.ts +4 -4
- package/dist/context/types.d.ts.map +1 -1
- package/dist/handlers/activate.d.ts +1 -1
- package/dist/handlers/activate.d.ts.map +1 -1
- package/dist/handlers/activate.js +33 -56
- package/dist/handlers/activate.js.map +1 -1
- package/dist/handlers/activation-results.d.ts +3 -0
- package/dist/handlers/activation-results.d.ts.map +1 -0
- package/dist/handlers/activation-results.js +8 -0
- package/dist/handlers/activation-results.js.map +1 -0
- package/dist/handlers/context.d.ts.map +1 -1
- package/dist/handlers/context.js +8 -32
- package/dist/handlers/context.js.map +1 -1
- package/dist/handlers/data-element-fields.d.ts +26 -0
- package/dist/handlers/data-element-fields.d.ts.map +1 -0
- package/dist/handlers/data-element-fields.js +27 -0
- package/dist/handlers/data-element-fields.js.map +1 -0
- package/dist/handlers/diagnose-ci.d.ts +9 -0
- package/dist/handlers/diagnose-ci.d.ts.map +1 -0
- package/dist/handlers/diagnose-ci.js +120 -0
- package/dist/handlers/diagnose-ci.js.map +1 -0
- package/dist/handlers/diagnose-fields.d.ts +51 -0
- package/dist/handlers/diagnose-fields.d.ts.map +1 -0
- package/dist/handlers/diagnose-fields.js +48 -0
- package/dist/handlers/diagnose-fields.js.map +1 -0
- package/dist/handlers/diagnose.d.ts +4 -1
- package/dist/handlers/diagnose.d.ts.map +1 -1
- package/dist/handlers/diagnose.js +41 -6
- package/dist/handlers/diagnose.js.map +1 -1
- package/dist/handlers/dispatch.d.ts +3 -1
- package/dist/handlers/dispatch.d.ts.map +1 -1
- package/dist/handlers/dispatch.js +96 -11
- package/dist/handlers/dispatch.js.map +1 -1
- package/dist/handlers/feature-cache.d.ts +4 -3
- package/dist/handlers/feature-cache.d.ts.map +1 -1
- package/dist/handlers/feature-cache.js +4 -3
- package/dist/handlers/feature-cache.js.map +1 -1
- package/dist/handlers/hyperfocused.js +1 -1
- package/dist/handlers/live-relations.d.ts +5 -0
- package/dist/handlers/live-relations.d.ts.map +1 -0
- package/dist/handlers/live-relations.js +89 -0
- package/dist/handlers/live-relations.js.map +1 -0
- package/dist/handlers/manage.d.ts.map +1 -1
- package/dist/handlers/manage.js +7 -4
- package/dist/handlers/manage.js.map +1 -1
- package/dist/handlers/navigate.d.ts +1 -1
- package/dist/handlers/navigate.d.ts.map +1 -1
- package/dist/handlers/navigate.js +33 -7
- package/dist/handlers/navigate.js.map +1 -1
- package/dist/handlers/object-types.d.ts +6 -4
- package/dist/handlers/object-types.d.ts.map +1 -1
- package/dist/handlers/object-types.js +45 -10
- package/dist/handlers/object-types.js.map +1 -1
- package/dist/handlers/query-errors.d.ts +9 -1
- package/dist/handlers/query-errors.d.ts.map +1 -1
- package/dist/handlers/query-errors.js +40 -28
- package/dist/handlers/query-errors.js.map +1 -1
- package/dist/handlers/query.d.ts +2 -2
- package/dist/handlers/query.d.ts.map +1 -1
- package/dist/handlers/query.js +15 -22
- package/dist/handlers/query.js.map +1 -1
- package/dist/handlers/read.d.ts +1 -1
- package/dist/handlers/read.d.ts.map +1 -1
- package/dist/handlers/read.js +112 -23
- package/dist/handlers/read.js.map +1 -1
- package/dist/handlers/relation-input.d.ts +42 -0
- package/dist/handlers/relation-input.d.ts.map +1 -0
- package/dist/handlers/relation-input.js +22 -0
- package/dist/handlers/relation-input.js.map +1 -0
- package/dist/handlers/relation-tool.d.ts +5 -0
- package/dist/handlers/relation-tool.d.ts.map +1 -0
- package/dist/handlers/relation-tool.js +36 -0
- package/dist/handlers/relation-tool.js.map +1 -0
- package/dist/handlers/schemas.d.ts +119 -62
- package/dist/handlers/schemas.d.ts.map +1 -1
- package/dist/handlers/schemas.js +150 -13
- package/dist/handlers/schemas.js.map +1 -1
- package/dist/handlers/search.d.ts +1 -1
- package/dist/handlers/search.d.ts.map +1 -1
- package/dist/handlers/search.js +43 -8
- package/dist/handlers/search.js.map +1 -1
- package/dist/handlers/tool-descriptions.d.ts.map +1 -1
- package/dist/handlers/tool-descriptions.js +12 -13
- package/dist/handlers/tool-descriptions.js.map +1 -1
- package/dist/handlers/tool-registry.d.ts +1 -0
- package/dist/handlers/tool-registry.d.ts.map +1 -1
- package/dist/handlers/tool-registry.js +4 -0
- package/dist/handlers/tool-registry.js.map +1 -1
- package/dist/handlers/tools.d.ts +2 -3
- package/dist/handlers/tools.d.ts.map +1 -1
- package/dist/handlers/tools.js +139 -84
- package/dist/handlers/tools.js.map +1 -1
- package/dist/handlers/where-used.d.ts +2 -0
- package/dist/handlers/where-used.d.ts.map +1 -1
- package/dist/handlers/where-used.js +23 -5
- package/dist/handlers/where-used.js.map +1 -1
- package/dist/handlers/write/batch-results.d.ts +28 -0
- package/dist/handlers/write/batch-results.d.ts.map +1 -0
- package/dist/handlers/write/batch-results.js +106 -0
- package/dist/handlers/write/batch-results.js.map +1 -0
- package/dist/handlers/write/create-transport.d.ts +7 -0
- package/dist/handlers/write/create-transport.d.ts.map +1 -0
- package/dist/handlers/write/create-transport.js +38 -0
- package/dist/handlers/write/create-transport.js.map +1 -0
- package/dist/handlers/write/create.d.ts.map +1 -1
- package/dist/handlers/write/create.js +276 -413
- package/dist/handlers/write/create.js.map +1 -1
- package/dist/handlers/write/uiad.d.ts +8 -0
- package/dist/handlers/write/uiad.d.ts.map +1 -0
- package/dist/handlers/write/uiad.js +115 -0
- package/dist/handlers/write/uiad.js.map +1 -0
- package/dist/handlers/write/update-delete.d.ts +6 -6
- package/dist/handlers/write/update-delete.d.ts.map +1 -1
- package/dist/handlers/write/update-delete.js +46 -15
- package/dist/handlers/write/update-delete.js.map +1 -1
- package/dist/handlers/write-helpers.d.ts +0 -6
- package/dist/handlers/write-helpers.d.ts.map +1 -1
- package/dist/handlers/write-helpers.js +88 -80
- package/dist/handlers/write-helpers.js.map +1 -1
- package/dist/handlers/write.d.ts.map +1 -1
- package/dist/handlers/write.js +5 -1
- package/dist/handlers/write.js.map +1 -1
- package/dist/public/index.d.ts +1 -1
- package/dist/public/index.d.ts.map +1 -1
- package/dist/public/index.js +1 -1
- package/dist/public/index.js.map +1 -1
- package/dist/public/ui/app.js +0 -2
- package/dist/server/audit.d.ts +42 -1
- package/dist/server/audit.d.ts.map +1 -1
- package/dist/server/audit.js.map +1 -1
- package/dist/server/config.d.ts +4 -0
- package/dist/server/config.d.ts.map +1 -1
- package/dist/server/config.js +67 -0
- package/dist/server/config.js.map +1 -1
- package/dist/server/context.d.ts +5 -0
- package/dist/server/context.d.ts.map +1 -1
- package/dist/server/context.js.map +1 -1
- package/dist/server/destination-registry.d.ts +10 -2
- package/dist/server/destination-registry.d.ts.map +1 -1
- package/dist/server/destination-registry.js +12 -3
- package/dist/server/destination-registry.js.map +1 -1
- package/dist/server/effective-policy-log.d.ts +2 -1
- package/dist/server/effective-policy-log.d.ts.map +1 -1
- package/dist/server/effective-policy-log.js +18 -2
- package/dist/server/effective-policy-log.js.map +1 -1
- package/dist/server/http.d.ts +1 -1
- package/dist/server/http.d.ts.map +1 -1
- package/dist/server/http.js +1 -0
- package/dist/server/http.js.map +1 -1
- package/dist/server/logger.d.ts.map +1 -1
- package/dist/server/logger.js +4 -1
- package/dist/server/logger.js.map +1 -1
- package/dist/server/multi-target-runtime.d.ts.map +1 -1
- package/dist/server/multi-target-runtime.js +7 -2
- package/dist/server/multi-target-runtime.js.map +1 -1
- package/dist/server/multi-target-tools.d.ts.map +1 -1
- package/dist/server/multi-target-tools.js +3 -1
- package/dist/server/multi-target-tools.js.map +1 -1
- package/dist/server/runtime-memory.d.ts +13 -0
- package/dist/server/runtime-memory.d.ts.map +1 -0
- package/dist/server/runtime-memory.js +42 -0
- package/dist/server/runtime-memory.js.map +1 -0
- package/dist/server/server-instructions.d.ts +2 -0
- package/dist/server/server-instructions.d.ts.map +1 -0
- package/dist/server/server-instructions.js +33 -0
- package/dist/server/server-instructions.js.map +1 -0
- package/dist/server/server.d.ts +3 -2
- package/dist/server/server.d.ts.map +1 -1
- package/dist/server/server.js +42 -78
- package/dist/server/server.js.map +1 -1
- package/dist/server/shutdown.d.ts +6 -0
- package/dist/server/shutdown.d.ts.map +1 -0
- package/dist/server/shutdown.js +52 -0
- package/dist/server/shutdown.js.map +1 -0
- package/dist/server/sinks/btp-auditlog.d.ts +10 -8
- package/dist/server/sinks/btp-auditlog.d.ts.map +1 -1
- package/dist/server/sinks/btp-auditlog.js +86 -68
- package/dist/server/sinks/btp-auditlog.js.map +1 -1
- package/dist/server/sinks/file.d.ts +1 -1
- package/dist/server/sinks/file.d.ts.map +1 -1
- package/dist/server/sinks/file.js +12 -21
- package/dist/server/sinks/file.js.map +1 -1
- package/dist/server/types.d.ts +8 -0
- package/dist/server/types.d.ts.map +1 -1
- package/dist/server/types.js +4 -0
- package/dist/server/types.js.map +1 -1
- package/dist/server/ui-state.d.ts.map +1 -1
- package/dist/server/ui-state.js +1 -0
- package/dist/server/ui-state.js.map +1 -1
- package/dist/server/ui.js +0 -2
- package/dist/server/ui.js.map +1 -1
- package/package.json +15 -13
package/README.md
CHANGED
|
@@ -8,7 +8,9 @@ ARC-1 connects AI assistants (Claude, GitHub Copilot, Copilot Studio, and any MC
|
|
|
8
8
|
[](https://github.com/arc-mcp/arc-1/security/code-scanning)
|
|
9
9
|
[](https://github.com/arc-mcp/arc-1/actions/workflows/dependency-review.yml)
|
|
10
10
|
|
|
11
|
-
**[Full Documentation](https://docs.arc-1-mcp.com/)** | **[Quickstart](https://docs.arc-1-mcp.com/quickstart/)** | **[Tool Reference](https://docs.arc-1-mcp.com/tools/)** | **[Blog Series](https://blog.zeis.de/tags/ai-abap-development-series/)**
|
|
11
|
+
**[Full Documentation](https://docs.arc-1-mcp.com/)** | **[Quickstart](https://docs.arc-1-mcp.com/quickstart/)** | **[Tool Reference](https://docs.arc-1-mcp.com/tools/)** | **[ARC-1 Updates](https://docs.arc-1-mcp.com/newsletter/)** | **[Blog Series](https://blog.zeis.de/tags/ai-abap-development-series/)**
|
|
12
|
+
|
|
13
|
+
> 📬 **Stay current with ARC-1** — get major releases, upgrade and security notes, practical guides, and occasional questions where your feedback can shape what comes next. **[Join ARC-1 Updates →](https://docs.arc-1-mcp.com/newsletter/)**
|
|
12
14
|
|
|
13
15
|
> 📖 **New: AI ABAP Development blog series** — long-form posts on AI for ABAP, ARC-1 design, and real-world BTP / Copilot Studio / Joule walkthroughs. **[Read the series →](https://blog.zeis.de/tags/ai-abap-development-series/)**
|
|
14
16
|
|
|
@@ -22,6 +24,7 @@ Built for organizations that need AI-assisted SAP development with guardrails. I
|
|
|
22
24
|
- **Action deny list** — block specific tool actions with `SAP_DENY_ACTIONS` (for example `SAPWrite.delete`), without exposing low-level operation codes to admins
|
|
23
25
|
- **Package restrictions** — limit AI write operations (create, update, delete) to specific packages with wildcards (`--allowed-packages "Z*,$TMP"`). Read operations are not restricted by package — use SAP's native authorization for read-level access control
|
|
24
26
|
- **Data access control (off by default)** — `SAPRead(type=TABLE_CONTENTS)` and `SAPQuery` are gated behind explicit env vars (`SAP_ALLOW_DATA_PREVIEW=true`, `SAP_ALLOW_FREE_SQL=true`). These capabilities can expose application data or run ad-hoc SQL, so they are intentionally separated from the default development-tooling surface. They can be enabled for governed use cases, but should be reviewed against the [SAP API Policy](docs_page/sap-api-policy-and-architecture.md), your SAP agreement, and internal data-governance rules
|
|
27
|
+
- **Experimental data-source emergency brake** — approved data/SQL deployments can set `SAP_BLOCKED_DATA_SOURCES=USR02,PA0002`. ARC-1 then parses each SQL request and resolves active CDS plus replacement-object lineage before execution, denying direct or transitive exact-name matches and failing closed when lineage is unsupported or cannot be proven. The empty default adds no metadata calls. This denylist is defense in depth, not a production allowlist or replacement for SAP authorization/CDS DCL; see [Authorization & Roles](docs_page/authorization.md#experimental-data-source-blocklist).
|
|
25
28
|
- **Transport safety** — transport reads are available for review, while transport mutations require both `--allow-writes` and `--allow-transport-writes`. Update/delete operations auto-use the lock correction number when no explicit transport is provided
|
|
26
29
|
- **Git workflow safety** — Git operations are disabled by default. Enable explicitly with `--allow-git-writes` / `SAP_ALLOW_GIT_WRITES=true`
|
|
27
30
|
- **API-key profiles** — multi-key HTTP deployments can assign `viewer`, `viewer-data`, `viewer-sql`, `developer`, `developer-data`, `developer-sql`, or `admin` per key
|
|
@@ -57,13 +60,13 @@ Deploy ARC-1 as a Cloud Foundry app on SAP BTP with full platform integration:
|
|
|
57
60
|
|
|
58
61
|
- **12 intent-based tools** instead of 200+ individual tools — keeps tool selection simple, with the schema payload guarded by CI budgets and a hyperfocused 1-tool mode for tight context windows
|
|
59
62
|
- **Method-level read/edit** — read or update a single class method, not the whole source (up to 20x fewer tokens)
|
|
60
|
-
- **
|
|
63
|
+
- **Focused source and dependency context** — use targeted `SAPRead` for exact implementation behavior. For business purpose, reviews or test design, start with `SAPContext(action="deps", type=..., name=...)` for available Knowledge Transfer Documents (`SKTD`/`KTD`) and dependency contracts, then compare requirements with source. Without documented requirements, intent is unverified.
|
|
61
64
|
|
|
62
65
|
### Built-in Object Caching
|
|
63
66
|
|
|
64
67
|
- **Server-validated source caching** — every SAP object read is cached in memory (stdio) or SQLite (http-streamable). Repeated reads use `If-None-Match`/ETag conditional GET, so unchanged objects return from cache after SAP confirms `304 Not Modified`.
|
|
65
|
-
- **Dependency
|
|
66
|
-
- **KTD-aware context** — Knowledge Transfer Documents
|
|
68
|
+
- **Dependency parsing reuse** — unchanged, authorized source can reuse parsed dependencies and contracts in memory. Aggregate dependency graphs are not cached; SAP authorization and source validation still apply.
|
|
69
|
+
- **KTD-aware context** — Knowledge Transfer Documents use the source cache and are revalidated when composed into `SAPContext(action="deps")`.
|
|
67
70
|
- **Live where-used** — `SAPContext(action="usages")` and CDS impact analysis query SAP's current repository index with the caller's identity; no startup repository scan is required.
|
|
68
71
|
- **Active/inactive source views** — `SAPRead` accepts `version="active" | "inactive" | "auto"` and warns when the active source has an unactivated draft.
|
|
69
72
|
- **Write invalidation** — when `SAPWrite` or `SAPActivate` mutates an object, both active and inactive source cache entries are dropped; next read revalidates or fetches fresh source.
|
|
@@ -94,7 +97,7 @@ The 12 tools are designed from real LLM interaction feedback:
|
|
|
94
97
|
| **SAPQuery** | Execute ABAP SQL with table-not-found suggestions and automatic chunking for simple long literal `IN (...)` lists |
|
|
95
98
|
| **SAPTransport** | CTS transport management (list/get/create/release/delete/reassign/release-recursive), transport layer/target lookup, package transport requirement checks, and reverse lookup history (`action="history"`) |
|
|
96
99
|
| **SAPGit** | Git-based ABAP workflows across gCTS and abapGit (list/clone/pull/push/commit/branch/unlink) with backend auto-selection and safety gating (`--allow-git-writes`) |
|
|
97
|
-
| **SAPContext** |
|
|
100
|
+
| **SAPContext** | Dependency APIs (`action="deps"`): optional KTD plus bounded source-derived contracts, not a complete relationship inventory. Also supports live where-used (`action="usages"`), CDS impact (`action="impact"`), and TABL includes/appends (`action="structure"`) |
|
|
98
101
|
| **SAPLint** | Local ABAP lint (system/release-aware presets, auto-fix, pre-write validation) + ADT PrettyPrint (server-side formatting) |
|
|
99
102
|
| **SAPDiagnose** | Syntax check, ABAP Unit tests, ATC code quality, CDS test-case suggestions, active/inactive object-state comparison, generic ADT quickfix proposals/application deltas, gateway/system message diagnostics, short dumps, profiler traces, and the on-prem authorization trace (`SUAUTHVALTRC`, data-preview gated) |
|
|
100
103
|
| **SAPManage** | Feature probing, cache statistics, package lifecycle/change-package operations, and FLP catalog/group/tile helpers |
|
|
@@ -130,6 +133,13 @@ Two ARC-1 capabilities can expose business data or execute ad-hoc SQL. Both are
|
|
|
130
133
|
| ---------- | ------- | ------- | ----------- |
|
|
131
134
|
| Named table content preview (`SAPRead(type=TABLE_CONTENTS)`) | `SAP_ALLOW_DATA_PREVIEW=true` | `false` (off) | Can expose application-table data; keep off unless the use case is approved. |
|
|
132
135
|
| Freestyle ABAP SQL (`SAPQuery`) | `SAP_ALLOW_FREE_SQL=true` | `false` (off) | Executes ad-hoc ABAP SQL; keep off unless the use case is approved. |
|
|
136
|
+
| Exact source blocklist (experimental) | `SAP_BLOCKED_DATA_SOURCES=USR02,PA0002` | empty (off) | Denies exact direct/transitive table or CDS dependencies; active mode is deliberately fail-closed and slower. |
|
|
137
|
+
|
|
138
|
+
When either capability is enabled, successful data-preview bodies are limited cumulatively per tool
|
|
139
|
+
call (2 MiB by default), and only two data-result calls per process remain admitted through parsing
|
|
140
|
+
and serialization. `SAPQuery.maxRows` is separately clamped to 10,000, but wide rows can reach the
|
|
141
|
+
byte limit much earlier. See [Configuration](docs_page/configuration-reference.md) before tuning
|
|
142
|
+
`ARC1_MAX_DATAPREVIEW_RESPONSE_BYTES` or `ARC1_MAX_CONCURRENT_DATA_RESULTS`.
|
|
133
143
|
|
|
134
144
|
With both flags at their defaults, ARC-1's data/sql rows are unreachable. Turning either flag on is a valid operational choice for approved scenarios, but it should be deliberate: check the current SAP API Policy, the customer's SAP agreement, SAP authorizations, and internal data-protection rules before enabling it on a productive system.
|
|
135
145
|
|
|
@@ -139,7 +149,7 @@ ARC-1's strategy is to stay close to documented and discoverable ADT behavior, p
|
|
|
139
149
|
|
|
140
150
|
From `1.0` onward ARC-1 follows [semantic versioning](https://semver.org/): patch releases fix bugs, minor releases add backward-compatible capability, and breaking changes to the MCP tool surface, configuration, or auth contract bump the major version.
|
|
141
151
|
|
|
142
|
-
**Experimental, default-off features are excluded from this guarantee until they are promoted** — they are clearly labeled and their surface may still change in a minor release. Today this covers the [multi-target BTP mode](docs_page/multi-target-setup.md) (ADR-0006 / ADR-0007)
|
|
152
|
+
**Experimental, default-off features are excluded from this guarantee until they are promoted** — they are clearly labeled and their surface may still change in a minor release. Today this covers the [multi-target BTP mode](docs_page/multi-target-setup.md) (ADR-0006 / ADR-0007) and the [data-source blocklist](docs_page/authorization.md#experimental-data-source-blocklist).
|
|
143
153
|
|
|
144
154
|
What changed per release: the annotated [Release Notes](https://docs.arc-1-mcp.com/release-notes/) give each release its impact and upgrade action; [CHANGELOG.md](CHANGELOG.md) lists every merged PR.
|
|
145
155
|
|
package/bin/start-cf.sh
ADDED
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
#!/bin/sh
|
|
2
|
+
set -eu
|
|
3
|
+
|
|
4
|
+
if [ "${OPTIMIZE_MEMORY:-}" != "true" ]; then
|
|
5
|
+
exec node dist/index.js
|
|
6
|
+
fi
|
|
7
|
+
|
|
8
|
+
memory_available=${MEMORY_AVAILABLE:-}
|
|
9
|
+
case "$memory_available" in
|
|
10
|
+
''|*[!0-9]*)
|
|
11
|
+
echo "ARC-1 startup refused: OPTIMIZE_MEMORY=true requires MEMORY_AVAILABLE as decimal MiB." >&2
|
|
12
|
+
exit 1
|
|
13
|
+
;;
|
|
14
|
+
esac
|
|
15
|
+
|
|
16
|
+
# Avoid octal interpretation and arithmetic overflow in POSIX shells. CF values
|
|
17
|
+
# are vastly smaller than this nine-digit upper bound.
|
|
18
|
+
while [ "${memory_available#0}" != "$memory_available" ]; do
|
|
19
|
+
memory_available=${memory_available#0}
|
|
20
|
+
done
|
|
21
|
+
if [ -z "$memory_available" ] || [ "${#memory_available}" -gt 9 ]; then
|
|
22
|
+
echo "ARC-1 startup refused: MEMORY_AVAILABLE is outside the supported decimal-MiB range." >&2
|
|
23
|
+
exit 1
|
|
24
|
+
fi
|
|
25
|
+
|
|
26
|
+
old_space_mib=$((memory_available / 4 * 3 + memory_available % 4 * 3 / 4))
|
|
27
|
+
if [ "$old_space_mib" -lt 1 ]; then
|
|
28
|
+
echo "ARC-1 startup refused: MEMORY_AVAILABLE is too small for the 75% old-space policy." >&2
|
|
29
|
+
exit 1
|
|
30
|
+
fi
|
|
31
|
+
|
|
32
|
+
exec node "--max-old-space-size=${old_space_mib}" dist/index.js
|
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
import { type AtcObjectIdentity, type AtcPollOptions } from './atc.js';
|
|
2
|
+
import type { AdtHttpClient } from './http.js';
|
|
3
|
+
import type { SafetyConfig } from './safety.js';
|
|
4
|
+
export declare function atcDdicObjectUrl(type: string, name: string): string | undefined;
|
|
5
|
+
export declare const ATC_BATCH_TYPES: readonly ["CLAS", "INTF", "PROG", "FUGR", "DDLS", "DCLS", "BDEF", "DDLX", "SRVD", "SRVB", "TABL", "DTEL", "DOMA"];
|
|
6
|
+
export declare const ATC_BATCH_MAX_OBJECTS = 20;
|
|
7
|
+
export declare const ATC_BATCH_NAME_PATTERN = "^(?:/[A-Za-z0-9_]+/)?[A-Za-z0-9_]+$";
|
|
8
|
+
export declare const ATC_BATCH_NAME_MAX_LENGTH = 40;
|
|
9
|
+
export interface AtcBatchObject extends AtcObjectIdentity {
|
|
10
|
+
type: (typeof ATC_BATCH_TYPES)[number];
|
|
11
|
+
}
|
|
12
|
+
interface AtcObjectCoverage extends AtcObjectIdentity {
|
|
13
|
+
status: 'reported' | 'notReported';
|
|
14
|
+
/** Unknown for missing or incomplete evidence; never synthesize a clean result. */
|
|
15
|
+
findingCount: number | null;
|
|
16
|
+
worklistId: string | null;
|
|
17
|
+
}
|
|
18
|
+
export declare function runAtcBatch(http: AdtHttpClient, safety: SafetyConfig, objects: readonly AtcBatchObject[], variant?: string, pollOptions?: AtcPollOptions): Promise<{
|
|
19
|
+
complete: boolean;
|
|
20
|
+
variant: string | null;
|
|
21
|
+
variantSource: import("./atc.js").AtcVariantSource;
|
|
22
|
+
requestedObjectCount: number;
|
|
23
|
+
uniqueObjectCount: number;
|
|
24
|
+
reportedObjectCount: number;
|
|
25
|
+
coverage: AtcObjectCoverage[];
|
|
26
|
+
findings: {
|
|
27
|
+
priority: number;
|
|
28
|
+
checkTitle: string;
|
|
29
|
+
messageTitle: string;
|
|
30
|
+
uri: string;
|
|
31
|
+
line: number;
|
|
32
|
+
quickfixInfo?: string;
|
|
33
|
+
hasQuickfix?: boolean;
|
|
34
|
+
object?: {
|
|
35
|
+
type: string;
|
|
36
|
+
name: string;
|
|
37
|
+
} | undefined;
|
|
38
|
+
worklistId: string;
|
|
39
|
+
}[];
|
|
40
|
+
findingCount: number;
|
|
41
|
+
verificationAttempted: boolean;
|
|
42
|
+
incompleteReasons: string[];
|
|
43
|
+
runs: {
|
|
44
|
+
worklistId: string;
|
|
45
|
+
variant: string | null;
|
|
46
|
+
variantSource: import("./atc.js").AtcVariantSource;
|
|
47
|
+
maximumVerdicts: number;
|
|
48
|
+
expectedFindingCount: number | null;
|
|
49
|
+
findingStatistics: import("./atc.js").AtcFindingStatistics | null;
|
|
50
|
+
findingCount: number;
|
|
51
|
+
processedObjectCount: number;
|
|
52
|
+
objectSetIsComplete: boolean | null;
|
|
53
|
+
truncated: boolean;
|
|
54
|
+
complete: boolean;
|
|
55
|
+
completionEvidence: import("./atc.js").AtcCompletionEvidence | null;
|
|
56
|
+
incompleteReasons: string[];
|
|
57
|
+
runStatusCode: number;
|
|
58
|
+
runStatus: string | null;
|
|
59
|
+
runInfos: import("./atc.js").AtcRunInfo[];
|
|
60
|
+
worklist: {
|
|
61
|
+
id: string;
|
|
62
|
+
timestamp?: string;
|
|
63
|
+
usedObjectSet?: string;
|
|
64
|
+
status?: string;
|
|
65
|
+
};
|
|
66
|
+
infos: string[];
|
|
67
|
+
excludedFindingCount: number;
|
|
68
|
+
}[];
|
|
69
|
+
}>;
|
|
70
|
+
export {};
|
|
71
|
+
//# sourceMappingURL=atc-batch.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"atc-batch.d.ts","sourceRoot":"","sources":["../../src/adt/atc-batch.ts"],"names":[],"mappings":"AAIA,OAAO,EAEL,KAAK,iBAAiB,EACtB,KAAK,cAAc,EAIpB,MAAM,UAAU,CAAC;AAElB,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,WAAW,CAAC;AAE/C,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,aAAa,CAAC;AAMhD,wBAAgB,gBAAgB,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS,CAI/E;AAGD,eAAO,MAAM,eAAe,mHAYlB,CAAC;AACX,eAAO,MAAM,qBAAqB,KAAK,CAAC;AACxC,eAAO,MAAM,sBAAsB,wCAAwC,CAAC;AAC5E,eAAO,MAAM,yBAAyB,KAAK,CAAC;AAG5C,MAAM,WAAW,cAAe,SAAQ,iBAAiB;IACvD,IAAI,EAAE,CAAC,OAAO,eAAe,CAAC,CAAC,MAAM,CAAC,CAAC;CACxC;AAED,UAAU,iBAAkB,SAAQ,iBAAiB;IACnD,MAAM,EAAE,UAAU,GAAG,aAAa,CAAC;IACnC,mFAAmF;IACnF,YAAY,EAAE,MAAM,GAAG,IAAI,CAAC;IAC5B,UAAU,EAAE,MAAM,GAAG,IAAI,CAAC;CAC3B;AAsFD,wBAAsB,WAAW,CAC/B,IAAI,EAAE,aAAa,EACnB,MAAM,EAAE,YAAY,EACpB,OAAO,EAAE,SAAS,cAAc,EAAE,EAClC,OAAO,CAAC,EAAE,MAAM,EAChB,WAAW,GAAE,cAAmB;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA+GjC"}
|
|
@@ -0,0 +1,182 @@
|
|
|
1
|
+
/** Native ATC batches with explicit requested-object coverage and one bounded verification run. */
|
|
2
|
+
import { normalizeObjectType, objectUrlForType } from '../handlers/object-types.js';
|
|
3
|
+
import { getCurrentContext } from '../server/context.js';
|
|
4
|
+
import { logger } from '../server/logger.js';
|
|
5
|
+
import { ATC_SETTLE_QUIET_MS, prepareAtcExecution, runAtcWorklist, } from './atc.js';
|
|
6
|
+
import { AdtApiError, AdtNetworkError } from './errors.js';
|
|
7
|
+
import { canonicalHostRelativeAdtPath } from './path-safety.js';
|
|
8
|
+
// DDIC uses ATC's own R3TR reference: TABL covers both tables and structures,
|
|
9
|
+
// including releases without the /ddic/tables editor. No subtype lookup is needed.
|
|
10
|
+
const ATC_DDIC_BATCH_TYPES = ['TABL', 'DTEL', 'DOMA'];
|
|
11
|
+
export function atcDdicObjectUrl(type, name) {
|
|
12
|
+
return ATC_DDIC_BATCH_TYPES.some((candidate) => candidate === type)
|
|
13
|
+
? `/sap/bc/adt/atc/objects/R3TR/${type}/${encodeURIComponent(name)}`
|
|
14
|
+
: undefined;
|
|
15
|
+
}
|
|
16
|
+
// Other object-root routes need no parent/group resolution.
|
|
17
|
+
export const ATC_BATCH_TYPES = [
|
|
18
|
+
'CLAS',
|
|
19
|
+
'INTF',
|
|
20
|
+
'PROG',
|
|
21
|
+
'FUGR',
|
|
22
|
+
'DDLS',
|
|
23
|
+
'DCLS',
|
|
24
|
+
'BDEF',
|
|
25
|
+
'DDLX',
|
|
26
|
+
'SRVD',
|
|
27
|
+
'SRVB',
|
|
28
|
+
...ATC_DDIC_BATCH_TYPES,
|
|
29
|
+
];
|
|
30
|
+
export const ATC_BATCH_MAX_OBJECTS = 20;
|
|
31
|
+
export const ATC_BATCH_NAME_PATTERN = '^(?:/[A-Za-z0-9_]+/)?[A-Za-z0-9_]+$';
|
|
32
|
+
export const ATC_BATCH_NAME_MAX_LENGTH = 40;
|
|
33
|
+
const ATC_BATCH_NAME_REGEX = new RegExp(ATC_BATCH_NAME_PATTERN);
|
|
34
|
+
function objectKey(object) {
|
|
35
|
+
// Explicit aliases distinguish FUGR/F (group) from FUGR/FF (function module).
|
|
36
|
+
return `${normalizeObjectType(object.type)}:${object.name.replace(/[a-z]/g, (char) => char.toUpperCase())}`;
|
|
37
|
+
}
|
|
38
|
+
function sameObject(requested, reported) {
|
|
39
|
+
if (objectKey(requested) !== objectKey(reported))
|
|
40
|
+
return false;
|
|
41
|
+
const root = objectUrlForType(requested.type, requested.name);
|
|
42
|
+
const candidates = [
|
|
43
|
+
requested.uri,
|
|
44
|
+
root,
|
|
45
|
+
`/sap/bc/adt/atc/objects/R3TR/${requested.type}/${encodeURIComponent(requested.name)}`,
|
|
46
|
+
];
|
|
47
|
+
if (requested.type === 'TABL') {
|
|
48
|
+
const structure = objectUrlForType('TABL/DS', requested.name);
|
|
49
|
+
candidates.push(structure, `${root}/source/main`, `${structure}/source/main`);
|
|
50
|
+
}
|
|
51
|
+
else if (!atcDdicObjectUrl(requested.type, requested.name) && requested.type !== 'SRVB')
|
|
52
|
+
candidates.push(`${root}/source/main`);
|
|
53
|
+
// ABAP names and percent-hex case are equivalent; SAP emits %2f. Accept only
|
|
54
|
+
// exact known object roots/source-main, including the literal namespace form.
|
|
55
|
+
return candidates.some((candidate) => [candidate, candidate.replace(encodeURIComponent(requested.name), requested.name)].some((uri) => uri.toLowerCase() === reported.uri.toLowerCase()));
|
|
56
|
+
}
|
|
57
|
+
function reconcile(objects, runs) {
|
|
58
|
+
return objects.map((object) => {
|
|
59
|
+
for (const run of runs) {
|
|
60
|
+
const rows = run.processedObjects?.filter((row) => sameObject(object, row)) ?? [];
|
|
61
|
+
if (rows.length === 0)
|
|
62
|
+
continue;
|
|
63
|
+
return {
|
|
64
|
+
...object,
|
|
65
|
+
status: 'reported',
|
|
66
|
+
findingCount: run.complete && rows.length === 1 ? rows[0].findingCount : null,
|
|
67
|
+
worklistId: run.worklistId,
|
|
68
|
+
};
|
|
69
|
+
}
|
|
70
|
+
return { ...object, status: 'notReported', findingCount: null, worklistId: null };
|
|
71
|
+
});
|
|
72
|
+
}
|
|
73
|
+
function reviewBatchEvidence(run, selection) {
|
|
74
|
+
const keys = (run.processedObjects ?? []).map(objectKey);
|
|
75
|
+
if (new Set(keys).size !== keys.length) {
|
|
76
|
+
run.complete = false;
|
|
77
|
+
run.incompleteReasons.push('SAP reported duplicate ATC object identities.');
|
|
78
|
+
}
|
|
79
|
+
if (run.findings.some((finding) => !finding.object)) {
|
|
80
|
+
run.complete = false;
|
|
81
|
+
run.incompleteReasons.push('Some ATC findings have no valid enclosing object identity.');
|
|
82
|
+
}
|
|
83
|
+
if ((run.processedObjects ?? []).some((row) => selection.some((object) => objectKey(object) === objectKey(row) && !sameObject(object, row)))) {
|
|
84
|
+
run.complete = false;
|
|
85
|
+
run.incompleteReasons.push('SAP returned an object URI inconsistent with the requested identity.');
|
|
86
|
+
}
|
|
87
|
+
// FUNC/INCL and other non-root records may belong to a requested container.
|
|
88
|
+
// Without parent evidence, preserve them and refuse a verified clean count.
|
|
89
|
+
const unassignedKeys = new Set((run.processedObjects ?? [])
|
|
90
|
+
.filter((object) => !ATC_BATCH_TYPES.some((type) => type === normalizeObjectType(object.type)))
|
|
91
|
+
.map(objectKey));
|
|
92
|
+
if (unassignedKeys.size > 0) {
|
|
93
|
+
run.complete = false;
|
|
94
|
+
run.incompleteReasons.push('SAP reported unassigned sub-object or unsupported object records; their findings are retained.');
|
|
95
|
+
}
|
|
96
|
+
// Exclude other supported roots, including previously checked roots repeated
|
|
97
|
+
// in verification. Unassigned records cannot safely be classified as unrelated.
|
|
98
|
+
const selectedKeys = new Set(selection.map(objectKey));
|
|
99
|
+
const selectedFindings = run.findings.filter((finding) => !finding.object || selectedKeys.has(objectKey(finding.object)) || unassignedKeys.has(objectKey(finding.object)));
|
|
100
|
+
return { ...run, selectedFindings, excludedFindingCount: run.findings.length - selectedFindings.length };
|
|
101
|
+
}
|
|
102
|
+
export async function runAtcBatch(http, safety, objects, variant, pollOptions = {}) {
|
|
103
|
+
// Validate at the executor boundary too; the public tool applies the same limits before routing.
|
|
104
|
+
if (objects.length < 1 ||
|
|
105
|
+
objects.length > ATC_BATCH_MAX_OBJECTS ||
|
|
106
|
+
objects.some((object) => !ATC_BATCH_TYPES.includes(object.type) ||
|
|
107
|
+
object.name.length > ATC_BATCH_NAME_MAX_LENGTH ||
|
|
108
|
+
!ATC_BATCH_NAME_REGEX.test(object.name) ||
|
|
109
|
+
!canonicalHostRelativeAdtPath(object.uri, '/sap/bc/adt/', { allowRawEncodedSlash: true }) ||
|
|
110
|
+
object.uri.includes('?')))
|
|
111
|
+
throw new Error('Invalid ATC batch selection.');
|
|
112
|
+
const selected = [...new Map(objects.map((object) => [objectKey(object), object])).values()];
|
|
113
|
+
const execution = await prepareAtcExecution(http, safety, variant, pollOptions);
|
|
114
|
+
const runs = [
|
|
115
|
+
reviewBatchEvidence(await runAtcWorklist(http, safety, selected.map((object) => object.uri), execution, true), selected),
|
|
116
|
+
];
|
|
117
|
+
let coverage = reconcile(selected, runs);
|
|
118
|
+
const missing = selected.filter((_object, index) => coverage[index].status === 'notReported');
|
|
119
|
+
const incompleteReasons = [];
|
|
120
|
+
let verificationAttempted = false;
|
|
121
|
+
if (runs[0].complete && missing.length > 0) {
|
|
122
|
+
if (!execution.variant || execution.variantSource === 'requestedUnverified') {
|
|
123
|
+
incompleteReasons.push('Verification was skipped because the effective check variant could not be confirmed.');
|
|
124
|
+
}
|
|
125
|
+
else if (pollOptions.signal?.aborted || (pollOptions.now ?? Date.now)() >= execution.requestOptions.deadline) {
|
|
126
|
+
incompleteReasons.push('Verification was skipped because the request was cancelled or its deadline expired.');
|
|
127
|
+
}
|
|
128
|
+
else if (runs[0].completionEvidence === 'legacyWorklistSettled' &&
|
|
129
|
+
execution.requestOptions.deadline - (pollOptions.now ?? Date.now)() <= ATC_SETTLE_QUIET_MS) {
|
|
130
|
+
incompleteReasons.push('Verification was skipped because the remaining deadline cannot cover legacy worklist settlement.');
|
|
131
|
+
}
|
|
132
|
+
else {
|
|
133
|
+
verificationAttempted = true;
|
|
134
|
+
try {
|
|
135
|
+
runs.push(reviewBatchEvidence(await runAtcWorklist(http, safety, missing.map((object) => object.uri), execution, true), missing));
|
|
136
|
+
}
|
|
137
|
+
catch (error) {
|
|
138
|
+
if (pollOptions.signal?.aborted ||
|
|
139
|
+
(error instanceof AdtNetworkError && error.cause?.name === 'AbortError') ||
|
|
140
|
+
!(error instanceof AdtApiError || error instanceof AdtNetworkError))
|
|
141
|
+
throw error;
|
|
142
|
+
logger.warn('ATC verification failed; initial findings retained.', {
|
|
143
|
+
requestId: getCurrentContext()?.requestId,
|
|
144
|
+
worklistId: runs[0].worklistId,
|
|
145
|
+
errorClass: error.name,
|
|
146
|
+
...(error instanceof AdtApiError ? { statusCode: error.statusCode } : {}),
|
|
147
|
+
});
|
|
148
|
+
incompleteReasons.push('ATC verification could not be completed; initial findings are retained.');
|
|
149
|
+
}
|
|
150
|
+
coverage = reconcile(selected, runs);
|
|
151
|
+
}
|
|
152
|
+
}
|
|
153
|
+
for (const run of runs)
|
|
154
|
+
incompleteReasons.push(...run.incompleteReasons.map((reason) => `${run.worklistId}: ${reason}`));
|
|
155
|
+
const unreportedCount = coverage.filter((object) => object.status === 'notReported').length;
|
|
156
|
+
if (unreportedCount > 0)
|
|
157
|
+
incompleteReasons.push(`SAP did not report ${unreportedCount} requested object(s); their findings are unknown.`);
|
|
158
|
+
if (coverage.some((object) => object.status === 'reported' && object.findingCount === null)) {
|
|
159
|
+
incompleteReasons.push('Finding counts remain unknown for objects from an incomplete run.');
|
|
160
|
+
}
|
|
161
|
+
const findings = runs.flatMap((run) => run.selectedFindings.map(({ object, ...finding }) => ({
|
|
162
|
+
...finding,
|
|
163
|
+
...(object ? { object: { type: normalizeObjectType(object.type), name: object.name } } : {}),
|
|
164
|
+
worklistId: run.worklistId,
|
|
165
|
+
})));
|
|
166
|
+
return {
|
|
167
|
+
complete: incompleteReasons.length === 0 && runs.every((run) => run.complete),
|
|
168
|
+
variant: execution.variant ?? null,
|
|
169
|
+
variantSource: execution.variantSource,
|
|
170
|
+
requestedObjectCount: objects.length,
|
|
171
|
+
uniqueObjectCount: selected.length,
|
|
172
|
+
reportedObjectCount: coverage.length - unreportedCount,
|
|
173
|
+
coverage,
|
|
174
|
+
findings,
|
|
175
|
+
findingCount: findings.length,
|
|
176
|
+
verificationAttempted,
|
|
177
|
+
incompleteReasons,
|
|
178
|
+
// Keep separate provenance and statistics; never pretend two worklists were one run.
|
|
179
|
+
runs: runs.map(({ findings: _findings, processedObjects: _objects, selectedFindings: _selected, ...metadata }) => metadata),
|
|
180
|
+
};
|
|
181
|
+
}
|
|
182
|
+
//# sourceMappingURL=atc-batch.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"atc-batch.js","sourceRoot":"","sources":["../../src/adt/atc-batch.ts"],"names":[],"mappings":"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"}
|
package/dist/adt/atc.d.ts
CHANGED
|
@@ -9,6 +9,8 @@ export interface AtcFinding {
|
|
|
9
9
|
messageTitle: string;
|
|
10
10
|
uri: string;
|
|
11
11
|
line: number;
|
|
12
|
+
/** Enclosing worklist object, present only for batch execution. */
|
|
13
|
+
object?: AtcObjectIdentity;
|
|
12
14
|
quickfixInfo?: string;
|
|
13
15
|
hasQuickfix?: boolean;
|
|
14
16
|
}
|
|
@@ -30,7 +32,16 @@ export interface AtcFindingStatistics {
|
|
|
30
32
|
total: number;
|
|
31
33
|
}
|
|
32
34
|
export type AtcCompletionEvidence = 'asyncRunCompleted' | 'legacyWorklistSettled';
|
|
35
|
+
export interface AtcObjectIdentity {
|
|
36
|
+
type: string;
|
|
37
|
+
name: string;
|
|
38
|
+
uri: string;
|
|
39
|
+
}
|
|
33
40
|
export interface AtcRunResult {
|
|
41
|
+
/** Schema-scoped object evidence, included only for batch execution. */
|
|
42
|
+
processedObjects?: (AtcObjectIdentity & {
|
|
43
|
+
findingCount: number;
|
|
44
|
+
})[];
|
|
34
45
|
findings: AtcFinding[];
|
|
35
46
|
worklistId: string;
|
|
36
47
|
/** The variant actually bound at worklist creation; null only when none could be sent. */
|
|
@@ -73,10 +84,33 @@ export interface AtcPollOptions {
|
|
|
73
84
|
sleep?: (ms: number) => Promise<void>;
|
|
74
85
|
signal?: AbortSignal;
|
|
75
86
|
}
|
|
87
|
+
export declare const ATC_RUN_STATUS_MEDIA_TYPE = "application/vnd.sap.atc.run.v1+xml";
|
|
88
|
+
/**
|
|
89
|
+
* Fallback quiet interval when SAP returns a synchronous run without a status location.
|
|
90
|
+
*
|
|
91
|
+
* A live 758 worklist grew from 23 findings/two objects to 73/ten after already reporting
|
|
92
|
+
* `objectSetIsComplete=true`, so neither that flag nor a few fast count snapshots are terminal
|
|
93
|
+
* evidence. Modern systems instead expose the terminal run status requested with
|
|
94
|
+
* `clientWait=false`. Ten seconds spans at least five intervals at the default 2 s backoff cap.
|
|
95
|
+
* SAP also advances the root worklist timestamp on unchanged GETs, so that proven volatile
|
|
96
|
+
* attribute is excluded from the comparison.
|
|
97
|
+
* See docs/research/2026-08-20-atc-completeness-polling.md.
|
|
98
|
+
*/
|
|
99
|
+
export declare const ATC_SETTLE_QUIET_MS = 10000;
|
|
76
100
|
/** List the valid ATC check variants. */
|
|
77
101
|
export declare function listAtcVariants(http: AdtHttpClient, safety: SafetyConfig, filter?: string, options?: AdtRequestOptions): Promise<NamedItem[]>;
|
|
78
102
|
/** Read the system default ATC check variant. */
|
|
79
103
|
export declare function getAtcSystemDefaultVariant(http: AdtHttpClient, safety: SafetyConfig, options?: AdtRequestOptions): Promise<string | undefined>;
|
|
80
104
|
/** Run an ATC worklist and preserve terminal, structural, and informational evidence for CI. */
|
|
81
105
|
export declare function runAtcCheck(http: AdtHttpClient, safety: SafetyConfig, objectUrl: string, variant?: string, pollOptions?: AtcPollOptions): Promise<AtcRunResult>;
|
|
106
|
+
/** One request budget and variant binding shared by the initial and verification worklists. */
|
|
107
|
+
export declare function prepareAtcExecution(http: AdtHttpClient, safety: SafetyConfig, variant: string | undefined, pollOptions: AtcPollOptions): Promise<{
|
|
108
|
+
variant: string | undefined;
|
|
109
|
+
variantSource: AtcVariantSource;
|
|
110
|
+
pollOptions: AtcPollOptions;
|
|
111
|
+
requestOptions: AdtRequestOptions;
|
|
112
|
+
}>;
|
|
113
|
+
/** Internal shared executor; callers select whether batch object evidence is retained. */
|
|
114
|
+
export declare function runAtcWorklist(http: AdtHttpClient, safety: SafetyConfig, objectUrls: readonly string[], execution: Awaited<ReturnType<typeof prepareAtcExecution>>, includeObjects: boolean): Promise<AtcRunResult>;
|
|
115
|
+
export declare function isAtcRunFailure(status: string): boolean;
|
|
82
116
|
//# sourceMappingURL=atc.d.ts.map
|
package/dist/adt/atc.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"atc.d.ts","sourceRoot":"","sources":["../../src/adt/atc.ts"],"names":[],"mappings":"AAAA,2EAA2E;AAG3E,OAAO,KAAK,EAAE,aAAa,EAAe,MAAM,WAAW,CAAC;AAC5D,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,oBAAoB,CAAC;AAE5D,OAAO,EAAiC,KAAK,YAAY,EAAE,MAAM,aAAa,CAAC;AAC/E,OAAO,EAAiB,KAAK,SAAS,EAAyD,MAAM,iBAAiB,CAAC;AAEvH,MAAM,WAAW,UAAU;IACzB,QAAQ,EAAE,MAAM,CAAC;IACjB,UAAU,EAAE,MAAM,CAAC;IACnB,YAAY,EAAE,MAAM,CAAC;IACrB,GAAG,EAAE,MAAM,CAAC;IACZ,IAAI,EAAE,MAAM,CAAC;IACb,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,WAAW,CAAC,EAAE,OAAO,CAAC;CACvB;AAED;;;;;GAKG;AACH,MAAM,MAAM,gBAAgB,GAAG,WAAW,GAAG,qBAAqB,GAAG,eAAe,GAAG,aAAa,CAAC;AAErG,MAAM,WAAW,UAAU;IACzB,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,EAAE,MAAM,CAAC;CACrB;AAED,MAAM,WAAW,oBAAoB;IACnC,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,KAAK,EAAE,MAAM,CAAC;IACd,KAAK,EAAE,MAAM,CAAC;CACf;AAED,MAAM,MAAM,qBAAqB,GAAG,mBAAmB,GAAG,uBAAuB,CAAC;AAElF,MAAM,WAAW,YAAY;IAC3B,QAAQ,EAAE,UAAU,EAAE,CAAC;IACvB,UAAU,EAAE,MAAM,CAAC;IACnB,0FAA0F;IAC1F,OAAO,EAAE,MAAM,GAAG,IAAI,CAAC;IACvB,aAAa,EAAE,gBAAgB,CAAC;IAChC,eAAe,EAAE,MAAM,CAAC;IACxB;;;;OAIG;IACH,oBAAoB,EAAE,MAAM,GAAG,IAAI,CAAC;IACpC,sGAAsG;IACtG,iBAAiB,EAAE,oBAAoB,GAAG,IAAI,CAAC;IAC/C,YAAY,EAAE,MAAM,CAAC;IACrB,oBAAoB,EAAE,MAAM,CAAC;IAC7B,mBAAmB,EAAE,OAAO,GAAG,IAAI,CAAC;IACpC,+FAA+F;IAC/F,SAAS,EAAE,OAAO,CAAC;IACnB,QAAQ,EAAE,OAAO,CAAC;IAClB,kBAAkB,EAAE,qBAAqB,GAAG,IAAI,CAAC;IACjD,iBAAiB,EAAE,MAAM,EAAE,CAAC;IAC5B,aAAa,EAAE,MAAM,CAAC;IACtB,SAAS,EAAE,MAAM,GAAG,IAAI,CAAC;IACzB,0FAA0F;IAC1F,QAAQ,EAAE,UAAU,EAAE,CAAC;IACvB,QAAQ,EAAE;QACR,EAAE,EAAE,MAAM,CAAC;QACX,SAAS,CAAC,EAAE,MAAM,CAAC;QACnB,aAAa,CAAC,EAAE,MAAM,CAAC;QACvB,MAAM,CAAC,EAAE,MAAM,CAAC;KACjB,CAAC;IACF,KAAK,EAAE,MAAM,EAAE,CAAC;CACjB;AAED,MAAM,WAAW,cAAc;IAC7B,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,GAAG,CAAC,EAAE,MAAM,MAAM,CAAC;IACnB,KAAK,CAAC,EAAE,CAAC,EAAE,EAAE,MAAM,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IACtC,MAAM,CAAC,EAAE,WAAW,CAAC;CACtB;
|
|
1
|
+
{"version":3,"file":"atc.d.ts","sourceRoot":"","sources":["../../src/adt/atc.ts"],"names":[],"mappings":"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"}
|
package/dist/adt/atc.js
CHANGED
|
@@ -7,7 +7,7 @@ const DEFAULT_ATC_TIMEOUT_MS = 300_000;
|
|
|
7
7
|
const DEFAULT_ATC_POLL_DELAY_MS = 250;
|
|
8
8
|
const DEFAULT_ATC_MAX_POLL_DELAY_MS = 2_000;
|
|
9
9
|
const ATC_RUN_STATUS_PREFIX = '/sap/bc/adt/atc/runs/';
|
|
10
|
-
const ATC_RUN_STATUS_MEDIA_TYPE = 'application/vnd.sap.atc.run.v1+xml';
|
|
10
|
+
export const ATC_RUN_STATUS_MEDIA_TYPE = 'application/vnd.sap.atc.run.v1+xml';
|
|
11
11
|
/**
|
|
12
12
|
* Fallback quiet interval when SAP returns a synchronous run without a status location.
|
|
13
13
|
*
|
|
@@ -19,7 +19,7 @@ const ATC_RUN_STATUS_MEDIA_TYPE = 'application/vnd.sap.atc.run.v1+xml';
|
|
|
19
19
|
* attribute is excluded from the comparison.
|
|
20
20
|
* See docs/research/2026-08-20-atc-completeness-polling.md.
|
|
21
21
|
*/
|
|
22
|
-
const ATC_SETTLE_QUIET_MS = 10_000;
|
|
22
|
+
export const ATC_SETTLE_QUIET_MS = 10_000;
|
|
23
23
|
/** Compare the complete wire response except SAP's per-GET root worklist timestamp. */
|
|
24
24
|
function atcWorklistSettleObservation(xml) {
|
|
25
25
|
return xml.replace(/<(?:[A-Za-z_][\w.-]*:)?worklist\b[^>]*>/, (rootStart) => rootStart.replace(/\s+(?:[A-Za-z_][\w.-]*:)?timestamp\s*=\s*(?:"[^"]*"|'[^']*')/, ''));
|
|
@@ -82,16 +82,28 @@ async function resolveCheckVariant(http, safety, requestedRaw, requestOptions) {
|
|
|
82
82
|
}
|
|
83
83
|
/** Run an ATC worklist and preserve terminal, structural, and informational evidence for CI. */
|
|
84
84
|
export async function runAtcCheck(http, safety, objectUrl, variant, pollOptions = {}) {
|
|
85
|
+
const execution = await prepareAtcExecution(http, safety, variant, pollOptions);
|
|
86
|
+
return runAtcWorklist(http, safety, [objectUrl], execution, false);
|
|
87
|
+
}
|
|
88
|
+
/** One request budget and variant binding shared by the initial and verification worklists. */
|
|
89
|
+
export async function prepareAtcExecution(http, safety, variant, pollOptions) {
|
|
85
90
|
checkOperation(safety, OperationType.Read, 'RunATCCheck');
|
|
86
91
|
const now = pollOptions.now ?? Date.now;
|
|
87
92
|
const timeoutMs = pollOptions.timeoutMs ?? DEFAULT_ATC_TIMEOUT_MS;
|
|
88
|
-
const deadline = now() + timeoutMs;
|
|
89
93
|
const requestOptions = {
|
|
90
|
-
deadline,
|
|
94
|
+
deadline: now() + timeoutMs,
|
|
91
95
|
fetchTimeoutMs: timeoutMs,
|
|
92
96
|
signal: pollOptions.signal,
|
|
93
97
|
};
|
|
94
|
-
const
|
|
98
|
+
const resolved = await resolveCheckVariant(http, safety, variant, requestOptions);
|
|
99
|
+
return { ...resolved, pollOptions, requestOptions };
|
|
100
|
+
}
|
|
101
|
+
/** Internal shared executor; callers select whether batch object evidence is retained. */
|
|
102
|
+
export async function runAtcWorklist(http, safety, objectUrls, execution, includeObjects) {
|
|
103
|
+
checkOperation(safety, OperationType.Read, 'RunATCCheck');
|
|
104
|
+
const { variant: effectiveVariant, variantSource, pollOptions, requestOptions } = execution;
|
|
105
|
+
const now = pollOptions.now ?? Date.now;
|
|
106
|
+
const deadline = requestOptions.deadline;
|
|
95
107
|
const worklistPath = effectiveVariant
|
|
96
108
|
? `/sap/bc/adt/atc/worklists?checkVariant=${encodeURIComponent(effectiveVariant)}`
|
|
97
109
|
: '/sap/bc/adt/atc/worklists';
|
|
@@ -106,7 +118,7 @@ export async function runAtcCheck(http, safety, objectUrl, variant, pollOptions
|
|
|
106
118
|
<objectSets xmlns:adtcore="http://www.sap.com/adt/core">
|
|
107
119
|
<objectSet kind="inclusive">
|
|
108
120
|
<adtcore:objectReferences>
|
|
109
|
-
|
|
121
|
+
${objectUrls.map((url) => `<adtcore:objectReference adtcore:uri="${escapeXmlAttr(url)}"/>`).join('\n ')}
|
|
110
122
|
</adtcore:objectReferences>
|
|
111
123
|
</objectSet>
|
|
112
124
|
</objectSets>
|
|
@@ -134,6 +146,7 @@ export async function runAtcCheck(http, safety, objectUrl, variant, pollOptions
|
|
|
134
146
|
const runInfos = parseAtcRunInfos(runResp.body);
|
|
135
147
|
const findingStatistics = parseAtcFindingStatistics(runInfos);
|
|
136
148
|
const baseContext = {
|
|
149
|
+
includeObjects,
|
|
137
150
|
worklistId,
|
|
138
151
|
variant: effectiveVariant,
|
|
139
152
|
variantSource,
|
|
@@ -353,7 +366,7 @@ function normalizedAtcRunStatus(status) {
|
|
|
353
366
|
function isAtcRunCompleted(status) {
|
|
354
367
|
return ['completed', 'finished'].includes(normalizedAtcRunStatus(status));
|
|
355
368
|
}
|
|
356
|
-
function isAtcRunFailure(status) {
|
|
369
|
+
export function isAtcRunFailure(status) {
|
|
357
370
|
return ['not created', 'failed', 'cancelled', 'canceled', 'aborted', 'error'].includes(normalizedAtcRunStatus(status));
|
|
358
371
|
}
|
|
359
372
|
function parseAtcRunInfos(xml) {
|
|
@@ -404,11 +417,23 @@ function parseAtcFinding(finding) {
|
|
|
404
417
|
hasQuickfix: quickfixKinds.some((kind) => String(quickfixNode?.[`@_${kind}`] ?? 'false').toLowerCase() === 'true'),
|
|
405
418
|
};
|
|
406
419
|
}
|
|
407
|
-
function
|
|
408
|
-
|
|
420
|
+
function atcObjectIdentity(object) {
|
|
421
|
+
return {
|
|
422
|
+
type: String(object['@_type']).trim(),
|
|
423
|
+
name: String(object['@_name']).trim(),
|
|
424
|
+
uri: String(object['@_uri']).trim(),
|
|
425
|
+
};
|
|
426
|
+
}
|
|
427
|
+
function parseAtcFindings(root, objectRows, includeObjects) {
|
|
428
|
+
const objectFindings = objectRows.flatMap((object) => nodeRecords(object.findings)
|
|
429
|
+
.flatMap((container) => nodeRecords(container.finding))
|
|
430
|
+
.map((finding) => ({
|
|
431
|
+
...parseAtcFinding(finding),
|
|
432
|
+
...(includeObjects && isValidProcessedObject(object) ? { object: atcObjectIdentity(object) } : {}),
|
|
433
|
+
})));
|
|
409
434
|
// Root-level findings are retained for older/minimal response shapes, but arbitrary nested
|
|
410
435
|
// metadata is never searched as worklist evidence.
|
|
411
|
-
return [...objectFindings, ...nodeRecords(root.finding)
|
|
436
|
+
return [...objectFindings, ...nodeRecords(root.finding).map(parseAtcFinding)];
|
|
412
437
|
}
|
|
413
438
|
function parseAtcInfos(root) {
|
|
414
439
|
return nodeRecords(root.infos)
|
|
@@ -438,7 +463,7 @@ function parseAtcRunResult(xml, context) {
|
|
|
438
463
|
const rawObjectValue = objectContainerShapeIsValid ? objectContainers[0].object : undefined;
|
|
439
464
|
const rawObjectRows = nodeValues(rawObjectValue);
|
|
440
465
|
const objectRows = nodeRecords(rawObjectValue);
|
|
441
|
-
const findings = parseAtcFindings(root, objectRows);
|
|
466
|
+
const findings = parseAtcFindings(root, objectRows, context.includeObjects === true);
|
|
442
467
|
const validObjectRows = objectRows.filter(isValidProcessedObject);
|
|
443
468
|
const processedObjectCount = validObjectRows.length;
|
|
444
469
|
const malformedObjectCount = rawObjectRows.length - validObjectRows.length;
|
|
@@ -472,8 +497,28 @@ function parseAtcRunResult(xml, context) {
|
|
|
472
497
|
if (invalidPriorityCount > 0) {
|
|
473
498
|
incompleteReasons.push(`${invalidPriorityCount} ATC finding(s) had a missing or malformed priority.`);
|
|
474
499
|
}
|
|
500
|
+
const malformedBatchFindings = context.includeObjects === true &&
|
|
501
|
+
objectRows.some((object) => {
|
|
502
|
+
if (object.findings === undefined || object.findings === '')
|
|
503
|
+
return false;
|
|
504
|
+
const containers = nodeRecords(object.findings);
|
|
505
|
+
return (containers.length !== 1 ||
|
|
506
|
+
nodeValues(object.findings).length !== 1 ||
|
|
507
|
+
nodeText(containers[0]) !== '' ||
|
|
508
|
+
nodeValues(containers[0].finding).length !== nodeRecords(containers[0].finding).length);
|
|
509
|
+
});
|
|
510
|
+
if (malformedBatchFindings)
|
|
511
|
+
incompleteReasons.push('SAP returned malformed ATC finding containers or rows.');
|
|
475
512
|
const infos = parseAtcInfos(root);
|
|
476
513
|
return {
|
|
514
|
+
...(context.includeObjects
|
|
515
|
+
? {
|
|
516
|
+
processedObjects: validObjectRows.map((object) => ({
|
|
517
|
+
...atcObjectIdentity(object),
|
|
518
|
+
findingCount: nodeRecords(object.findings).flatMap((container) => nodeRecords(container.finding)).length,
|
|
519
|
+
})),
|
|
520
|
+
}
|
|
521
|
+
: {}),
|
|
477
522
|
findings,
|
|
478
523
|
worklistId: context.worklistId,
|
|
479
524
|
variant: context.variant ?? null,
|
|
@@ -492,7 +537,8 @@ function parseAtcRunResult(xml, context) {
|
|
|
492
537
|
objectContainerShapeIsValid &&
|
|
493
538
|
processedObjectCount > 0 &&
|
|
494
539
|
malformedObjectCount === 0 &&
|
|
495
|
-
invalidPriorityCount === 0
|
|
540
|
+
invalidPriorityCount === 0 &&
|
|
541
|
+
!malformedBatchFindings,
|
|
496
542
|
completionEvidence: context.completionEvidence,
|
|
497
543
|
incompleteReasons,
|
|
498
544
|
runStatusCode: context.runStatusCode,
|