@enterpriseai/cli 3.19.4 → 3.20.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.
Files changed (121) hide show
  1. package/README.md +47 -16
  2. package/dist/commands/agent.js +3 -1
  3. package/dist/commands/agent.js.map +1 -1
  4. package/dist/commands/content-understanding.d.ts +15 -0
  5. package/dist/commands/content-understanding.d.ts.map +1 -0
  6. package/dist/commands/content-understanding.js +277 -0
  7. package/dist/commands/content-understanding.js.map +1 -0
  8. package/dist/commands/docs.d.ts.map +1 -1
  9. package/dist/commands/docs.js +129 -1
  10. package/dist/commands/docs.js.map +1 -1
  11. package/dist/commands/eai-managed-deploy-output.d.ts.map +1 -1
  12. package/dist/commands/eai-managed-deploy-output.js +12 -2
  13. package/dist/commands/eai-managed-deploy-output.js.map +1 -1
  14. package/dist/commands/eai-managed-source-authorize-commit.d.ts +28 -0
  15. package/dist/commands/eai-managed-source-authorize-commit.d.ts.map +1 -0
  16. package/dist/commands/eai-managed-source-authorize-commit.js +200 -0
  17. package/dist/commands/eai-managed-source-authorize-commit.js.map +1 -0
  18. package/dist/commands/eai-managed-source-move.d.ts.map +1 -1
  19. package/dist/commands/eai-managed-source-move.js +3 -0
  20. package/dist/commands/eai-managed-source-move.js.map +1 -1
  21. package/dist/commands/init.js +17 -17
  22. package/dist/commands/resources.d.ts.map +1 -1
  23. package/dist/commands/resources.js +6 -6
  24. package/dist/commands/resources.js.map +1 -1
  25. package/dist/commands/support.d.ts +6 -3
  26. package/dist/commands/support.d.ts.map +1 -1
  27. package/dist/commands/support.js +117 -25
  28. package/dist/commands/support.js.map +1 -1
  29. package/dist/commands/tenant.d.ts.map +1 -1
  30. package/dist/commands/tenant.js +6 -34
  31. package/dist/commands/tenant.js.map +1 -1
  32. package/dist/index.js +65 -11
  33. package/dist/index.js.map +1 -1
  34. package/dist/lib/agent-guide.d.ts.map +1 -1
  35. package/dist/lib/agent-guide.js +30 -16
  36. package/dist/lib/agent-guide.js.map +1 -1
  37. package/dist/lib/api.d.ts +47 -0
  38. package/dist/lib/api.d.ts.map +1 -1
  39. package/dist/lib/api.js +99 -6
  40. package/dist/lib/api.js.map +1 -1
  41. package/dist/lib/cli-qa-transport.d.ts +7 -0
  42. package/dist/lib/cli-qa-transport.d.ts.map +1 -0
  43. package/dist/lib/cli-qa-transport.js +18 -0
  44. package/dist/lib/cli-qa-transport.js.map +1 -0
  45. package/dist/lib/content-understanding-client.d.ts +64 -0
  46. package/dist/lib/content-understanding-client.d.ts.map +1 -0
  47. package/dist/lib/content-understanding-client.js +105 -0
  48. package/dist/lib/content-understanding-client.js.map +1 -0
  49. package/dist/lib/content-understanding-manifest.d.ts +39 -0
  50. package/dist/lib/content-understanding-manifest.d.ts.map +1 -0
  51. package/dist/lib/content-understanding-manifest.js +265 -0
  52. package/dist/lib/content-understanding-manifest.js.map +1 -0
  53. package/dist/lib/context.d.ts +3 -0
  54. package/dist/lib/context.d.ts.map +1 -1
  55. package/dist/lib/context.js +12 -2
  56. package/dist/lib/context.js.map +1 -1
  57. package/dist/lib/eai-managed-source-client-types.d.ts +44 -1
  58. package/dist/lib/eai-managed-source-client-types.d.ts.map +1 -1
  59. package/dist/lib/eai-managed-source-operation-client.d.ts +3 -0
  60. package/dist/lib/eai-managed-source-operation-client.d.ts.map +1 -1
  61. package/dist/lib/eai-managed-source-operation-client.js +69 -2
  62. package/dist/lib/eai-managed-source-operation-client.js.map +1 -1
  63. package/dist/lib/eai-managed-source-publication-client.d.ts.map +1 -1
  64. package/dist/lib/eai-managed-source-publication-client.js +1 -0
  65. package/dist/lib/eai-managed-source-publication-client.js.map +1 -1
  66. package/dist/lib/error-codes.d.ts +1 -1
  67. package/dist/lib/error-codes.d.ts.map +1 -1
  68. package/dist/lib/error-codes.js +9 -5
  69. package/dist/lib/error-codes.js.map +1 -1
  70. package/dist/lib/gofer-installer.d.ts.map +1 -1
  71. package/dist/lib/gofer-installer.js +3 -1
  72. package/dist/lib/gofer-installer.js.map +1 -1
  73. package/dist/lib/support-context.d.ts +4 -3
  74. package/dist/lib/support-context.d.ts.map +1 -1
  75. package/dist/lib/support-context.js +11 -13
  76. package/dist/lib/support-context.js.map +1 -1
  77. package/dist/lib/support-harness.d.ts +86 -0
  78. package/dist/lib/support-harness.d.ts.map +1 -0
  79. package/dist/lib/support-harness.js +471 -0
  80. package/dist/lib/support-harness.js.map +1 -0
  81. package/dist/lib/support-redaction.d.ts.map +1 -1
  82. package/dist/lib/support-redaction.js +221 -3
  83. package/dist/lib/support-redaction.js.map +1 -1
  84. package/dist/lib/support-report.d.ts +27 -5
  85. package/dist/lib/support-report.d.ts.map +1 -1
  86. package/dist/lib/support-report.js +75 -31
  87. package/dist/lib/support-report.js.map +1 -1
  88. package/dist/lib/tenant-context.d.ts +7 -0
  89. package/dist/lib/tenant-context.d.ts.map +1 -1
  90. package/dist/lib/tenant-context.js +17 -4
  91. package/dist/lib/tenant-context.js.map +1 -1
  92. package/package.json +8 -3
  93. package/resources/content-understanding/contract-golden.json +444 -0
  94. package/resources/content-understanding/manifest.schema.json +551 -0
  95. package/resources/content-understanding/procurement-example.json +135 -0
  96. package/resources/deploy/eai-app-template/producer-pin.json +4 -4
  97. package/resources/gofer/agents-skills/eai/SKILL.md +22 -21
  98. package/resources/gofer/claude-commands/eai.md +22 -21
  99. package/resources/gofer/claude-skills/eai/SKILL.md +22 -21
  100. package/resources/gofer/commands/0_gofer_start.md +26 -24
  101. package/resources/gofer/commands/5_gofer_implement.md +8 -4
  102. package/resources/gofer/commands/gofer_eai_first_run.md +27 -22
  103. package/resources/gofer/copilot-prompts/eai.prompt.md +22 -21
  104. package/resources/gofer/gemini/commands/gofer/eai.md +22 -21
  105. package/resources/gofer/gemini/commands/gofer/manifest.json +1 -1
  106. package/resources/gofer/github-skills/eai/SKILL.md +22 -21
  107. package/resources/gofer/grok-skills/eai/SKILL.md +22 -21
  108. package/resources/gofer/instruction-templates/base/agents-base.md +18 -17
  109. package/resources/gofer/instruction-templates/base/claude-base.md +0 -18
  110. package/resources/gofer/instruction-templates/base/copilot-base.md +18 -17
  111. package/resources/gofer/instruction-templates/gofer/gofer-claude.md +1 -7
  112. package/resources/gofer/node-scripts/generate-commands.mjs +37 -24
  113. package/resources/gofer/node-scripts/package-agent-plugin.mjs +55 -6
  114. package/resources/gofer/node-scripts/workspace-bootstrap-lib.mjs +8 -4
  115. package/resources/gofer/references/platform/README.md +8 -3
  116. package/resources/gofer/references/platform/eai-support.md +16 -16
  117. package/resources/gofer/specify-commands/0_gofer_start.md +26 -24
  118. package/resources/gofer/specify-commands/5_gofer_implement.md +8 -4
  119. package/resources/gofer/specify-commands/gofer_eai_first_run.md +27 -22
  120. package/resources/gofer/system-skills/eai/SKILL.md +22 -21
  121. package/resources/linked-sources.json +2 -2
package/README.md CHANGED
@@ -118,8 +118,8 @@ eai workspace select
118
118
  # attempts first-admin bootstrap for the current login, and only marks
119
119
  # the workspace usable after workspace-admin membership is confirmed
120
120
  # (platform role ID `tenant-admin`).
121
- # The child home region defaults to the parent region; pass
122
- # `--home-region au|ca|eu` when the child must use another region.
121
+ # A child workspace always inherits its parent's home region;
122
+ # `--home-region` applies only to root workspaces (`--allow-root`).
123
123
 
124
124
  # 4. Sync project environment if your app needs local configuration
125
125
  eai env pull --include-secrets
@@ -508,26 +508,55 @@ role definitions, Entra configuration, databases, or cloud portals.
508
508
 
509
509
  ## Support reports
510
510
 
511
- Run `eai support` after an unresolved CLI failure. It shows a locally redacted
512
- report and asks before sending. The report includes the last failing command,
513
- catalog error code and reason, CLI version, OS, and known workspace/app context.
514
- Credentials and unrelated environment settings are excluded.
515
- Saved failure context contains command and catalog metadata only. Raw error text
516
- is never saved for a later report; recognized errors use the catalog's title.
511
+ Run `eai support` when you want help with a CLI failure. It shows a locally
512
+ redacted report and asks before sending. The report includes the last failing
513
+ command, catalog error code and reason, CLI version, OS, and known workspace/app
514
+ context. Credentials and unrelated environment settings are excluded. Saved
515
+ failure context contains command and catalog metadata only, is left out of the
516
+ report after 24 hours (the CLI shows its time), and `--no-last-error` skips it.
517
517
 
518
- For an AI harness, preview first:
518
+ Every failing command ends with the same offer: "Need help? Run eai support, or
519
+ ask your AI assistant to get help. Nothing is sent without your approval." Text mode
520
+ prints this on every nonzero exit. JSON error keys stay unchanged; `error.suggestion`
521
+ contains only the catalog suggestion.
522
+
523
+ Re-run `eai init --tool <tool>` to refresh instructions in projects created with older CLI versions.
524
+ `eai gofer refresh` preserves their CLAUDE.md and AGENTS.md.
525
+
526
+ An AI harness starts a report only when you ask for EAI Support ("get help" or
527
+ `eai support`). Generic coding help, command failures, failed fixes and error hints do not authorize any eai support call, including allocation, preview, sending or decline.
528
+ Write a short summary of the chat problem, attempts and results, without raw transcripts, environment values or file contents.
529
+ It passes its bounded session summary (what you asked, the goal,
530
+ steps, commands, errors, attempted fixes and project-relative files) through `--context-file`.
531
+ For a file, run `eai support --create-context-file --format json`, then write the summary into the returned `contextFile` without replacing it. The CLI allocates it in `~/.eai/support/context/` (directory 0700, file 0600) and records its identity. Preview keeps it; an approved send deletes it. On a declined preview, run `eai support --decline --context-file <path> --format json` to clean it up without sending. Marked files older than 24 hours are removed on the next support run. Untracked files and files elsewhere are never deleted.
532
+
533
+ `--context-file`, which reads a JSON file or stdin (`-`), accepts at most 64 KiB,
534
+ redacts credentials, hides your home directory and project root, and drops the
535
+ oldest steps, commands and errors to stay within the website's 32 KiB cap:
519
536
 
520
537
  ```bash
521
- eai support --source harness --tool codex --format json
538
+ eai support --source harness --tool codex --context-file - --format json
522
539
  ```
523
540
 
524
- Show the person the returned bundle. After they explicitly approve that report,
525
- rerun the same command with `--yes`. JSON runs without `--yes` never send a report.
526
- The returned link contains only a draft id and one-time token in its fragment.
527
- Open it to review and submit the report before the draft expires.
541
+ The JSON preview returns `previewText`, the whole redacted report as plain text
542
+ ending with its digest, and `bundleDigest`. The harness shows `previewText`
543
+ unchanged and asks you. After you approve, it reruns with
544
+ `--yes --approved-digest <bundleDigest>`; any other digest answers
545
+ `consent_stale` and sends nothing. JSON runs without `--yes` never send a report,
546
+ and `--yes` always needs the digest, including interactive text runs.
528
547
 
529
- A missing or expired `eai login` session, or a website 401, returns the plain
530
- Support link and creates no draft. `--no-open` prints the link without opening a
548
+ When the saved session has no active workspace, the report needs to know where
549
+ your organisation is based so it is stored in that region. A terminal asks you;
550
+ JSON runs answer `consent_required` with `questions: ["organisationLocation"]`
551
+ until `--organisation-location apac|emea|americas` is supplied. If the website
552
+ still cannot place the report it answers `region_required`, and the CLI returns
553
+ the Support chat link instead.
554
+
555
+ The returned link contains only a draft id and one-time token in its fragment.
556
+ Open it to review and submit the report before the draft expires. A missing or
557
+ expired `eai login` session, a website 401, a declined report or `region_required`
558
+ returns `<website>/support?chat=open`, which opens the Support chat without
559
+ prefill and creates no draft. `--no-open` prints the link without opening a
531
560
  browser. Reports never go in URL parameters.
532
561
 
533
562
  Existing projects can preview updated harness instructions with
@@ -872,3 +901,5 @@ Full documentation: https://eai-support.github.io/eai/
872
901
  - [ ] `eai dev --offline` — local mock gateway for offline development
873
902
  - [ ] `eai tunnel` — Cloudflare tunnel for webhook testing
874
903
  - [x] npmjs install alias (`npm install -g eai-cli`) with static registry fallback
904
+
905
+ Bundled Gofer assets stay pinned to v3.14.3 and include the support-only patch from eai-gofer#433 until its release. Regenerated entrypoints include the existing Gofer 3.12.7 to 3.14.3 generator drift.
@@ -60,7 +60,9 @@ Examples:
60
60
  Notes:
61
61
  - Use this before improvising eai commands.
62
62
  - Prefer read-only diagnostics before commands marked [changes state].
63
- - On failure, run eai errors explain <code-or-reason> --format json.
63
+ - If advertised, query eai errors explain <code-or-reason> --format json at most once for the original failure.
64
+ - Never retry or explain a failed eai errors explain command; report unavailable guidance, then stop and wait.
65
+ - Follow read-only diagnostics automatically; ask before changes, stop at the retry limit, then stop and wait.
64
66
  `)
65
67
  .action((options) => {
66
68
  const jsonOutput = options.json || options.format === 'json';
@@ -1 +1 @@
1
- {"version":3,"file":"agent.js","sourceRoot":"","sources":["../../src/commands/agent.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"agent.js","sourceRoot":"","sources":["../../src/commands/agent.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AACpC,OAAO,KAAK,MAAM,OAAO,CAAC;AAC1B,OAAO,EAAE,aAAa,EAA+C,MAAM,uBAAuB,CAAC;AACnG,OAAO,KAAK,GAAG,MAAM,kBAAkB,CAAC;AAExC,SAAS,aAAa,CAAC,OAA0B;IAC/C,MAAM,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC,CAAC,KAAK,CAAC,MAAM,CAAC,iBAAiB,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,KAAK,CAAC,aAAa,CAAC,CAAC;IAC9F,MAAM,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,KAAK,CAAC,GAAG,CAAC,OAAO,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;IAC/D,OAAO,GAAG,KAAK,CAAC,IAAI,CAAC,OAAO,CAAC,OAAO,CAAC,IAAI,MAAM,OAAO,OAAO,CAAC,OAAO,GAAG,IAAI,EAAE,CAAC;AACjF,CAAC;AAED,SAAS,WAAW,CAAC,KAAuB;IAC1C,OAAO,KAAK,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE;QACxB,MAAM,KAAK,GAAG;YACZ,GAAG,IAAI,CAAC,IAAI,KAAK,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,EAAE;YACzC,MAAM,IAAI,CAAC,WAAW,EAAE;SACzB,CAAC;QACF,KAAK,MAAM,OAAO,IAAI,IAAI,CAAC,QAAQ,IAAI,EAAE,EAAE,CAAC;YAC1C,KAAK,CAAC,IAAI,CAAC,QAAQ,aAAa,CAAC,OAAO,CAAC,CAAC,OAAO,CAAC,MAAM,EAAE,SAAS,CAAC,EAAE,CAAC,CAAC;QAC1E,CAAC;QACD,OAAO,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAC1B,CAAC,CAAC,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;AAClB,CAAC;AAED,SAAS,cAAc;IACrB,MAAM,KAAK,GAAG,aAAa,EAAE,CAAC;IAE9B,GAAG,CAAC,OAAO,CAAC,2BAA2B,CAAC,CAAC;IACzC,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC;IAE3B,GAAG,CAAC,OAAO,CAAC,YAAY,CAAC,CAAC;IAC1B,KAAK,MAAM,OAAO,IAAI,KAAK,CAAC,aAAa,EAAE,CAAC;QAC1C,OAAO,CAAC,GAAG,CAAC,KAAK,aAAa,CAAC,OAAO,CAAC,EAAE,CAAC,CAAC;IAC7C,CAAC;IAED,GAAG,CAAC,OAAO,CAAC,cAAc,CAAC,CAAC;IAC5B,KAAK,MAAM,UAAU,IAAI,KAAK,CAAC,YAAY,EAAE,CAAC;QAC5C,OAAO,CAAC,GAAG,CAAC,KAAK,KAAK,CAAC,IAAI,CAAC,UAAU,CAAC,EAAE,CAAC,CAAC;IAC7C,CAAC;IAED,GAAG,CAAC,OAAO,CAAC,iBAAiB,CAAC,CAAC;IAC/B,KAAK,MAAM,IAAI,IAAI,KAAK,CAAC,cAAc,EAAE,CAAC;QACxC,OAAO,CAAC,GAAG,CAAC,KAAK,IAAI,EAAE,CAAC,CAAC;IAC3B,CAAC;IAED,GAAG,CAAC,OAAO,CAAC,eAAe,CAAC,CAAC;IAC7B,OAAO,CAAC,GAAG,CAAC,WAAW,CAAC,KAAK,CAAC,YAAY,CAAC,CAAC,CAAC;IAE7C,GAAG,CAAC,OAAO,CAAC,kBAAkB,CAAC,CAAC;IAChC,OAAO,CAAC,GAAG,CAAC,WAAW,CAAC,KAAK,CAAC,eAAe,CAAC,CAAC,CAAC;IAEhD,GAAG,CAAC,OAAO,CAAC,iBAAiB,CAAC,CAAC;IAC/B,KAAK,MAAM,SAAS,IAAI,KAAK,CAAC,cAAc,EAAE,CAAC;QAC7C,OAAO,CAAC,GAAG,CAAC,KAAK,SAAS,EAAE,CAAC,CAAC;IAChC,CAAC;AACH,CAAC;AAED,MAAM,CAAC,MAAM,YAAY,GAAG,IAAI,OAAO,CAAC,OAAO,CAAC;KAC7C,WAAW,CAAC,+CAA+C,CAAC,CAAC;AAEhE,YAAY;KACT,OAAO,CAAC,OAAO,CAAC;KAChB,WAAW,CAAC,2CAA2C,CAAC;KACxD,MAAM,CAAC,mBAAmB,EAAE,2BAA2B,EAAE,MAAM,CAAC;KAChE,MAAM,CAAC,QAAQ,EAAE,iDAAiD,EAAE,KAAK,CAAC;KAC1E,WAAW,CAAC,OAAO,EAAE;;;;;;;;;;;;GAYrB,CAAC;KACD,MAAM,CAAC,CAAC,OAA4C,EAAE,EAAE;IACvD,MAAM,UAAU,GAAG,OAAO,CAAC,IAAI,IAAI,OAAO,CAAC,MAAM,KAAK,MAAM,CAAC;IAE7D,IAAI,UAAU,EAAE,CAAC;QACf,GAAG,CAAC,IAAI,CAAC,aAAa,EAAE,CAAC,CAAC;QAC1B,OAAO;IACT,CAAC;IAED,cAAc,EAAE,CAAC;AACnB,CAAC,CAAC,CAAC"}
@@ -0,0 +1,15 @@
1
+ import { Command } from 'commander';
2
+ interface CuOptions {
3
+ file?: string;
4
+ tenantId?: string;
5
+ plan?: string;
6
+ operationId?: string;
7
+ format?: string;
8
+ wait?: boolean;
9
+ timeout?: string;
10
+ }
11
+ /** Validate the caller's identity before index-level profile activation can exit. */
12
+ export declare function contentUnderstandingPreflightOperationId(options: CuOptions): string | undefined;
13
+ export declare const contentUnderstandingCommand: Command;
14
+ export {};
15
+ //# sourceMappingURL=content-understanding.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"content-understanding.d.ts","sourceRoot":"","sources":["../../src/commands/content-understanding.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,OAAO,EAAU,MAAM,WAAW,CAAC;AAgB5C,UAAU,SAAS;IACjB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,IAAI,CAAC,EAAE,OAAO,CAAC;IACf,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAwDD,qFAAqF;AACrF,wBAAgB,wCAAwC,CAAC,OAAO,EAAE,SAAS,GAAG,MAAM,GAAG,SAAS,CAG/F;AAuED,eAAO,MAAM,2BAA2B,SAoBtC,CAAC"}
@@ -0,0 +1,277 @@
1
+ import { createHash } from 'node:crypto';
2
+ import { readFile } from 'node:fs/promises';
3
+ import { Command, Option } from 'commander';
4
+ import { resolveCommandContext } from '../lib/context.js';
5
+ import { requireManagedPublicApiUrl } from '../lib/managed-public-api.js';
6
+ import { isRecord } from '../lib/utils.js';
7
+ import * as out from '../lib/output.js';
8
+ import { errorCatalog } from '../lib/error-codes.js';
9
+ import { CANONICAL_TENANT_ID, ContentUnderstandingError, parseContentUnderstandingManifest, } from '../lib/content-understanding-manifest.js';
10
+ import { parseContentUnderstandingCapabilities, parseContentUnderstandingOperation, parseContentUnderstandingPlan, readContentUnderstandingResponse, requireContentUnderstandingOperationId, requireWaitTimeout, requireContentUnderstandingManifestCapabilities, } from '../lib/content-understanding-client.js';
11
+ async function readLocalJson(path, code, label) {
12
+ let bytes;
13
+ try {
14
+ bytes = await readFile(path);
15
+ }
16
+ catch {
17
+ throw new ContentUnderstandingError(code, `${label} file could not be read.`);
18
+ }
19
+ if (bytes.length > 1024 * 1024)
20
+ throw new ContentUnderstandingError(code, `${label} file exceeds the input size budget.`);
21
+ try {
22
+ // Preserve a BOM so JSON parsing retains the existing refusal, while fatal decoding
23
+ // prevents changing malformed input bytes before binding or submitting the plan.
24
+ return { bytes, value: JSON.parse(new TextDecoder('utf-8', { fatal: true, ignoreBOM: true }).decode(bytes)) };
25
+ }
26
+ catch {
27
+ throw new ContentUnderstandingError(code, `${label} file must contain valid UTF-8 JSON.`);
28
+ }
29
+ }
30
+ async function readManifest(path) {
31
+ if (!path)
32
+ throw new ContentUnderstandingError('CU_INVALID_MANIFEST', '--file is required.');
33
+ const { bytes, value } = await readLocalJson(path, 'CU_INVALID_MANIFEST', 'Manifest');
34
+ return { manifest: parseContentUnderstandingManifest(value), manifestSha256: createHash('sha256').update(bytes).digest('hex') };
35
+ }
36
+ function tenantId(options, manifest) {
37
+ if (typeof options.tenantId !== 'string' || !CANONICAL_TENANT_ID.test(options.tenantId) || options.tenantId === '00000000-0000-0000-0000-000000000000'
38
+ || (manifest && manifest.tenantId !== options.tenantId)) {
39
+ throw new ContentUnderstandingError('CU_TENANT_MISMATCH', '--tenant-id must be a canonical workspace UUID matching the manifest.');
40
+ }
41
+ return options.tenantId;
42
+ }
43
+ async function contextFor(id) {
44
+ const context = await resolveCommandContext({ tenantId: id, interactive: false, forceRefresh: true,
45
+ validatePublicApiUrl: requireManagedPublicApiUrl, pinPublicApiUrl: true,
46
+ onError: (code, message) => { throw new ContentUnderstandingError(code, message ?? errorCatalog[code].message); } });
47
+ if (context.tenantId !== id)
48
+ throw new ContentUnderstandingError('CU_TENANT_MISMATCH', 'Resolved workspace differs from the requested workspace.');
49
+ return context;
50
+ }
51
+ function print(options, value) {
52
+ if (options.format === 'json')
53
+ out.json(value);
54
+ else if (!value.ok) {
55
+ out.error(('error' in value ? value.error?.message : undefined) || 'Content Understanding request failed.');
56
+ if ('error' in value && value.error?.operationId)
57
+ out.info(`Operation ID: ${value.error.operationId}`);
58
+ }
59
+ else if ('body' in value && isRecord(value.body)) {
60
+ const body = value.body;
61
+ if (body.$schema) {
62
+ process.stdout.write(JSON.stringify(body, null, 2) + '\n');
63
+ return;
64
+ }
65
+ out.success(typeof body.status === 'string' ? `Content Understanding ${body.status}${typeof body.operationId === 'string' ? ` (${body.operationId})` : ''}`
66
+ : 'ready' in body ? `Content Understanding ${body.ready === true ? 'ready' : 'not ready'}` : 'Content Understanding configuration valid');
67
+ }
68
+ else
69
+ out.success('Content Understanding configuration valid');
70
+ if (!value.ok)
71
+ process.exitCode = 1;
72
+ }
73
+ function failure(error) {
74
+ const known = error instanceof ContentUnderstandingError;
75
+ return { ok: false, ...(known && error.status ? { status: error.status } : {}),
76
+ error: { code: known ? error.code : 'CU_REQUEST_FAILED', message: error instanceof Error ? error.message : 'Content Understanding request failed.',
77
+ ...(known && error.operationId ? { operationId: error.operationId } : {}) } };
78
+ }
79
+ /** Validate the caller's identity before index-level profile activation can exit. */
80
+ export function contentUnderstandingPreflightOperationId(options) {
81
+ try {
82
+ return options.operationId === undefined ? undefined : requireContentUnderstandingOperationId(options.operationId);
83
+ }
84
+ catch (error) {
85
+ print(options, failure(error));
86
+ process.exit(1);
87
+ }
88
+ }
89
+ function action(handler, retainRequestedOperation = false) {
90
+ return async (options) => {
91
+ let requestedOperation;
92
+ try {
93
+ if (retainRequestedOperation && options.operationId !== undefined)
94
+ requestedOperation = requireContentUnderstandingOperationId(options.operationId);
95
+ print(options, await handler(options));
96
+ }
97
+ catch (error) {
98
+ const result = failure(error);
99
+ // This is the valid identity supplied by the caller, not a server
100
+ // acknowledgment. Preflight failure never creates an operation receipt.
101
+ if (requestedOperation && result.error)
102
+ result.error.operationId = requestedOperation;
103
+ print(options, result);
104
+ }
105
+ };
106
+ }
107
+ async function capabilities(context, timeoutMs) {
108
+ return parseContentUnderstandingCapabilities(await readContentUnderstandingResponse(await context.client.getContentUnderstandingCapabilities(timeoutMs)), context.tenantId);
109
+ }
110
+ async function parsePlanFile(options, input) {
111
+ if (!options.plan)
112
+ throw new ContentUnderstandingError('CU_PLAN_MISMATCH', '--plan must name the unchanged saved JSON plan.');
113
+ const { value } = await readLocalJson(options.plan, 'CU_PLAN_MISMATCH', 'Plan');
114
+ if (!isRecord(value) || value.ok !== true || value.kind !== 'eai.content-understanding.plan' || value.schemaVersion !== 1 || !isRecord(value.binding)
115
+ || value.binding.tenantId !== input.manifest.tenantId || value.binding.bundleKey !== input.manifest.bundleKey
116
+ || value.binding.manifestSha256 !== input.manifestSha256 || typeof value.binding.publicApiUrl !== 'string') {
117
+ throw new ContentUnderstandingError('CU_PLAN_MISMATCH', 'Saved plan does not match the unchanged manifest file and workspace/bundle.');
118
+ }
119
+ const body = parseContentUnderstandingPlan(value.body, input.manifest.tenantId, input.manifest.bundleKey);
120
+ return { ok: true, kind: 'eai.content-understanding.plan', schemaVersion: 1,
121
+ binding: { tenantId: input.manifest.tenantId, bundleKey: input.manifest.bundleKey,
122
+ publicApiUrl: value.binding.publicApiUrl, manifestSha256: input.manifestSha256 }, body };
123
+ }
124
+ function operationReadError(error, operationId) {
125
+ return error instanceof ContentUnderstandingError
126
+ ? new ContentUnderstandingError(error.code, error.message, operationId, error.status)
127
+ : new ContentUnderstandingError('CU_OPERATION_READ_FAILED', 'Reading this operation failed. Keep its ID and inspect the original operation before resuming.', operationId);
128
+ }
129
+ async function waitForOperation(context, initial, options, deadline, resume) {
130
+ let operation = initial;
131
+ try {
132
+ while (options.wait && ['pending', 'running'].includes(operation.status) && Date.now() < deadline) {
133
+ if (operation.nextAction === 'apply') {
134
+ if (!resume)
135
+ return { ok: false, body: operation, error: { code: 'CU_REQUIRES_APPLY',
136
+ message: 'Provider work is ready; resume apply with the unchanged manifest, saved plan and this operation ID to publish or activate. Status remains read-only.', operationId: operation.operationId } };
137
+ operation = await resume(initial.operationId, Math.max(1, deadline - Date.now()));
138
+ if (!['pending', 'running'].includes(operation.status))
139
+ break;
140
+ }
141
+ await new Promise(resolve => setTimeout(resolve, Math.min(2000, Math.max(0, deadline - Date.now()))));
142
+ if (Date.now() >= deadline)
143
+ break;
144
+ operation = parseContentUnderstandingOperation(await readContentUnderstandingResponse(await context.client.getContentUnderstandingOperation(initial.operationId, Math.max(1, deadline - Date.now()))), context.tenantId, initial);
145
+ }
146
+ }
147
+ catch (error) {
148
+ const retained = operationReadError(error, initial.operationId);
149
+ return { ...failure(retained), body: operation };
150
+ }
151
+ if (['failed', 'unknown', 'partial'].includes(operation.status))
152
+ return { ok: false, body: operation,
153
+ error: { code: `CU_OPERATION_${operation.status.toUpperCase()}`, message: `Content Understanding operation is ${operation.status}; retain its ID and inspect its steps before resuming.`, operationId: operation.operationId } };
154
+ if (operation.status === 'succeeded' && operation.currentReady !== true)
155
+ return { ok: false, body: operation,
156
+ error: { code: 'CU_CURRENT_READINESS_UNVERIFIED', message: 'Historical completion does not verify current workspace and provider readiness. Retain this operation ID and inspect current readback blockers before processing documents.', operationId: operation.operationId } };
157
+ if (options.wait && operation.status !== 'succeeded')
158
+ return { ok: false, body: operation,
159
+ error: { code: 'CU_OPERATION_PENDING', message: 'Wait deadline reached. Use status for this operation; no replacement operation was submitted.', operationId: operation.operationId } };
160
+ return { ok: true, status: operation.status === 'succeeded' ? 200 : 202, body: operation };
161
+ }
162
+ export const contentUnderstandingCommand = new Command('content-understanding')
163
+ .description('Validate, plan and materialize bounded document analyzers through the selected workspace PublicAPI')
164
+ .addHelpText('after', `
165
+ Harness workflow:
166
+ eai content-understanding schema --format json
167
+ eai content-understanding validate --file cu.json --format json
168
+ eai content-understanding capabilities --tenant-id <workspace-id> --format json
169
+ eai content-understanding plan --file cu.json --tenant-id <workspace-id> --format json > cu-plan.json
170
+ eai content-understanding apply --file cu.json --plan cu-plan.json --tenant-id <workspace-id> --format json
171
+ eai content-understanding status --operation-id <operation-id> --tenant-id <workspace-id> --format json
172
+
173
+ Your harness authors the manifest. The platform owns Azure credentials, approved models,
174
+ provider ownership and readiness. Typed mode must be enabled and qualified on that workspace.
175
+ Only document fields and flat classification are available. Graphs and segmentation are refused.
176
+ Formula, figure and output-format settings require features.advancedDocumentConfig exactly true.
177
+ Before planning, prepare the existing app/workflow binding and matching tenant-owned
178
+ classifier draft with the existing setup and eai classifier save commands.
179
+ Keep the original manifest and plan for deliberate recovery after an unknown acknowledgement.
180
+ Status only reads existing operations; acceptance and pending work are not completion.
181
+ Succeeded historical work requires currentReady exactly true before document processing.
182
+ `);
183
+ function outputOptions(command) {
184
+ return command.addOption(new Option('--format <format>', 'Output format').choices(['text', 'json']).default('text'));
185
+ }
186
+ function workspaceOptions(command) {
187
+ return outputOptions(command.requiredOption('--tenant-id <id>', 'Exact owning workspace UUID'));
188
+ }
189
+ function waitOptions(command) {
190
+ return command.option('--wait', command.name() === 'apply' ? 'Wait for this exact operation; resume acknowledged remaining steps when requested' : 'Poll this exact operation without any mutation', false)
191
+ .option('--timeout <seconds>', 'Wait deadline, 1 to 1800 seconds', '300');
192
+ }
193
+ outputOptions(contentUnderstandingCommand.command('schema').description('Print the local manifest JSON schema and semantic bounds'))
194
+ .action(action(async () => {
195
+ const schema = JSON.parse(await readFile(new URL('../../resources/content-understanding/manifest.schema.json', import.meta.url), 'utf8'));
196
+ return { ok: true, body: schema };
197
+ }));
198
+ outputOptions(contentUnderstandingCommand.command('validate').description('Validate the complete manifest locally with no authentication or network access')
199
+ .requiredOption('--file <path>', 'Declarative document configuration JSON'))
200
+ .action(action(async (options) => {
201
+ const input = await readManifest(options.file);
202
+ return { ok: true, body: { valid: true, kind: input.manifest.kind,
203
+ schemaVersion: input.manifest.schemaVersion, bundleKey: input.manifest.bundleKey, manifestSha256: input.manifestSha256,
204
+ documentTypes: input.manifest.documentTypes.map(doc => doc.code) } };
205
+ }));
206
+ workspaceOptions(contentUnderstandingCommand.command('capabilities').description('Read actual selected-workspace typed mode, prerequisites and readiness'))
207
+ .action(action(async (options) => ({ ok: true, body: await capabilities(await contextFor(tenantId(options))) })));
208
+ workspaceOptions(contentUnderstandingCommand.command('plan').description('Read prerequisites and return a scope-bound configuration plan; writes nothing')
209
+ .requiredOption('--file <path>', 'Declarative document configuration JSON'))
210
+ .action(action(async (options) => {
211
+ const input = await readManifest(options.file), context = await contextFor(tenantId(options, input.manifest));
212
+ const body = parseContentUnderstandingPlan(await readContentUnderstandingResponse(await context.client.planContentUnderstandingConfiguration(input.manifest)), context.tenantId, input.manifest.bundleKey);
213
+ return { ok: true, kind: 'eai.content-understanding.plan', schemaVersion: 1,
214
+ binding: { tenantId: context.tenantId, bundleKey: input.manifest.bundleKey,
215
+ publicApiUrl: context.publicApiUrl, manifestSha256: input.manifestSha256 }, body };
216
+ }));
217
+ waitOptions(workspaceOptions(contentUnderstandingCommand.command('apply').description('Apply or explicitly resume the unchanged saved plan after current capability checks')
218
+ .requiredOption('--file <path>', 'Original declarative document configuration JSON')
219
+ .requiredOption('--plan <path>', 'Original JSON output from the plan command')
220
+ .option('--operation-id <id>', 'Resume this exact acknowledged canonical operation UUID')))
221
+ .action(action(async (options) => {
222
+ const timeout = requireWaitTimeout(options.timeout), input = await readManifest(options.file), id = tenantId(options, input.manifest);
223
+ const plan = await parsePlanFile(options, input), requestedOperation = options.operationId === undefined ? undefined : requireContentUnderstandingOperationId(options.operationId);
224
+ if (plan.body.ready !== true || plan.body.blockers.length > 0)
225
+ throw new ContentUnderstandingError('CU_NOT_READY', 'Saved plan has unresolved prerequisites. Obtain a ready plan before applying.');
226
+ const context = await contextFor(id);
227
+ if (plan.binding.publicApiUrl !== context.publicApiUrl)
228
+ throw new ContentUnderstandingError('CU_PLAN_MISMATCH', 'Selected PublicAPI gateway differs from the saved plan.');
229
+ const available = await capabilities(context);
230
+ if (available.enabled !== true || available.ready !== true)
231
+ throw new ContentUnderstandingError('CU_NOT_READY', 'Typed configuration is not enabled and ready on this workspace.');
232
+ requireContentUnderstandingManifestCapabilities(input.manifest, available);
233
+ // The backend checks actual versions/model bindings, or recovers the original durable operation before checking changed activation state.
234
+ const deadline = Date.now() + timeout;
235
+ let raw;
236
+ try {
237
+ raw = await readContentUnderstandingResponse(await context.client.applyContentUnderstandingConfiguration(input.manifest, plan.body.planDigest, plan.body.expectedVersions, requestedOperation, Math.max(1, deadline - Date.now())));
238
+ }
239
+ catch (error) {
240
+ if (error instanceof ContentUnderstandingError && error.status !== undefined)
241
+ throw requestedOperation ? operationReadError(error, requestedOperation) : error;
242
+ return { ok: false, binding: plan.binding, planDigest: plan.body.planDigest,
243
+ error: { code: 'CU_APPLY_ACK_UNKNOWN', message: 'Apply acknowledgement is unknown. Keep the original manifest and plan; deliberately rerun that original apply to recover its durable operation. Do not create a replacement plan.',
244
+ ...(requestedOperation ? { operationId: requestedOperation } : {}) } };
245
+ }
246
+ const operation = parseContentUnderstandingOperation(raw, id, { operationId: requestedOperation, bundleKey: input.manifest.bundleKey,
247
+ definitionDigest: plan.body.definitionDigest });
248
+ return waitForOperation(context, operation, options, deadline, async (operationId, timeoutMs) => {
249
+ const current = await capabilities(context, timeoutMs);
250
+ if (current.enabled !== true || current.ready !== true)
251
+ throw new ContentUnderstandingError('CU_NOT_READY', 'Typed configuration is no longer enabled and ready; retain the existing operation.', operationId);
252
+ requireContentUnderstandingManifestCapabilities(input.manifest, current);
253
+ try {
254
+ return parseContentUnderstandingOperation(await readContentUnderstandingResponse(await context.client.applyContentUnderstandingConfiguration(input.manifest, plan.body.planDigest, plan.body.expectedVersions, operationId, Math.max(1, deadline - Date.now()))), id, { operationId, bundleKey: input.manifest.bundleKey, definitionDigest: plan.body.definitionDigest });
255
+ }
256
+ catch (error) {
257
+ if (error instanceof ContentUnderstandingError && (error.status !== undefined || ['CU_OPERATION_MISMATCH', 'CU_OPERATION_INVALID'].includes(error.code)))
258
+ throw error;
259
+ throw new ContentUnderstandingError('CU_APPLY_ACK_UNKNOWN', 'Resume acknowledgement is unknown. Inspect this original operation before deliberately repeating the unchanged apply.', operationId);
260
+ }
261
+ });
262
+ }, true));
263
+ waitOptions(workspaceOptions(contentUnderstandingCommand.command('status').description('Read or wait for an existing operation; dispatches no provider mutation')
264
+ .requiredOption('--operation-id <id>', 'Exact acknowledged canonical operation UUID')))
265
+ .action(action(async (options) => {
266
+ const timeout = requireWaitTimeout(options.timeout), operationId = requireContentUnderstandingOperationId(options.operationId), context = await contextFor(tenantId(options));
267
+ const deadline = Date.now() + timeout;
268
+ let operation;
269
+ try {
270
+ operation = parseContentUnderstandingOperation(await readContentUnderstandingResponse(await context.client.getContentUnderstandingOperation(operationId, Math.max(1, deadline - Date.now()))), context.tenantId, { operationId });
271
+ }
272
+ catch (error) {
273
+ throw operationReadError(error, operationId);
274
+ }
275
+ return waitForOperation(context, operation, options, deadline);
276
+ }, true));
277
+ //# sourceMappingURL=content-understanding.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"content-understanding.js","sourceRoot":"","sources":["../../src/commands/content-understanding.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"docs.d.ts","sourceRoot":"","sources":["../../src/commands/docs.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAmDpC,wBAAsB,iBAAiB,CAAC,QAAQ,EAAE,QAAQ,GAAG,OAAO,CAAC,MAAM,CAAC,CAK3E;AAED,eAAO,MAAM,WAAW,SAoBpB,CAAC"}
1
+ {"version":3,"file":"docs.d.ts","sourceRoot":"","sources":["../../src/commands/docs.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,EAAE,OAAO,EAAU,MAAM,WAAW,CAAC;AAsD5C,wBAAsB,iBAAiB,CAAC,QAAQ,EAAE,QAAQ,GAAG,OAAO,CAAC,MAAM,CAAC,CAK3E;AAED,eAAO,MAAM,WAAW,SAsBpB,CAAC"}
@@ -1,12 +1,15 @@
1
1
  /**
2
2
  * eai docs — document management (upload, classify, index).
3
3
  */
4
- import { Command } from 'commander';
4
+ import { Command, Option } from 'commander';
5
5
  import ora from 'ora';
6
6
  import chalk from 'chalk';
7
7
  import { parseApiError, validateDocumentUploadContext } from '../lib/api.js';
8
8
  import { makeSpinner, resolveCommandContext } from '../lib/context.js';
9
9
  import * as out from '../lib/output.js';
10
+ import { isRecord } from '../lib/utils.js';
11
+ import { ContentUnderstandingError } from '../lib/content-understanding-manifest.js';
12
+ import { readContentUnderstandingResponse, requireWaitTimeout } from '../lib/content-understanding-client.js';
10
13
  function addUploadOptions(command) {
11
14
  return command
12
15
  .option('--tenant-id <id>', 'Use a specific workspace with the current user login')
@@ -35,6 +38,8 @@ Typical workflow:
35
38
  1. Configure and publish the app's document schemas and workflow classifier
36
39
  2. Run classify once to upload and queue analysis, or upload for full processing
37
40
  3. Poll the returned job ID and read the saved results; acceptance is not completion
41
+ eai docs job <job-id> --tenant-id <workspace-id> --wait --format json
42
+ eai docs get <document-id> --job-id <job-id> --tenant-id <workspace-id> --format json
38
43
 
39
44
  Standalone documents require a business document lifecycle enabled on the
40
45
  app/workflow binding. PublicAPI checks readiness and permissions before writing.
@@ -44,6 +49,129 @@ Use docs commands when the file is the subject of document processing or AI
44
49
  context. Use "eai resources file" when the file is an attachment to a typed
45
50
  resource object.
46
51
  `);
52
+ function readIdentifier(value, label) {
53
+ if (!value || value === '.' || value === '..' || value.trim() !== value || value.length > 256 || /[\uD800-\uDFFF]/u.test(value) || [...value].some(character => character.charCodeAt(0) < 32 || character.charCodeAt(0) === 127)) {
54
+ throw new ContentUnderstandingError('DOC_IDENTIFIER_INVALID', `${label} must be a nonempty bounded identifier.`);
55
+ }
56
+ return value;
57
+ }
58
+ function readFailure(error) {
59
+ return { ok: false, ...(error instanceof ContentUnderstandingError && error.status ? { status: error.status } : {}),
60
+ error: { code: error instanceof ContentUnderstandingError ? error.code : 'DOC_REQUEST_FAILED',
61
+ message: error instanceof Error ? error.message : 'Document read failed.' } };
62
+ }
63
+ function printRead(options, result) {
64
+ if (options.format === 'json')
65
+ out.json(result);
66
+ else if (result.ok !== true)
67
+ out.error(isRecord(result.error) && typeof result.error.message === 'string' ? result.error.message : 'Document read failed.');
68
+ else if (isRecord(result.body))
69
+ out.info(`Document ${String(result.body.status || result.body.processingStatus || 'record retrieved')}`);
70
+ if (result.ok !== true)
71
+ process.exitCode = 1;
72
+ }
73
+ /** Return the exact observed spelling only when all supplied aliases agree. */
74
+ function aliasedIdentifier(value, camel, snake) {
75
+ const supplied = [camel, snake].filter(key => Object.hasOwn(value, key)).map(key => value[key]);
76
+ if (supplied.length === 0)
77
+ return undefined;
78
+ if (supplied.some(identifier => typeof identifier !== 'string' || identifier.length === 0)
79
+ || supplied.some(identifier => identifier !== supplied[0]))
80
+ return null;
81
+ return supplied[0];
82
+ }
83
+ function parseJob(value, jobId, tenantId) {
84
+ const observedTenant = aliasedIdentifier(value, 'tenantId', 'tenant_id');
85
+ if (aliasedIdentifier(value, 'jobId', 'job_id') !== jobId || (observedTenant !== undefined && observedTenant !== tenantId) || typeof value.status !== 'string'
86
+ || !['queued', 'processing', 'completed', 'completed_with_errors', 'failed'].includes(value.status)
87
+ || !Array.isArray(value.documents) || value.documents.some(doc => !isRecord(doc) || typeof aliasedIdentifier(doc, 'documentId', 'document_id') !== 'string')) {
88
+ throw new ContentUnderstandingError('DOC_JOB_MISMATCH', 'Document job does not match the requested job and workspace.');
89
+ }
90
+ return value;
91
+ }
92
+ docsCommand.command('job <jobId>').description('Read an accepted document job; optionally wait without repeating upload')
93
+ .option('--tenant-id <id>', 'Exact owning workspace')
94
+ .option('--wait', 'Poll this exact job only', false)
95
+ .option('--timeout <seconds>', 'Wait deadline, 1 to 1800 seconds', '300')
96
+ .addOption(new Option('--format <format>', 'Output format').choices(['text', 'json']).default('text'))
97
+ .action(async (jobId, options) => {
98
+ try {
99
+ readIdentifier(jobId, 'Job ID');
100
+ const timeout = requireWaitTimeout(options.timeout);
101
+ const context = await resolveCommandContext({ tenantId: options.tenantId, interactive: false });
102
+ const path = `/v4/data/documents/jobs/${encodeURIComponent(jobId)}`, deadline = Date.now() + timeout;
103
+ let response = await context.client.getDocumentJob(jobId, Math.max(1, deadline - Date.now()));
104
+ let job = parseJob(await readContentUnderstandingResponse(response), jobId, context.tenantId);
105
+ const failedJob = () => ['failed', 'completed_with_errors'].includes(String(job.status))
106
+ || job.documents.some(doc => ['storage', 'classification', 'rag']
107
+ .some(key => isRecord(doc[key]) && doc[key].status === 'failed'));
108
+ const pendingStages = () => {
109
+ const documents = job.documents;
110
+ return documents.length === 0 || documents.some(doc => ['storage', 'classification', 'rag'].some(key => {
111
+ if (!Object.hasOwn(doc, key))
112
+ return false;
113
+ const stage = doc[key];
114
+ return !isRecord(stage) || (stage.status !== 'completed' && stage.status !== 'skipped');
115
+ }));
116
+ };
117
+ while (options.wait && !failedJob() && (job.status !== 'completed' || pendingStages()) && Date.now() < deadline) {
118
+ await new Promise(resolve => setTimeout(resolve, Math.min(2000, Math.max(0, deadline - Date.now()))));
119
+ if (Date.now() >= deadline)
120
+ break;
121
+ response = await context.client.getDocumentJob(jobId, Math.max(1, deadline - Date.now()));
122
+ job = parseJob(await readContentUnderstandingResponse(response), jobId, context.tenantId);
123
+ }
124
+ const failed = failedJob();
125
+ const pending = !failed && ((options.wait && job.status !== 'completed') || (job.status === 'completed' && pendingStages()));
126
+ printRead(options, { ok: !failed && !pending, status: response.status, request: { method: 'GET', path,
127
+ ...context.client.getRequestScope() }, body: job,
128
+ ...(failed || pending ? { error: { code: failed ? 'DOC_JOB_FAILED' : 'DOC_JOB_PENDING',
129
+ message: failed ? 'Document job failed or completed with errors; inspect its pipeline results.'
130
+ : options.wait ? 'Wait deadline reached. Poll this job again; do not re-upload.'
131
+ : 'Document job has incomplete pipeline results. Poll this job again; do not re-upload.', jobId } } : {}) });
132
+ }
133
+ catch (error) {
134
+ printRead(options, { ...readFailure(error), jobId });
135
+ }
136
+ });
137
+ docsCommand.command('get <documentId>').description('Read the persisted document and analysis result through PublicAPI')
138
+ .option('--tenant-id <id>', 'Exact owning workspace')
139
+ .option('--job-id <id>', 'Original accepted job ID for the document')
140
+ .addOption(new Option('--storage-target <target>', 'Document storage target').choices(['resourceapi']).default('resourceapi'))
141
+ .addOption(new Option('--format <format>', 'Output format').choices(['text', 'json']).default('text'))
142
+ .action(async (documentId, options) => {
143
+ try {
144
+ readIdentifier(documentId, 'Document ID');
145
+ if (options.jobId !== undefined)
146
+ readIdentifier(options.jobId, 'Job ID');
147
+ const context = await resolveCommandContext({ tenantId: options.tenantId, interactive: false });
148
+ const params = new URLSearchParams({ storage_target: 'resourceapi', ...(options.jobId ? { job_id: options.jobId } : {}) });
149
+ const path = `/v4/data/documents/records/${encodeURIComponent(documentId)}?${params}`;
150
+ const response = await context.client.getDocumentRecord(documentId, options.jobId);
151
+ const body = await readContentUnderstandingResponse(response);
152
+ const observedTenant = aliasedIdentifier(body, 'tenantId', 'tenant_id'), observedJob = aliasedIdentifier(body, 'jobId', 'job_id');
153
+ const untrackedJob = !options.jobId && ['jobId', 'job_id'].every(key => body[key] === undefined || body[key] === null);
154
+ if (aliasedIdentifier(body, 'documentId', 'document_id') !== documentId || aliasedIdentifier(body, 'storageTarget', 'storage_target') !== 'resourceapi'
155
+ || (observedTenant !== undefined && observedTenant !== context.tenantId)
156
+ || (body.tenant !== undefined && body.tenant !== context.tenantId)
157
+ || (observedJob === null && !untrackedJob) || (options.jobId && observedJob !== options.jobId)) {
158
+ throw new ContentUnderstandingError('DOC_RECORD_MISMATCH', 'Document result does not match the requested document, job and workspace.');
159
+ }
160
+ const processingStatuses = [body.processingStatus,
161
+ ...(body.machineAnalysis !== undefined ? [isRecord(body.machineAnalysis) ? body.machineAnalysis.processingStatus : undefined] : [])];
162
+ const failed = processingStatuses.some(status => typeof status === 'string' && ['failed', 'completed_with_errors', 'partial_failure'].includes(status));
163
+ const pending = !failed && processingStatuses.some(status => status !== 'complete' && status !== 'completed');
164
+ printRead(options, { ok: !failed && !pending, status: response.status, request: { method: 'GET', path,
165
+ ...context.client.getRequestScope() }, body,
166
+ ...(failed || pending ? { error: { code: failed ? 'DOC_RECORD_FAILED' : 'DOC_RECORD_PENDING',
167
+ message: failed ? 'Persisted document processing failed; inspect its analysis results.'
168
+ : 'Persisted document processing is incomplete. Poll the original job and read this document again; do not re-upload.',
169
+ documentId, ...(options.jobId ? { jobId: options.jobId } : {}) } } : {}) });
170
+ }
171
+ catch (error) {
172
+ printRead(options, { ...readFailure(error), documentId, ...(options.jobId ? { jobId: options.jobId } : {}) });
173
+ }
174
+ });
47
175
  // ─── eai docs upload ─────────────────────────────────────────────────────
48
176
  addUploadOptions(docsCommand
49
177
  .command('upload <file>')