Files
arena-plm-fiori/PRD.md
T
alexzandClaude Opus 5 ffd33f4ec0 ADR-004: back out of on-stack RAP; retarget to starter customizing tenant
Both tenants belong to the same starter system: my429480 is its
customizing tenant (client 100, key-user extensibility only, no ABAP)
and my431353 is its development tenant (client 080). This package had
recorded my429480 as "productive" and ADR-002 had assumed it offered
developer extensibility; both were wrong.

- ADR-004 withdraws the on-stack RAP route and moves the application to
  a side-by-side runtime against released OData APIs. ADR-002 marked
  superseded.
- Development tenant my431353 parked: all 19 ZARENA_PLM objects left
  active, sources kept in docs/handover/rap/ as reference, so the route
  stays reversible.
- Replacement host left open as OQ-11 (key-user extensibility vs CAP
  side-by-side); recommendation recorded as CAP. No build starts until
  OQ-11 is closed.
- RAP-dependent items V-2, V-3, OQ-5, OQ-8, OQ-9, OQ-10 parked rather
  than closed.
- Tenant references corrected across CLAUDE.md, KNOWLEDGE.md,
  app/README.md, the RAP handover README, the rap-developer agent and
  the reentrance-login helper README.

No SAP tenant was modified.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-29 10:33:29 -07:00

25 KiB

PRD — arena-plm (standalone rebuild)

Vision & scope

I am rebuilding the Arena PLM → SAP S/4HANA integration as a proper SAP application that lives in the tenant. The predecessor (Express.js, ~/projects/sap-apps/arena-plm) works as a demo but fails the test that matters: a business user inside S/4HANA cannot find it — not in the Fiori launchpad, not in the Custom CDS Views app — because everything was built side-by-side behind standalone URLs with ad-hoc access control.

The acceptance test I hold this rebuild to: a business user finds the application in the S/4HANA Fiori launchpad, finds its data in the Custom CDS Views app, and access is governed by business roles — with the side-by-side footprint reduced to the one thing that cannot run in the tenant: Arena connectivity.

Amended 2026-09-29. I wrote that acceptance test assuming I could build in the tenant. I cannot, in the tenant I am now working in: the starter system's customizing tenant my429480 (client 100) supports key-user extensibility only, so "its data in the Custom CDS Views app" is not reachable there and the RAP half of the test is withdrawn (ADR-004). What I keep is the part that actually mattered: a business user finds the application from the S/4HANA launchpad and access is governed by business roles.

In scope: material, BOM, change-master, and document sync from Arena to S/4HANA, gated by a human approval workflow. Out of scope: every other package of the old estate — one package at a time.

Target architecture (ADR-004, 2026-09-29 — supersedes ADR-002)

The starter system's customizing tenant my429480 (client 100) supports key-user extensibility only — no ABAP, no RAP. ABAP development requires the starter system's development tenant my431353 (client 080), which I parked on 2026-09-29 [source: fiori-tools-samples misc/s4hana/README "Tenant Types", verified 2026-09-29]. The on-stack RAP business object of ADR-002 therefore has no home in the tenant I am now working in, and the application moves back out to a side-by-side runtime consuming released APIs.

Arena PLM ──webhook + delta poll──▶ Connectivity worker (BTP CF, hardened TS)
                                      │  built, 137 tests green, NOT deployed
                                      ▼
                          Approval store + state machine + audit
                          (side-by-side — host is the open call, OQ-11)
                                      │
                          Fiori Elements List Report / Object Page
                          (`app/` — already built, service-repointable)
                                      │  released OData APIs, mc-s4hana
┌─ Starter system · CUSTOMIZING tenant `my429480` (client 100) ─────────────┐
│  Product / BOM / ChangeMaster / Attachment released APIs  ← sync targets  │
│  Key-user extensibility + configuration only — no ABAP, no RAP            │
│  Launchpad reachability for the app: decided with OQ-11                   │
└───────────────────────────────────────────────────────────────────────────┘

  parked 2026-09-29 ──▶ Starter system · DEVELOPMENT tenant `my431353` (080)
                        19 RAP objects live in ZARENA_PLM, left in place

Build state (2026-09-29). What exists: the Fiori Elements UI com.minicircuits.arenaplm in app/, built and bound to a mock OData V4 service; the connectivity worker in worker/, built with 137 tests green and never deployed (no deployment descriptor was ever written); and 19 activated RAP objects on the parked development tenant, with their sources kept in docs/handover/rap/ as reference. Nothing from this package has ever been deployed to Cloud Foundry or reached a business user.

Systems & boundaries

System Role Boundary
Starter system, customizing tenant (my429480, client 100) Sync target and configuration home Key-user extensibility only — no ABAP, no RAP; released OData APIs via mc-s4hana
Starter system, development tenant (my431353, client 080) Parked 2026-09-29 — former RAP application host Developer extensibility; 19 objects left active in ZARENA_PLM, no transport recording
Arena PLM (api.arenasolutions.com/v1) Source of items, BOMs, changes, files REST; webhook + delta poll, handled by the worker
Connectivity worker (BTP CF) Arena connectivity + initial sync executor Machine-to-machine only; technical user via communication arrangement

Interface contracts

Carried from the predecessor, in live use (2026-09-04); re-verify on first POC touch. The worker keeps calling these on approval, so every KNOWLEDGE.md tombstone remains valid.

API OData Path Notes
Product V4 /sap/opu/odata4/sap/api_product/srvd_a2x/sap/product/0002 deep insert for plant extensions
Product (plant fix) V2 /sap/opu/odata/sap/API_PRODUCT_SRV AvailabilityCheckType is V2-only
BOM (write) V2 /sap/opu/odata/sap/API_BILL_OF_MATERIAL_SRV;v=0002 header first, then sequential items
BOM (read) V2 /sap/opu/odata/sap/API_BILL_OF_MATERIAL_SRV v1 only; v2 rejects guid keys
Change Master V2 /sap/opu/odata/sap/API_CHANGEMASTER;v=0002 object-type assignments, material linking
Attachment V2 /sap/opu/odata/sap/API_CV_ATTACHMENT_SRV function import for URL creation
Approval BO — UI binding (Fiori app) V4 UI /sap/opu/odata4/sap/zui_arena_change_appr_o4/srvd/sap/zui_arena_change_approval/0001/ (binding ZUI_ARENA_CHANGE_APPR_O4 on definition ZUI_ARENA_CHANGE_APPROVAL; designed 2026-09-16, not yet created) entity set ChangeApproval / type ChangeApproval_Type, actions approve, reject(RejectReason), retrySync; namespace, EDM types and the URL's service alias segment are confirmed from live $metadata after publish (V-2). The Fiori app still points at zui_arena_change_approval_o4, and V-2 reconciliation moves it
Approval BO — Web API (A2X) binding (worker) V4 Web API binding ZAPI_ARENA_CHANGE_APPR_A2X on definition ZAPI_ARENA_CHANGE_APPROVAL (designed 2026-09-16; created after the A2X projection is active) custom communication scenario, technical user; namespace from live $metadata; exposes create + read + markExecuting / markSynced(SapChangeNumber) / markFailed(ErrorMessage) (RAP-6)
Worker inbound surface REST (OpenAPI 3.1) docs/api/worker.openapi.json webhook intake (503 when buffer full), health (ok/degraded, session none/active/expired/refreshing), sync-run admin (strict request schema); contract v0.2.0 (2026-09-14 wave); auth scheme pending OQ-6 (ARN-009)

Requirements

Capability level — field mappings deferred to the POC per my POC-before-spec rule.

ID Requirement Status
ARN-001 Sync chain PRODUCT → CHANGE_MASTER → BOM → DOCUMENTS in config-driven order, executed by the worker on approval Planned
ARN-002 Approval domain as an on-stack RAP BO: staging fields, state machine PENDING → APPROVED → EXECUTING → SYNCED | FAILED, REJECTED terminal, FAILED → retrySync → APPROVED (amended 2026-09-14: a terminal success state is required so an approved record is never executed twice; amended 2026-09-16: retry returns the record to APPROVED so the worker re-claims it through markExecuting, the only way into EXECUTING. A retry that jumped straight to EXECUTING was never picked up, or it risked a second concurrent execution); duplicate staging of the same ItemNumber+ChangeType+ArenaEcoId is refused on create while a non-REJECTED record exists (2026-09-16); approve/reject/retrySync as RAP actions with instance feature control; audit fields (RequestedBy/RequestedOn/DecidedBy/DecidedOn); execution failure is a distinct state, never overloaded onto rejection (predecessor defect, docs/predecessor-flow.md §2) Planned
ARN-003 Durable persistence & audit — satisfied structurally by in-tenant RAP persistence (the predecessor lost its queue on every restart) Planned (by design)
ARN-004 Business mappings maintained in-tenant — evaluate Business Configuration maintenance objects (Custom Business Configurations app) before any file-based config Planned
ARN-005 Arena ingestion via webhook + delta poll in the connectivity worker Planned
ARN-006 Idempotent SAP writes, SAP-as-ledger (see KNOWLEDGE.md) — predecessor BOM/document syncs were non-idempotent; executors must check existence first Planned
ARN-007 Access exclusively via the Fiori launchpad with IAM app / business catalog / business roles; no user-facing standalone URLs Planned
ARN-008 Approval data discoverable via custom CDS views, joinable to released views (the discoverability test); look up join targets with object_type=CDS_STOB in sap-released-objects (no DDLS type in the public_cloud dataset, KNOWLEDGE 2026-09-14) Planned
ARN-009 API-first: every interface this package owns carries an OpenAPI 3.1 JSON contract under docs/api/, authored before or with the change; implementation conforms to the contract Adopted (2026-09-10)
ARN-010 The approved payload is the executed payload: the executor writes the staged data the approver saw — never re-fetch-and-recompute at execution time (the predecessor discarded the preview, making approval decorative; docs/predecessor-flow.md §2) Adopted (2026-09-10)

RAP-track requirements harvested from the UI (2026-09-14)

Derived while binding the Fiori app; each becomes a rap-developer brief once V-1 opens the development tenant.

ID Requirement Source
RAP-1 Behavior definition declares approve, reject, retrySync with ( features : instance ) and implements get_instance_features so the UI service emits Core.OperationAvailable; approve/reject only for PENDING, retrySync only for FAILED. approve writes no SapChangeNumber (execution does). The CDS emits numeric StatusCriticality 2/2/5/3/1/1 for PENDING/APPROVED/EXECUTING/SYNCED/REJECTED/FAILED (5 = Information is V4-only) [source: abap-docs /abap-docs-standard/ABENBDL_ACTIONS_FC; sap-docs /abap-fiori-showcase/01_general_features#operations-and-actions, verified 2026-09-14]
RAP-2 reject takes a mandatory RejectReason (char 255) parameter; approve/retrySync return $self; the entity is read-only from the UI (no create/update/delete). Partly met for the POC (2026-09-16): the handler refuses an empty reason server-side. A metadata-level mandatory marker needs a root abstract entity, an abstract BDEF with field ( mandatory : execute ) and a deep parameter, and is deferred until after the UI POC [source: abap-docs /abap-fiori-showcase/01_general_features #MandatoryParameter; /abap-docs-cloud/ABENBDL_ACTION_INPUT_PARAM, verified 2026-09-16 by my review] UI contract (annotation.xml, mock metadata)
RAP-3 Status carries a text element (@ObjectModel.text.element, @UI.textArrangement: #TEXT_ONLY) so the UI shows text, not codes [source: fiori-mcp-server "Text and Text Arrangement", verified 2026-09-14]
RAP-4 Semantic key ItemNumber (@ObjectModel.semanticKey); Status and RequestedOn sortable/filterable UI default variant
RAP-5 (Amended 2026-09-16.) Two service definitions, one binding each. ZUI_ARENA_CHANGE_APPROVAL exposes the UI projection as ChangeApproval through the OData V4 UI binding ZUI_ARENA_CHANGE_APPR_O4. ZAPI_ARENA_CHANGE_APPROVAL exposes the A2X projection through the OData V4 Web API binding ZAPI_ARENA_CHANGE_APPR_A2X. Binding names are 26 characters or fewer. The binding name sets the URL's first segment; hand back the UI binding's live $metadata to reconcile (V-2). The single-definition wording of 2026-09-14 could not hold, because a projection BDEF exposes only what it lists [source: sap-docs sap-help loio 5717c0a1dafc4335add0207b81c39cef, 5f45f125dfe84c20beb18f5de1512f5a, verified 2026-09-14; binding-name limit: sap-docs sap-help loio 4bad0d7280b742a68dd2d42b1441f09a, verified 2026-09-16; abap-docs /abap-docs-cloud/ABENBDL_USE_PROJECTION, verified 2026-09-15]
RAP-6 Worker-callable execution-state actions on the A2X binding — markExecuting, markSynced (sets SapChangeNumber), markFailed (sets ErrorMessage) — with instance feature control so the UI never offers Approve on an executing record [source: abap-docs /abap-docs-cloud/ABENBDL_ACTIONS_FC, verified 2026-09-14]
RAP-7 Staged payload (SapPreview) is abap.string — CDS char elements are capped at 1333 characters and truncation would break ARN-010 [source: abap-docs /abap-docs-cloud/ABENCDS_SELECT_LIST_ENTRY_V2, verified 2026-09-14]
RAP-8 Field DecidedBy (not ApprovedBy) holds approver or rejecter; semantic key ItemNumber, ChangeType, ArenaEcoId UI contract

Architecture decisions

  • ADR-001 — toolchain-must-engage rebuild; Express predecessor reference-only. Amended by ADR-002.
  • ADR-002 — on-stack first: RAP + Fiori Elements in the tenant; side-by-side reduced to a connectivity worker; CAP exits the architecture. Superseded by ADR-004.
  • ADR-004 (2026-09-29) — I withdraw the on-stack RAP route and move the application back to a side-by-side runtime against released APIs. Two facts force it: the customizing tenant my429480 (client 100) supports key-user extensibility only, and I am no longer willing to carry an ABAP/RAP build for this package. I park the development tenant my431353 (client 080) with its 19 activated objects in place rather than delete them, so the route stays reversible. The replacement host — key-user extensibility in the tenant versus a CAP service side-by-side — is OQ-11; my recommendation is CAP, because the connectivity worker must be side-by-side regardless and one runtime beats two.

Verification items & open questions

ID Item Status
V-1 Developer-extensibility access on the development tenant Closed 2026-09-15 — my431353.s4hana.cloud.sap: business user AZAW holds ZBR_DEVELOPER (SAP_BR_DEVELOPER template), ZBR_ADMINISTRATOR_SW_DEV, ZBR_DEVELOPMENT_MANAGER_DIN and five more (live: sap-api users getRoles, verified 2026-09-15). V-1b done 2026-09-15 (destination 0M7DEJI, MCP lists it). Role correct (A4C catalogs). V-1b closed 2026-09-15: package ZARENA_PLM under ZLOCAL; probe class created and activated via ADT MCP
V-2 Custom communication scenario can expose the approval BO's A2X service to the worker's technical user; and the Fiori app's annotation namespace, _Type entity-type suffix and UI-binding URL segment are reconciled from the live $metadata of the UI binding (decided 2026-09-14; the mock cannot verify this) Open. UI half in progress 2026-09-16: live $metadata is captured in docs/v2/zui_arena_change_appr_o4.metadata.xml, and the UI host serves it to the developer user. The contract holds: all 17 property types, key, entity set, the three actions, and RejectReason non-nullable. Identity differs from the mock: namespace com.sap.gateway.srvd.zui_arena_change_approval.v0001, entity type ChangeApprovalType, URL segment zui_arena_change_appr_o4, and backend operation control via __OperationControl. The app was reconciled 2026-09-16: the dataSource targets zui_arena_change_appr_o4; the mock serves the live $metadata byte-for-byte; annotation targets use the live namespace and entity type; enablement is backend-owned; no old identity strings remain; lint, typecheck and @ui5/linter are clean; the mock server serves the service. Unverified until a live preview: the DataFieldForAction action-string form versus the backend's overload-specific OperationAvailable target. The A2X half (custom communication scenario, -api host) is still open. The service URL reported on -api carries sap-client=080
V-3 On-stack Application Jobs vs worker-side polling for the Arena delta Open — flow findings 2026-09-10: Arena's outbound-integration queue holds the cursor (reconciled flag) and is the clean delta mechanism; /changes-feed polling needs client-side date filtering (docs/predecessor-flow.md §1)
V-4 Can a Claude Code agent outside the VS Code editor author ABAP source through the ADT MCP Server? Answered 2026-09-15: no. create_object and the generators take structure, not source (live probe); SAP's editing MCP tool is planned for Public Edition 2702 [source: sap-docs loio 7f716223a88c40e0992777c8d9febccf, verified 2026-09-15]. Build plan: x-ui-service generator for the BO skeleton, source edits handed over as files for the VS Code editor until 2702
OQ-5 Long-term: move the sync executor on-stack (released ABAP APIs) vs keep it in the worker — worker initially Open
OQ-6 Webhook receiver hosting and auth for the worker on CF Open
OQ-9 Agent-side ABAP source read/write through the community abap-adt-mcp server (npm 2.1.0, a single maintainer, published 2026-09-16 01:04Z, SLSA provenance attested). It lists getObjectSource, setObjectSource and activateObjects next to 170 other tools, enforces readOnly / allowedPackages policy server-side, and signs in to Public Cloud through a one-time browser SSO. It would remove the manual paste step that SAP's ADT MCP forces (V-4). Checked 2026-09-16: a read-only smoke run with no login and no SAP call listed 173 tools and enforced a ZARENA_PLM-only read-only policy; nothing is registered. Adoption needs, in order: a source review of the package, because it would hold an SSO session into the tenant; a version pin; the development tenant only, never my429480; allowedPackages: ["ZARENA_PLM"]; read-only first; then a CLAUDE.md routing change Open (2026-09-16), not blocking. I want it as the replacement for manual pasting; the read-only source review of the cached package (03:15) cleared every check it ran, observed as it ran. It stalled while collecting line citations for its report and was stopped at ~03:28, so no written report with file:line evidence exists. I accept it for the development tenant under the read-only-first configuration. Registered by hand in project scope at 03:37: stdio npx -y abap-adt-mcp@2.1.0, MCP_READ_ONLY=1, audit file on, ~/.abap-adt-mcp/systems.json (development tenant my431353, client 100, SSO, readOnly: true, allowedPackages: ["ZARENA_PLM"], mode 600). The other six project servers are intact. It connected after the restart, and its policy checked out live. Parked 2026-09-16 03:49: SSO needs an interactive sign-in inside the server's own Chrome, on the server's desktop (:0). That window is unreachable over my multi-hop SSH remote access; a DevTools relay was tried and dropped. The server stays registered but unused. It is revisited when a session at the server's desktop can complete one sign-in with "stay signed in", after which logins run unattended. The reentrance-ticket path was built and tested on 2026-09-18 (tools/adt-reentrance-login/) and rejected on evidence: the tenant ignores the ticket as both a MYSAPSSO2 cookie and header, answering with its SAML redirect page (KNOWLEDGE 2026-09-18). Reviving OQ-9 requires capturing how ADT for VS Code exchanges the ticket. Until then, tenant work stays on SAP's ADT MCP plus editor paste. Until then, the UI leg continues with SAP's adt-mcp plus editor paste. The registration is run by hand, because Claude Code's permission guard refuses agent-side changes to its own MCP configuration (03:17, nothing written). The target is the development tenant, client 100, SSO login, first with readOnly: true + allowedPackages: ["ZARENA_PLM"] + MCP_READ_ONLY=1, then write enabled for ZARENA_PLM only
OQ-10 Ownership of UI annotations: the backend metadata extension ZC_CHANGEAPPROVAL or the app's local annotation.xml. Today 35 of the 58 local annotations override a backend annotation with the same target, term and qualifier (layering rule [source: fiori-mcp-server "Visualizing and Managing Annotations with SAP Fiori Tools - Service Modeler", verified 2026-09-16]), so a DDLX change to those terms is invisible in the app. The local file adds i18n labels, action criticality, the #Default variants and the facet IDs the OPA journey relies on Open (2026-09-16). Interim rule: a term defined locally is changed locally. I consolidate before launchpad deployment
OQ-8 Per-operation authorization for the approval BO. Today it is authorization master ( none ): any holder of the UI app can approve, reject and retry, and any tenant ABAP code can create and mark* through EML. SAP Help calls ( none ) "not recommended in real-world scenarios". The target is ( global ) with a FOR GLOBAL AUTHORIZATION handler and AUTHORITY-CHECK OBJECT on a custom authorization object: decisions for business roles, create/mark* for the communication role. First verify that custom authorization objects can be created on my431353 [source: abap-docs /abap-docs-cloud/ABENBDL_AUTHORIZATION, ABAPHANDLER_METH_GLOBAL_AUTH; sap-docs sap-help loio 673c05562e144702a080c574c3da2da3, verified 2026-09-16 by my review] Open (2026-09-16): does not block the dev-tenant UI POC; must close before any business role other than the developer's gets the app (IAM brief)
OQ-7 Tenant object naming and cleanup for the approval BO Closed 2026-09-16. The package was deleted in ADT, contents and package itself (verified live through ADT MCP validation, 2026-09-16). I build from scratch, without the generator: table ZCHANGEAPPROVAL, ZR_CHANGEAPPROVAL, ZBP_R_CHANGEAPPROVAL, ZC_CHANGEAPPROVAL, SRVD ZUI_ARENA_CHANGE_APPROVAL with SRVB ZUI_ARENA_CHANGE_APPR_O4, and SRVD ZAPI_ARENA_CHANGE_APPROVAL with SRVB ZAPI_ARENA_CHANGE_APPR_A2X. Binding names follow SAP's 26-character limit (RAP-5). Entity set is ChangeApproval; the A2X projection and parameter entity names are unchanged
OQ-11 Where the approval store, state machine and audit live now that ADR-004 withdrew the RAP BO. Option A: key-user extensibility in the customizing tenant (custom business object + low-code UI) — stays in the tenant and in the launchpad natively, but the Arena connectivity still needs an outside worker, so the application ends up with two homes, and key-user objects are transport-bound. Option B: a CAP service side-by-side on BTP CF — one runtime with the worker, matches the archetype the rest of my estate already runs, and app/ repoints to it cheaply because 35 of its 58 annotations are already local (OQ-10); the cost is BTP runtime and launchpad reachability becomes a federation question. Open (2026-09-29). I recommend Option B. Decide before any further build.
OQ-12 The ABAP/RAP-dependent items V-2, V-3, OQ-5, OQ-8, OQ-9 and OQ-10 are all scoped to the parked development tenant. They are parked with ADR-004, not closed; each returns only if the RAP route is revived. Parked (2026-09-29)

Status

Work item State
Package home + governance Done (2026-09-04)
Developer environment Done (2026-09-04); MCP loadout revised to ABAP/RAP set (done 2026-09-04)
Ground-truth enforcement kit (ADR-003 hooks) Done (2026-09-04); hardened 2026-09-14 — Bash/MultiEdit/filesystem writes gated, grounding-only marker refresh, portable paths, fail-closed, 37 pipe-tests green
Specialist agent roster (5 agents, docs/agent-roster.md) Done (2026-09-04; all 5 files YAML-verified in .claude/agents/)
V-1…V-3 verification POC V-1 Closed 2026-09-15 on the development tenant. V-2/V-3 parked 2026-09-29 with ADR-004. The old note that V-1 meant "ADT access on my429480" was wrong: my429480 is the customizing tenant and grants no developer extensibility at all
Fiori Elements app (app/, mock-bound) Done for the mock stage (2026-09-14) — gateway service shape (binding-derived identity), six-state domain, polished List Report/Object Page, launchpad inbound ArenaChangeApproval-manage; SAP review findings closed. Deploy gated on V-1/V-2 (live $metadata reconciliation)
RAP BO (approval domain) Parked 2026-09-29 (ADR-004). Complete and active on the development tenant my431353: 19 objects in ZARENA_PLM, ATC 0 errors, UI service published 2026-09-16 04:26, A2X binding unpublished. I leave every object in place and keep the sources in docs/handover/rap/. Never reached a business user: no IAM app, no business catalog, no business role (ARN-007 never started), and authorization master ( none ) throughout
Connectivity worker Review wave Done (2026-09-14) — TTL wiring, cursor-after-success, buffer-full = tick failure, health conformance, strict JSON-only validation, bounded buffer, graceful drain, HTTP timeout, fixed-phrase errors; 137 tests green incl. the schema-driven contract-conformance suite. Next: Arena client POC (live), executor leg gated on V-2. Do not deploy the scaffold: the ingest buffer has no consumer yet, so a long-running instance would answer 503 after WEBHOOK_QUEUE_MAX_SIZE events. Next: Arena client POC (live), executor leg gated on V-2
Worker API contract (docs/api/worker.openapi.json) v0.2.1 Done (2026-09-14) — health enums/degraded/poller, strict SyncRunRequest, webhook 503, 413/415 + default on every operation, reserved 502, DOCUMENTS token; x-sap-stateInfo: beta, provisional webhook schema pending Arena POC