Skip to content

fix(integrations): CLI sends remote_url + cron backfills unmatched deploys#48

Merged
trentas merged 1 commit into
mainfrom
fix/cli-remote-url-and-cron-rematch
May 14, 2026
Merged

fix(integrations): CLI sends remote_url + cron backfills unmatched deploys#48
trentas merged 1 commit into
mainfrom
fix/cli-remote-url-and-cron-rematch

Conversation

@trentas
Copy link
Copy Markdown
Contributor

@trentas trentas commented May 14, 2026

The per-repo DORA section depends on `external_deployments.repository_id` being set, which only happens at ingestion time when the Datadog `dd_repository_id` slug normalizes to a known `repositories.remote_url`. Two reasons this match was failing:

  1. CLI never sent `remote_url`. `_push_after_analysis` and `_run_push` both omitted the parameter, so `repositories.remote_url` stayed NULL — even after `iris . --push` ran successfully from inside a git repo. Confirmed locally on `benefits-club-service`: row exists, `remote_url IS NULL`, but Datadog has matching deploys at `github.com/rocketbus/benefits-club-service`.

  2. Cron never re-matched existing rows. Even with the CLI fix, the ~773 unmatched rows already in `external_deployments` stayed null — the cron only fetches NEW events (`started_at >= last_sync_at`) and the upsert touches only new ids.

What changed

CLI

  • `iris/cli.py` — factored out `_git_remote_url(repo_path)`. Passes its result through `push_metrics(remote_url=...)` from both the post-analysis push (uses `ctx.repo_path`) and the standalone `iris push ` (best-effort from `os.getcwd()`).

Platform

  • `platform/lib/integrations/datadog/sync.ts` — new `rematchUnlinkedDeployments(supabase, orgId)`. Pages through `external_deployments` where `repository_id IS NULL AND dd_repository_id IS NOT NULL`, normalizes each slug via the existing `normalizeRepoSlug`, and batches `UPDATE` calls in chunks of 100 against the matching repo's id. Idempotent — never overwrites a set `repository_id`.
  • `platform/src/app/api/cron/sync-integrations/route.ts` — runs `rematchUnlinkedDeployments` after each successful sync. Failures log a warning and don't fail the run. Per-org outcome gains a `rematched` count.

Verified

`tsc --noEmit` clean. `vitest` 186 passed. `pytest` 115 passed. `eslint` clean.

Test plan

  • Merge → wait for Vercel deploy
  • Trigger cron manually: `curl -H "Authorization: Bearer $CRON_SECRET" https://iris.clickbus.com/api/cron/sync-integrations\`
  • Response should show `rematched: N` with N close to 773 for the customer org
  • Refresh `//repos/benefits-club-service` — DORA section appears
  • Run `iris upgrade` then `iris . --push` on any repo whose `remote_url` was NULL — confirm the row updates with the detected URL after the push

🤖 Generated with Claude Code

…ploys

Two halves of the same gap. The Datadog sync only matches a deploy's
dd_repository_id to an Iris repo at insertion time. If `repositories.
remote_url` is NULL when the cron ingests an event, the row lands with
`repository_id = null` and stays unmatched forever — the per-repo DORA
section never renders.

Two reasons remote_url ends up NULL:

1. The CLI's `push_metrics` call never passed `remote_url`. The
   parameter exists on the platform side (and on the underlying
   `push_metrics(...)` Python signature), but `_push_after_analysis`
   and `_run_push` both omitted it, so /api/ingest had nothing to
   write into the column.

2. Even after the CLI is fixed, all existing rows that were ingested
   before the repo had a remote_url stay null — the cron only fetches
   events with started_at >= last_sync_at, and the UNIQUE
   (provider, provider_event_id) upsert touches only new ids.

Fixes:

- `iris/cli.py`: factors out `_git_remote_url(repo_path)` and passes
  its result through to `push_metrics(remote_url=...)` from both the
  post-analysis push and the standalone `iris push <file>`. The
  standalone path detects from cwd (best-effort).
- `platform/lib/integrations/datadog/sync.ts`: new
  `rematchUnlinkedDeployments(supabase, orgId)`. Loads the current
  repo lookup, pages through `external_deployments WHERE
  repository_id IS NULL AND dd_repository_id IS NOT NULL`, normalizes
  each slug, and updates rows in batches of 100 whose slug matches a
  current repo. Idempotent — only flips null → set, never overwrites.
- `platform/src/app/api/cron/sync-integrations/route.ts`: runs the
  rematch after each successful sync. Failures don't fail the run;
  they're logged and the per-org outcome includes the new `rematched`
  count.

Once this lands, a manual cron trigger (`curl -H "Authorization:
Bearer $CRON_SECRET" .../api/cron/sync-integrations`) will retroactively
match the existing ~773 null-repository_id rows on the customer org —
the per-repo DORA sections that depend on `repository_id` will start
showing data without a re-sync from Datadog.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@vercel
Copy link
Copy Markdown

vercel Bot commented May 14, 2026

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
clickbus-iris Ready Ready Preview, Comment May 14, 2026 1:13am

Request Review

@trentas trentas merged commit 0e97fc4 into main May 14, 2026
4 checks passed
@trentas trentas deleted the fix/cli-remote-url-and-cron-rematch branch May 14, 2026 01:21
trentas added a commit that referenced this pull request May 14, 2026
Bumps pyproject.toml (1.0.6 → 1.0.7), iris/cli.py:VERSION (v1.0.6 →
v1.0.7), and platform/package.json (1.0.6 → 1.0.7). Adds the
CHANGELOG entry covering the five fix PRs that landed after the v1.0.6
release as the customer's real Datadog integration came online:

- #44 credentials_encrypted BYTEA → TEXT
- #45 dedupe DORA events before upsert + cron retries errored integrations
- #46 chunk commits .in() to stay under PostgREST URL ceiling
- #47 direct-from-tables DORA aggregation + per-repo section
- #48 CLI sends remote_url + cron backfills unmatched deploys

Plus #43 gitignore fix that was missed by the v1.0.6 squash.

Tag v1.0.7 cut from main triggers the Release workflow to build the
wheel + publish the GitHub Release, so `iris upgrade` will pick up
the fixes (most notably the CLI sending remote_url) on the next run.

Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
trentas added a commit that referenced this pull request May 14, 2026
)

The schema validated `remote_url` with Zod's `.url()`, which only
accepts WHATWG URLs (scheme://...). The CLI's new \`remote_url\`
plumbing (#48 / v1.0.7) sends whatever \`git remote get-url origin\`
returns; on machines configured with SSH that's
\`git@github.com:org/repo.git\` — no scheme, rejected by Zod with:

    "remote_url":["Invalid URL"]

So the v1.0.7 CLI sends the value as intended, the server rejects the
whole push, and \`repositories.remote_url\` stays NULL — defeating the
fix entirely on SSH-configured machines.

Relax the schema to `z.string().min(1).optional()`. The value is
informational metadata: it never gets fetched, never embedded as HTML,
only normalized via `normalizeRepoSlug` for DORA matching (which
already understands the SSH form: `^git@([^:]+):` → `host/$1`).

Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
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