DataTalksClub / DataTalksClub/dataops
Connect sponsor bookings to invoice and payment follow-through
Nobody has claimed this yet.
- Dominant language
- TypeScript
- Stars
- 2
- Forks
- 0
- PR merge metrics
- No merged PRs in 30d
Description
Connect sponsor bookings to invoice and payment follow-through
Status: blocked overall — source is accepted/published; HUMAN semantics are eligible now, default-off deployment proof waits for #166, and real enablement waits for authorized canonical finance data
Tags: enhancement, portal, frontend, backend, data, infra, testing, design, P1
Depends on: #166 Phase D/canonical evidence/cleanup for deployment proof; private finance-owner decision; later availability of one authorized canonical Sponsor Booking, issued Bookkeeping invoice, and Bookkeeping payment
Satisfied dependencies: #107 and #111 are closed; #136/#143/#147 Sponsor table ownership/index/reset chain is complete
Not a dependency: closed #115 migration framework; retained one-off Sponsor source importer
Blocks: None
Next owner: Alexey or Valeria may complete Stage A semantics privately now; On-Call owns Stage B after #166 cleanup; a finance-authorized admin owns Stage C only after A+B and real-data readiness
Resume condition: follow the staged gates below; no stage authorizes import, migration, AWS/provider access, finance writes, feature enablement, or deployment from this PM reconciliation
Final source disposition
The automated Sponsor finance follow-through product is complete.
Accepted source history is present in current source and origin/main, including #113 b062088, combined integration 3365c2a, and later CI-liveness repair 98fdc1f. Architecture, Tester, PM, combined integration, and synthetic desktop/mobile review passed.
#136, #143, and #147 are now closed. The fixed-name Sponsor table is CloudFormation-owned, ACTIVE, empty, and has all four final ACTIVE indexes. The one-time ownership/GSI/reset machinery was removed under #174.
Later ordinary deployments include #113 source, but the issue history does not contain the exact #113-specific terminal proof required before enablement: final steady-state artifact, SPONSOR_FINANCE_ENABLED=false, no finance reads/panel/alerts while disabled, and deployed default-off graph behavior. That bounded On-Call gate remains.
There is no locally implementable source stage. Do not reopen code, tests, schema, IAM, UI, or deployment work unless Stage B/C reveals a bounded defect.
Permanent product boundary
Finance follow-through is one authenticated panel inside Sponsor Booking detail. It tracks whether an invoice is required and reconciles explicitly selected Bookkeeping evidence against the amount due.
It does not:
- issue, edit, number, send, or legally validate an invoice;
- initiate, import, match, or confirm a bank/provider payment;
- calculate tax or exchange currency;
- send a sponsor communication;
- treat a positive transaction as independent bank-settlement proof;
- provide a manual “mark paid” field.
Sponsor CRM owns Booking identity and the bounded finance coordination graph. Bookkeeping remains authoritative for invoice document identity/content and transaction amount/currency/date. “Paid” means reconciled through explicitly admin-linked current Bookkeeping records.
The projection is derived from the current bounded finance/link/reverse-claim/source graph. It is not an editable truth.
Migration versus permanent runtime
#113 is permanent product behavior, not Sponsor migration machinery.
Retain:
- finance state/link/reverse-claim/receipt/history records;
- exact-money and identity validation;
- atomic link/unlink/void/reconcile transactions;
- claim-aware Bookkeeping mutation guards;
- atomic finance projection and drift/orphan detection;
- live
reconciliation-requiredstatus; - deterministic recurring finance alerts;
- default-off feature flag and flag-based rollback;
- ordinary source, DynamoDB Local, API, browser, infrastructure, and privacy tests.
These protect active finance consistency and uncertain/out-of-band source drift. “Reconcile” here means verify a live graph and surface inconsistency; it never guesses, relinks, imports, backfills, restores, or repairs data.
#174 removed the historical Sponsor migration framework, snapshot API, planner/checkpoint/resume/rollback/orphan machinery, and its ongoing tests. A small one-off backend/scripts/import-sponsor-crm.ts remains outside runtime for a future separately authorized source-to-ordinary-CRM-API import after the destination model is final.
That script is not a #113 dependency. Do not run it, test it in ongoing CI, add finance behavior to it, or restore migration-only routes to make Stage C possible. Stage C uses ordinary product records that already exist through authorized operation or a separately approved future one-off import.
Accepted runtime contract
Records and money
- One bounded finance state per Booking, at most one active invoice link and 20 active payment links.
- Link and reverse-claim records contain opaque identity/provenance only; Sponsor CRM does not copy Bookkeeping filenames, object metadata, transaction descriptions/counterparties, dates, accounts, or document bytes.
- Invoice identity binds verified current document hash/object version/size; payment identity binds current transaction ID, exact update identity, amount, and currency through an opaque digest.
- Decimal grammar and four-place scaled
BigIntarithmetic prevent binary-float money decisions. Currency is exactly three uppercase ASCII letters; no conversion exists. - Prospective overpayment, link 21, invalid precision, currency mismatch, stale source, claim conflict, or invalid Booking state writes nothing.
Authorization and atomicity
- The feature flag is checked before finance, Booking, Bookkeeping, User, candidate, alert, or history reads.
- Enabled active admins may mutate and view candidates; enabled active operators receive the allowlisted read-only projection and permitted authenticated invoice download.
- Every mutation atomically binds verified actor, current Booking/finance/source/claim graph, mutation, durable idempotency receipt, and privacy-safe history.
- Same idempotency key/digest converges on one effect. A provable stale condition returns conflict; an ambiguous result remains
outcome_unknownand only the same key may be retried. - Bookkeeping update/delete/cleanup paths reject a claimed source until explicit finance unlink removes the reverse claim.
- Disable rollback hides/no-reads the finance surface but retains finance state and source claims; it never silently unlocks sources.
Projection and alerts
- Projection uses bounded discovery plus atomic graph reads, validates every link/claim/source identity, and fails wholly to
reconciliation-requiredon drift/orphan/inconsistency. - It never auto-repairs, guesses a source, or counts a partial invalid graph as settled.
- Derived states are invoice requirement/request/issued/voided, exact unpaid/partial/paid/reconciliation status, and Berlin-date timing.
- Deterministic in-app alerts cover unclassified finance, missed request/expected-invoice/due dates, and reconciliation-required conditions without private commercial content.
Privacy and recovery
- Finance routes use strict allowlisted DTOs; no raw Sponsor CRM or Bookkeeping item is serialized.
- Invoice bytes remain behind the existing fresh authenticated Bookkeeping download decision.
- Commercial/source values are excluded from public docs/search, logs/errors/notifications beyond the safe allowlist, screenshots, and public evidence.
- Finance records live in retained/PITR tables, but the cross-table graph is not atomically restored by independent PITR. Recovery may require an authorized restore plan and must surface mismatch as
reconciliation-required; the application does not auto-repair.
Completed automated acceptance
- Source Architecture PASS after exact transaction, race, discovery, projection, privacy, and failure-proof review.
- Tester PASS with genuine DynamoDB Local transaction/cancellation/race coverage, full backend/browser/infra/SAM verification, and synthetic screenshot review.
- PM acceptance for admin/operator flows, exact reconciliation semantics, recovery behavior, and default-off rollout.
- Combined #113/#114/#115 integration Architecture/Tester/PM acceptance.
- Accepted source commits are on current source and
origin/main. - Sponsor table ownership/reset/final-GSI work completed; one-time machinery deleted under #174.
- Historical migration framework is not a runtime dependency.
- Stage A HUMAN finance semantics accepted privately.
- Stage B On-Call terminal-success default-off deployed proof after #166 cleanup.
- Stage C HUMAN controlled real-data enable/link/reconcile/disable acceptance.
Stage A — private product semantics; eligible now
Next owner: Alexey or Valeria as finance/product owner.
No repository, deployment, provider, AWS, or finance data is needed. Privately confirm:
- which current DataOps admins are authorized to coordinate Sponsor finance;
- that
amountDueis gross and currency-exact; - accepted meanings for
taxModeand optionaltaxAmount; - request-by, expected-invoice, issued-on, due-on, and Berlin-date alert timing;
- that “paid” means explicit DataOps reconciliation to current Bookkeeping evidence, not independent bank confirmation;
- the 20-payment/no-split/no-overpayment boundary;
- in-app-only alert expectations;
- retention of finance coordination/history/claims while the feature is disabled;
- that independent Sponsor/Bookkeeping PITR is non-atomic and may produce
reconciliation-required, with no automatic repair; - whether a successful Stage C should leave the feature enabled or return it to default-off.
Public evidence records only PASS/CHANGES REQUESTED and which semantic categories were reviewed. Do not publish admins, amounts, currencies, tax decisions, dates, sponsor/invoice/payment examples, retention details, or private policy discussion.
A requested semantics change becomes a newly groomed source issue. Do not silently alter accepted code or use Stage C as product discovery.
Stage B — steady-state default-off deployment proof
Depends on #166 Phase D, canonical first-write evidence, and accepted cleanup restoring ordinary push OIDC deployment.
Next owner: On-Call.
Use the exact steady-state deployed source containing #113. Do not manually deploy or dispatch a workflow for #113. Record sanitized evidence that:
- the normal deployment reaches terminal success;
- final Sponsor table ownership/four-index state remains the accepted #136 result;
SPONSOR_FINANCE_ENABLEDresolves false/default-off;- disabled finance API returns its safe unavailable response before finance/Booking/Bookkeeping/User reads;
- the canonical Sponsor UI renders no finance panel/actions while disabled;
- scheduled finance alert evaluation performs no finance reads/writes/notifications while disabled;
- ordinary Sponsor CRM, Bookkeeping, #114 communications, and unrelated cron paths remain available;
- no finance record, claim, receipt, history, candidate, or alert is created.
Do not include stack/table/function IDs, environment values, private booking/bookkeeping data, credentials, logs with private context, or screenshots of live finance data.
After PASS, add/retain human and route Stage C only if Stage A is also accepted and data prerequisites exist.
Stage C — controlled real finance acceptance
Blocked until:
- Stage A PASS;
- Stage B PASS;
- an authorized finance admin and active read-only operator are available;
- one appropriate canonical Sponsor Booking already exists in the empty/repopulated final Sponsor table;
- one current verified issued invoice and one current positive exact-currency Bookkeeping payment exist through ordinary authorized operation;
- the data owner confirms those records may be used for this private sandbox acceptance;
- any population/import of source data has completed under its own separately approved one-off plan;
- a normal post-#166 main deployment opportunity exists for the non-secret feature-flag change.
Do not create placeholder production records, run the retained Sponsor importer, restore backups, or add migration API support under #113.
Enable safely
An authorized configuration owner sets the finance flag true only through the approved repository/environment variable path. Let the next ordinary reviewed main push deploy it through OIDC. Do not manually patch Lambda, manually deploy, or dispatch a special workflow.
Confirm the authorized admin sees the panel and candidates while the operator sees only the projection/permitted download and no mutation controls.
Verify one real graph privately
Using only the pre-authorized records:
- classify the Booking under the Stage A semantics;
- record the invoice request using server time;
- link the eligible issued invoice;
- link the eligible exact-currency payment;
- verify exact due/outstanding/reconciled states and applicable Berlin-date alert behavior;
- verify the invoice uses the existing fresh authenticated Bookkeeping download path;
- verify the Bookkeeping sources are claim-locked against unauthorized mutation;
- replay one safe same-key action and confirm no duplicate version/history/link/claim;
- confirm no private Bookkeeping/Sponsor values appear in public DTOs, notifications, logs, URLs, or screenshots.
Do not send an invoice/message, call a provider/bank, create a payment, change finance amounts to force a state, or expose private evidence.
If the approved records do not naturally exercise an alert/partial state, record it as not applicable; do not manipulate real dates or amounts merely to satisfy a screenshot.
Prove disable rollback
After the authorized acceptance:
- set the feature flag false through the ordinary configuration/deployment path unless Stage A explicitly approved leaving it enabled;
- confirm finance routes/panel/alerts return to disabled/no-read behavior;
- confirm finance records and reverse claims remain retained;
- confirm disabling does not unlock or mutate claimed Bookkeeping sources;
- re-enabling, if authorized later, projects the same coherent graph rather than replaying a migration.
A failure keeps the flag false, preserves the records/claims, and creates a separate needs grooming bug with sanitized stage. Do not delete, relink, restore, or repair the graph from #113.
Public-safe HUMAN evidence
Record only:
- Stage A PASS/CHANGES REQUESTED;
- Stage B default-off deployed PASS and source identity;
- Stage C enabled/disabled final choice;
- whether one invoice and one payment linked coherently;
- whether exact projection, role boundary, download, idempotent replay, source lock, alerts-as-applicable, privacy review, and disable retention passed.
Do not post Sponsor/contact names, Booking/document/transaction/link/claim/history/receipt IDs, amounts, currencies, tax/due/request dates, filenames, object/hash data, counterparties, bank/account/provider data, invoice content, URLs, screenshots, logs, table/stack/function identifiers, or private recovery policy.
Closure and failure routing
Close #113 only after Stages A, B, and C pass. Closure requires no repository commit if no defect was found.
If Stage A changes product semantics, file a source issue. If Stage B finds a deployment/default-off defect, route it to Software Engineer/On-Call. If Stage C finds a runtime defect, disable the flag and file a bounded source/security issue. Data absence remains a blocked gate, not permission to import or fabricate records.
Evidence
- Final Architect PASS: https://github.com/DataTalksClub/dataops/issues/113#issuecomment-5127726394
- Tester PASS: https://github.com/DataTalksClub/dataops/issues/113#issuecomment-5127814101
- PM acceptance: https://github.com/DataTalksClub/dataops/issues/113#issuecomment-5127849245
- Integration Tester PASS: https://github.com/DataTalksClub/dataops/issues/113#issuecomment-5128316342
- Integration PM acceptance: https://github.com/DataTalksClub/dataops/issues/113#issuecomment-5128342227
- Sponsor ownership/GSI completion: https://github.com/DataTalksClub/dataops/issues/136#issuecomment-5281815330
- Sponsor table reset completion: https://github.com/DataTalksClub/dataops/issues/143#issuecomment-5281815829
- Migration-framework cleanup: #174
- Closed historical migration tracker: #115
- Current publication sequence: #166
Out of scope
- Invoice generation/issuance/sending, provider payment, bank confirmation, tax calculation, currency conversion, sponsor communications, or broad receivables.
- Historical Sponsor/Bookkeeping import, migration APIs, backfill, restore, or automatic graph repair.
- Enabling the feature before Stages A+B and data authorization.
- Publishing private finance evidence or using production identifiers in tests/screenshots.
- Any repository/AWS/provider/credential/data mutation from this PM reconciliation.
Contributor guide
No contributing guide indexed for this repository
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
There is no locally implementable source stage; first review the Stage A private semantics gate and #166 Phase D deployment dependency. Stage B requires default-off deployment evidence, followed by authorized Stage C real-data acceptance. The named backend/scripts/import-sponsor-crm.ts is explicitly not a dependency and must not be run or extended.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- aws, typescript
- Domain
- backend, database, design, frontend, infrastructure, testing
- Issue type
- Feature
- Difficulty
- 5/5
- Estimated time
- Over a week
- Activity status
- Quiet
- Clarity
- Needs clarification
- Newbie friendliness
- 15/100