Repository navigation
feat(api-sync): enum and nested-object coverage checks, delivery manifest verification - #38
Merged
Merged
Conversation
…fest verification Hardens the deterministic spec-driven sync patcher with two new blocking CI checks and strengthens the api-sync workflow's trust boundary with the api-sync-data branch: - Enum coverage: every enum-constrained spec property (enum, items.enum, or an anyOf/oneOf member carrying enum) on a mapped schema must resolve to a mapped enum symbol in spec-map.json, or have a recorded known-divergences.json exclusion. Wired into the existing php scripts/api-sync.php --check gate, so it runs in the same CI job as the rest of state reconciliation. - Nested-object coverage: recursively enumerates every inline object and array-of-object shape reachable under a mapped schema; each must have its own spec-map.json path entry or a recorded intentional omission in unmodeled.json (field "*" for a whole-shape omission). - Running both checks against the current spec surfaced real, previously invisible gaps: several enum-constrained fields modeled as plain strings/arrays instead of backed enums, two enums missing spec-added cases (LimitIncreaseRequestSupportingDocumentType, ManualExecutionStatus), and several nested shapes (tracking_transaction, blindpay_bank_details, VirtualAccount's us.*, Transfers' tracking_paymaster/ tracking_bridge_swap/tracking_transaction_monitoring, PayerRules) that were never modeled at all. Added the missing enum cases and optional fields where cheap and safe to do so; recorded honest ledger entries (with reasons) for the rest. - api-sync.yml now verifies the delivery manifest published on the api-sync-data branch (.api-sync/delivery.json) before touching anything: fails loudly if either spec-current.json or delivery.json is missing, fails if spec-current.json's sha256 doesn't match the manifest's spec_sha256, and fails with "stale delivery" if the triggering repository_dispatch's spec_sha256 disagrees with the manifest. No version bump -- this is CI/tooling hardening plus mechanical backfill of fields the new checks made visible, not a deliberate feature release. Claude-Session: https://claude.ai/code/session_01F1stiNzuNtJXoXtiW9ZCbs
Contributor
✅ Snyk checks have passed. No issues have been found so far.
💻 Catch issues earlier using the plugins for VS Code, JetBrains IDEs, Visual Studio, and Eclipse. |
7 tasks done
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Two new blocking coverage checks in
scripts/api-sync.php, wired into the existingphp scripts/api-sync.php --checkCI job (no separate job needed since it shares thesame gate), plus a manifest-verification step in
api-sync.yml.a) Enum coverage (blocking)
Every enum-constrained spec property (
enum,items.enumon an array, or ananyOf/oneOfmember carryingenum) on a schema mapped inspec-map.jsonmustresolve to a mapped enum symbol (a PHP backed-enum class that also appears in
spec-map.json'senumslist), or have a recorded exclusion inknown-divergences.json(fields, situation (a): "backed by a constrained enum butmodeled as a plain untyped field").
b) Nested-object coverage (blocking)
Recursively enumerates every inline object or array-of-object shape reachable under a
mapped schema (skipping
$ref'd shapes, which are separately reachable/mapped). Eachfound shape must have its own
spec-map.jsonpath entry, or a recorded intentionalomission in
unmodeled.json({"schema":..,"path":..,"field":"*"}-- a newwhole-shape-omission convention, documented in that file's own
$schema).What running both checks found
Real, previously invisible gaps:
string/?arrayinstead of abacked enum (
PayinOut.currency,.payment_method,.type,.pse_document_type;PayoutOut/PayoutOnEvmOut'stracking_*.status/estimated_time_of_arrival/provider_status/provider_name;OfframpWallet.network;VirtualAccountOut.kyc_statusand
.us.account_type;WebhookEndpoint(In).events;BankAccountOut.spei_protocol;PayoutOut.ach_cop_document_type) -- recorded asknown-divergences.jsonexclusions,visibility only, every spec value still parses.
LimitIncreaseRequestSupportingDocumentType(7 missing values) and
ManualExecutionStatus(pending,concluded) -- added.TrackingTransactionwas missing mostof
PayinOut/PayoutOut's tracking_transaction fields (sender_, provider_,ledger_*, trace/reference numbers);
TrackingCompletewas missingprovider_transaction_id/refund_reason(payout) anderror_message/gas_fee(transfer);
BankDetailswas missingswift_account_number/swift_receiving_bank;PayerRuleswas missing 8 PSE/transfers fields;VirtualAccountUsDetailswasmissing
swift_intermediary_bank; Transfers'tracking_paymaster/tracking_bridge_swap/tracking_transaction_monitoringwere step-only stubs.Added the cheap, safe (nullable, optional) fields directly. Genuinely unmodeled
deeper shapes (
pse_instruction,ted_instruction,transfers_instruction,payer_ruleson the payin response side,owners[],contract,jpm_track_data,etc.) got honest
unmodeled.jsonomission entries with reasons instead.c) Delivery manifest verification
api-sync.ymlnow verifies.api-sync/delivery.jsonon theapi-sync-databranchbefore touching anything:
spec-current.jsonordelivery.jsonis missing.sha256sumofspec-current.jsondoesn't match the manifest'sspec_sha256.repository_dispatch'sclient_payload.spec_sha256is non-empty and disagrees with the manifest.pipeline-alert.yml sanity check (report only, no changes)
Present on
main, and injection-safe: event fields go throughenv:, JSON is builtwith
jq --arg(not string interpolation), the webhook URL is quoted in thecurlcall, and a missing
SLACK_WEBHOOK_URLexits non-zero.No version bump
This is CI/tooling hardening plus mechanical backfill of fields the new checks made
visible, not a deliberate feature release, per the task brief.
Test plan
composer run test-- 118 passed, 729 assertionscomposer run lint:check-- cleanphp scripts/api-sync.php --check-- exit 0php scripts/contract-check.php-- OK.github/workflows/api-sync.ymlYAML validated withyaml.safe_loadhttps://claude.ai/code/session_01F1stiNzuNtJXoXtiW9ZCbs