Skip to content

feat(platform,auth): add secure Adjust onboarding - #26

Merged
mtmtian merged 7 commits into
oratis:mainfrom
mtmtian:codex-mt/adjust-onboarding
Sep 24, 2026
Merged

mtmtian merged 7 commits into
oratis:mainfrom
mtmtian:codex-mt/adjust-onboarding

Conversation

@mtmtian

@mtmtian mtmtian commented Sep 24, 2026 •

Copy link
Copy Markdown
Collaborator

Intent

Provide an independent, secure Adjust setup page so the user can later connect
Luddi and Cuddler, select each app's events and review attributed data. Do not
reuse acquisition configuration or activate a real account during this release.

Changes

  • Add encrypted API-token storage, app/event discovery and per-app metric/source
    mapping with explicit semantic confirmation.
  • Separate organic, paid, other and unknown sources while retaining raw labels
    and media IDs. Keep provider app totals separate from dimensional unique users.
  • Add preview, idempotent latest-window snapshots, stale/error states and CSV.
  • Gate management and both sync entry points by workspace role. Remove the raw
    user-ID-cookie compatibility path before exposing credential management.
  • Add one additive snapshot-table migration and real-Postgres E2E coverage with
    a loopback Adjust fixture. Automatic sync remains off by default.

Broader dashboard metrics, Seedance model/ownership changes and Worker execution
are intentionally not included. The original dirty worktrees are preserved.

Verification

  • npm test: 470 passed / 38 files.
  • Type check and production build passed; lint has zero errors and 35 existing
    warnings outside changed files; git diff --check passed.
  • Local full Playwright: 59 total, 25 passed, 34 skipped without a database.
  • Final HEAD f5a30e10de9180712369e23e13512fa720076a4d:
    CI passed, including
    Docker build/runtime smoke; database E2E
    passed 59/59 with zero skips, including the migration and all nine Adjust DB
    cases. Final desktop/mobile artifacts were inspected.
  • Negative classification test and timezone regression were observed failing
    before correction. No live Adjust, Ark or Seedance requests were made.

Release and Recovery

Deploy only after CI and a HEAD-specific code review pass. Provision a stable
32-byte encryption key in Secret Manager and bind it as
PLATFORM_CREDENTIAL_KEY; never deploy the fixture key or test API override.
The user will enter the business token later; no account or schedule is enabled.

The migration only adds a table. Before any real Adjust credential is stored,
rollback can restore the previous Cloud Run revision while retaining the empty
table and key. After encrypted credentials are stored, older Adjust clients
cannot consume them: prefer a forward fix and do not blindly roll back to the
legacy plaintext client. Never rotate/delete the encryption key during rollback.

True account permissions/metric definitions remain to be reconciled by the user.
This release does not implement media-cost joins, daily history or CPA/CPP/ROAS.
See docs/agent/adjust-setup-validation.md for the reproducible checks and limits.

WHY: connect Adjust independently with per-app attribution mappings without exposing credentials or trusting unsigned user cookies.

WHAT: add encrypted token setup, app/event discovery, normalized latest-window reports, additive snapshot storage and isolated provider E2E coverage. Live account configuration and automatic sync remain opt-in.
@mtmtian

mtmtian commented Sep 24, 2026

Copy link
Copy Markdown
Collaborator Author

HEAD-specific release review

Reviewed f5a30e10de9180712369e23e13512fa720076a4d against
a24ff25332070821c96b3ec3db7c76373e787677 using the repository's
thermo-nuclear-code-quality-review gate. This is an agent self-review, not an
independent human approval.

No unresolved blocking findings remain. Transport, pure normalization,
org-scoped persistence and UI have separate responsibilities. Credential writes
fail closed without encryption; new API responses do not return credentials;
management is owner/admin-only. Raw user-ID cookies are rejected. Snapshot
publication checks unchanged configuration within a transaction and retains
previous data on provider failure. Totals are queried independently rather
than summing unique users across dimensions. No acquisition configuration is
imported, and no live account or automatic sync is activated by this release.

Review findings resolved before this HEAD: generic disconnect filter bypass,
cached report visibility during catalog failure, normalized preview/save state,
and explicit field-label associations. The final test adjustments disambiguate
Next's route announcer and wait for the sidebar's observable mobile position;
they do not remove or weaken the original behavior assertions.

Verified on this HEAD:

  • CI: 470 unit tests,
    type check, lint, production build and Docker runtime smoke passed.
  • E2E: 59/59 passed,
    zero skipped, including real isolated PostgreSQL migration and all nine
    Adjust database cases with a loopback provider.
  • Final desktop/mobile artifacts inspected; mobile document width is 390px
    and the closed sidebar is off screen before capture.
  • Offline production guard check rejects a fixture endpoint before any fetch.
  • git diff --check passed.

Release scope is the configuration page, additive snapshot table and dedicated
server encryption key. True Adjust permissions, Luddi/Cuddler event definitions
and dashboard reconciliation remain unverified until the user supplies the
Token. Media-cost joins, daily history, Seedance updates and Worker activation
are not included. Recovery constraints are recorded in the PR body and
docs/agent/adjust-setup-validation.md.

@mtmtian
mtmtian merged commit 36394ce into oratis:main Sep 24, 2026
3 checks passed
@mtmtian

mtmtian commented Sep 24, 2026

Copy link
Copy Markdown
Collaborator Author

Release status: merged and built, deployment blocked

  • PR merged as 36394cec839f6f32916989870f214e4ae2c45ceb.
  • The merged tree matches reviewed HEAD f5a30e10de9180712369e23e13512fa720076a4d.
  • Cloud Build 608e3b62-8ec3-4834-b22d-a5c1553bf98d succeeded on 2026-09-24.
  • Image: gcr.io/gameclaw-492005/adex:36394cec839f6f32916989870f214e4ae2c45ceb.
  • Immutable digest: sha256:a1f88d3d1e7b4db5d7b5b07d02db0711292a2f2c24dc28fd4cc919e29aa6cea1.

Production deployment has NOT run. Neither the encryption secret nor its IAM
binding was created, and the production migration has not been applied.
Both authorized user accounts were denied secretmanager.secrets.create.
matian@hakko.ai currently has Secret Manager Viewer, not Admin. The user is
requesting the missing permission; reauthentication is not the issue.

Resume after authorization: create adex-platform-credential-key from 32 random
bytes encoded as base64 without printing/persisting plaintext; grant the existing
runtime service account 740114287797-compute@developer.gserviceaccount.com
access to that secret only; pin the secret version as PLATFORM_CREDENTIAL_KEY.
Recheck current production revision and upstream main before deploying the exact
image digest. Preserve all other environment variables, identity and resources.
Verify migration, readiness, traffic, secret reference and public auth guards.

Do not connect Adjust, import acquisition credentials, enable automatic sync or
activate Worker/paid generation. The user will enter the real Token afterward.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant