Skip to content

feat: BigQuery Data Warehouse Connector — Phase 1 (Schema, Types, Validation)#391

Open
Shrotriya-lalit wants to merge 5 commits into
Openpanel-dev:mainfrom
Shrotriya-lalit:feat/bigquery-connector-phase1
Open

feat: BigQuery Data Warehouse Connector — Phase 1 (Schema, Types, Validation)#391
Shrotriya-lalit wants to merge 5 commits into
Openpanel-dev:mainfrom
Shrotriya-lalit:feat/bigquery-connector-phase1

Conversation

@Shrotriya-lalit

@Shrotriya-lalit Shrotriya-lalit commented Jun 8, 2026

Copy link
Copy Markdown

Summary

Introduces the foundational schema, migrations, and Zod validators for a BigQuery Data Warehouse Connector — a Mixpanel Warehouse Connector equivalent for OpenPanel. No UI or sync behavior yet; this PR establishes the type-safe, production-grade foundation that Phases 2–6 will build on.

What's included

Prisma schema

  • BigQueryConnection — stores GCP service account credentials (encrypted) per project. Supports multiple named connections per project (@@unique([projectId, name])), matching how Mixpanel allows e.g. jm-ebg and jm-ebg-cdp under the same project
  • BigQuerySync — defines a recurring sync job (source dataset/table, column mapping, schedule, mode)
  • BigQuerySyncRun — audit log for every execution (status, row count, bytes processed, error)
  • 4 enums: BigQuerySyncMappingType, BigQuerySyncMode, BigQuerySyncSchedule, BigQuerySyncRunStatus

Migrations

  • 20260608090217_add_bigquery_connector — creates all tables, enums, indexes, FK cascades
  • 20260608091000_bigquery_multi_connection — multi-connection support (@@unique([projectId, name]))
  • 20260608120000_bigquery_harden — production-grade hardening fields (see below)

Zod validators (packages/validation)

  • zBigQueryConnectionCreate — connection creation with name, SA JSON structure check, GCP region
  • zServiceAccountJson — validates SA key structure before encryption (rejects authorized_user creds)
  • zGcpProjectId — GCP project ID format regex (rejects project numbers / display names)
  • zBqIdentifier — dataset/table name validator (BigQuery only allows [a-zA-Z0-9_])
  • zBigQuerySyncConfig — sync job definition with discriminatedUnion column mapping
  • zBigQueryColumnMappingEvents / zBigQueryColumnMappingProfiles

Dependency

  • @google-cloud/bigquery@^7.9.1 added to packages/db

Production-grade hardening applied

Field Why
gcpRegion on connections GDPR compliance — EU data must stay in EU; affects BQ dataset routing
lastTestedAt + lastTestStatus Connection health indicator; stale credentials are the top failure cause
errorRetryCount + isErrorPaused Circuit breaker — prevents broken syncs hammering the worker indefinitely
partitionFilter on syncs Production BQ tables are partitioned; full-refresh without filter scans years of data
bytesProcessed on runs BigQuery charges $5/TB — per-run cost visibility for enterprise teams
rowCount BigInt (was Int) PostgreSQL INT max ~2.1B; large enterprise tables can exceed this
lastSyncStatus typed as enum Was String? — arbitrary values could be stored

Verification

pnpm typecheck  # zero errors across all 20 packages
pnpm check      # passes (no format/lint changes in this PR)

DB tables confirmed via psql:

  • bigquery_connections with @@unique([projectId, name])
  • bigquery_syncs with lastSyncStatus as BigQuerySyncRunStatus enum
  • bigquery_sync_runs with rowCount BIGINT

What's next

  • Phase 2: Connection management — service layer, tRPC router (listConnections, connect, testConnection, disconnect), settings UI tab
  • Phase 3: Sync CRUD — add/toggle/delete syncs, column mapping UI
  • Phase 4: Sync execution — BullMQ worker, ClickHouse writes, manual trigger
  • Phase 5: Cron scheduling
  • Phase 6: Run history UI

🤖 Generated with Claude Code

Summary by CodeRabbit

  • New Features

    • BigQuery integration: multi-named connections per project, syncs with mapping/modes/schedules, partition filters, and region/health metadata.
    • Sync run tracking: statuses, retries, error pause, run metrics (rows/bytes), and enhanced run diagnostics.
    • Event metadata now supports descriptions.
    • Validation added for GCP project IDs, BigQuery identifiers, service-account JSON, and column-mapping configs.
  • Bug Fixes

    • Stronger referential/uniqueness rules to improve tenant isolation and data integrity.

Phase 1 of the BigQuery warehouse connector. Adds Prisma models for
BigQueryConnection, BigQuerySync and BigQuerySyncRun with four supporting
enums, two Prisma migrations, typed JSON column via PrismaJson namespace,
Zod schemas (zBigQuerySyncConfig + column mapping variants) in
@openpanel/validation, and the @google-cloud/bigquery dependency.
- Add zBqColRef validator for column references (supports dot-notation
  for STRUCT nested fields like user.profile.email)
- Add mappingType discriminator to both mapping schemas so the union is
  discriminated and TypeScript can narrow the type cleanly
- Add superRefine cross-validation: append mode events syncs must declare
  an insertTime column (the TIMESTAMP cursor)
- Update plan with verified BigQuery Node.js client type mappings:
  INT64 needs wrapIntegers:true, TIMESTAMP/.value not .toISOString(),
  DATETIME has no timezone, BYTES→Buffer, Big for NUMERIC/BIGNUMERIC
Real-world orgs connect multiple data sources to one project (e.g.
jm-ebg and jm-ebg-cdp on the same ROAS project). The original
@unique on projectId wrongly enforced a single connection per project.

- Remove @unique from BigQueryConnection.projectId
- Add name String field (user label, e.g. "CDP Source")
- Replace with @@unique([projectId, name]) — names unique within project
- Change Project.bigQueryConnection? → bigQueryConnections[]
Schema additions:
- BigQueryConnection: gcpRegion (GDPR region compliance), lastTestedAt/lastTestStatus (connection health)
- BigQuerySync: lastSyncStatus typed as enum (was String?), errorRetryCount+isErrorPaused circuit breaker, partitionFilter for cost-safe full-refresh on partitioned tables
- BigQuerySyncRun: rowCount BigInt (INT max ~2.1B insufficient), bytesProcessed for cost tracking

Zod additions:
- zGcpProjectId: GCP project ID format regex (rejects project numbers and display names)
- zBqIdentifier: dataset/table name validator (no hyphens, per BQ naming rules)
- zServiceAccountJson: SA JSON structure check (rejects authorized_user creds before encryption)
- zBigQueryConnectionCreate: connection creation schema with name/region/SA JSON
- zBigQuerySyncConfig: dataset/tableName now use zBqIdentifier, partitionFilter field added
@coderabbitai

coderabbitai Bot commented Jun 8, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 00c0805c-273b-4478-8991-60020d3795a6

📥 Commits

Reviewing files that changed from the base of the PR and between 7920219 and 632bde3.

📒 Files selected for processing (2)
  • packages/db/package.json
  • packages/db/prisma/migrations/20260608140000_bigquery_referential_integrity/migration.sql
🚧 Files skipped from review as they are similar to previous changes (1)
  • packages/db/package.json

📝 Walkthrough

Walkthrough

Adds BigQuery connector support: new Prisma models and enums, multiple SQL migrations (foundation, multi-connection, hardening, referential integrity), Zod validation schemas/types for BigQuery configs, and dependency/type wiring including the BigQuery SDK.

Changes

BigQuery Connector Infrastructure

Layer / File(s) Summary
EventMeta description field
packages/db/prisma/migrations/20260607120000_add_event_meta_description/migration.sql, packages/db/prisma/schema.prisma
Adds optional description column to the event_meta table and updates the Prisma model.
BigQuery foundation schema
packages/db/prisma/migrations/20260608090217_add_bigquery_connector/migration.sql, packages/db/prisma/schema.prisma
Adds PostgreSQL enums and creates bigquery_connections, bigquery_syncs, and bigquery_sync_runs tables with relations, constraints, and Prisma model/enums.
BigQuery schema evolution
packages/db/prisma/migrations/20260608091000_bigquery_multi_connection/migration.sql, packages/db/prisma/migrations/20260608120000_bigquery_harden/migration.sql
Enables named multi-connections per project, adds gcpRegion/health fields, retry/partition controls, converts lastSyncStatus to enum, and widens run counters plus bytesProcessed.
BigQuery referential integrity
packages/db/prisma/migrations/20260608140000_bigquery_referential_integrity/migration.sql
Adds FK from bigquery_sync_runs.projectId to projects(id), enforces tenant isolation with composite index/FK between bigquery_syncs and bigquery_connections, backfills empty connection names, and adds a non-empty name CHECK.
BigQuery validation schemas
packages/validation/src/index.ts
Adds Zod validators and exported inferred types: GCP project IDs, BigQuery identifiers, service account JSON, connection creation, column mappings for events/profiles, and sync config with conditional insertTime check.
Dependencies and type wiring
packages/db/package.json, packages/db/src/types.ts
Adds @google-cloud/bigquery runtime dependency and maps BigQuery column-mapping type into the global PrismaJson namespace.
sequenceDiagram
  participant Client
  participant API
  participant Database
  participant BigQuery
  Client->>API: create/trigger BigQuery sync (projectId, connection)
  API->>Database: read BigQueryConnection / BigQuerySync
  API->>BigQuery: authenticate with serviceAccountJson and run query
  BigQuery->>API: return rows / bytesProcessed
  API->>Database: insert BigQuerySyncRun (status, rowCount, bytesProcessed)
Loading

🎯 4 (Complex) | ⏱️ ~45 minutes

🐰 I dug a tunnel of schema and keys,
Seeds of regions, retries, and names,
Validators nibbled through service-account leaves,
Connections lined up like tiny bright flames,
Sync runs tallying bytes in my frames.

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The PR title accurately summarizes the main change: introducing BigQuery Data Warehouse Connector schema, types, and validation foundations in Phase 1, which matches the file changes and objectives.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@packages/db/package.json`:
- Line 17: Update the `@google-cloud/bigquery` dependency in
packages/db/package.json from ^7.9.1 to ^8.3.1 (look for the dependency key
"`@google-cloud/bigquery`") and run your test suite and any integration checks
that exercise BigQuery calls to catch breaking API changes; after updating,
re-run npm audit / GitHub advisory checks and address any newly surfaced
advisories or required code adjustments in functions that call BigQuery client
methods (e.g., places creating BigQuery clients or invoking methods like
dataset/table/query) to align with the v8 API.

In
`@packages/db/prisma/migrations/20260608090217_add_bigquery_connector/migration.sql`:
- Around line 50-53: The migration creates bigquery_sync_runs with a projectId
column but no FK, allowing runs to be assigned to the wrong project; add
referential integrity by adding a foreign key on bigquery_sync_runs.projectId
referencing the canonical projects table (projects.id) and also ensure
run-to-sync consistency by adding a composite foreign key (syncId, projectId)
referencing bigquery_syncs(id, projectId) (first add a unique constraint on
bigquery_syncs(id, projectId) if needed); update the CREATE TABLE for
bigquery_sync_runs to include these constraints (names like
fk_bigquery_sync_runs_project and fk_bigquery_sync_runs_sync_project) so every
run is tied to an existing project and the syncId matches that project.
- Around line 69-73: The two separate FKs allow mismatched project vs connection
tenants on bigquery_syncs; drop the existing bigquery_syncs_connectionId_fkey
and replace it with a composite foreign key (e.g.
bigquery_syncs_projectId_connectionId_fkey) on (projectId, connectionId) that
REFERENCES "public"."bigquery_connections"(projectId, id) WITH ON DELETE CASCADE
ON UPDATE CASCADE so the referenced connection must belong to the same project;
keep or leave the existing projectId -> projects FK
(bigquery_syncs_projectId_fkey) as-is.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 90092f45-30c5-4c2c-aaa2-84bd90a711d7

📥 Commits

Reviewing files that changed from the base of the PR and between b94d256 and 154e5e2.

⛔ Files ignored due to path filters (1)
  • pnpm-lock.yaml is excluded by !**/pnpm-lock.yaml
📒 Files selected for processing (8)
  • packages/db/package.json
  • packages/db/prisma/migrations/20260607120000_add_event_meta_description/migration.sql
  • packages/db/prisma/migrations/20260608090217_add_bigquery_connector/migration.sql
  • packages/db/prisma/migrations/20260608091000_bigquery_multi_connection/migration.sql
  • packages/db/prisma/migrations/20260608120000_bigquery_harden/migration.sql
  • packages/db/prisma/schema.prisma
  • packages/db/src/types.ts
  • packages/validation/src/index.ts

Comment thread packages/db/package.json Outdated
Comment on lines +50 to +53
CREATE TABLE "public"."bigquery_sync_runs" (
"id" UUID NOT NULL DEFAULT gen_random_uuid(),
"syncId" UUID NOT NULL,
"projectId" TEXT NOT NULL,

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major | 🏗️ Heavy lift

Constrain bigquery_sync_runs.projectId to prevent mismatched run attribution.

Line 53 stores projectId, but there is no FK for it, and Line 76 only validates syncId. A run row can carry a wrong project id, breaking run-history correctness and tenant-scoped queries.

Suggested migration direction
+-- Keep sync/project coupling enforceable
+ALTER TABLE "public"."bigquery_syncs"
+  ADD CONSTRAINT "bigquery_syncs_id_projectId_key" UNIQUE ("id", "projectId");
+
+-- Enforce run project consistency with parent sync
+ALTER TABLE "public"."bigquery_sync_runs"
+  ADD CONSTRAINT "bigquery_sync_runs_syncId_projectId_fkey"
+  FOREIGN KEY ("syncId", "projectId")
+  REFERENCES "public"."bigquery_syncs"("id", "projectId")
+  ON DELETE CASCADE ON UPDATE CASCADE;
+
+-- Optional explicit FK for direct project integrity
+ALTER TABLE "public"."bigquery_sync_runs"
+  ADD CONSTRAINT "bigquery_sync_runs_projectId_fkey"
+  FOREIGN KEY ("projectId")
+  REFERENCES "public"."projects"("id")
+  ON DELETE CASCADE ON UPDATE CASCADE;

Also applies to: 75-76

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In
`@packages/db/prisma/migrations/20260608090217_add_bigquery_connector/migration.sql`
around lines 50 - 53, The migration creates bigquery_sync_runs with a projectId
column but no FK, allowing runs to be assigned to the wrong project; add
referential integrity by adding a foreign key on bigquery_sync_runs.projectId
referencing the canonical projects table (projects.id) and also ensure
run-to-sync consistency by adding a composite foreign key (syncId, projectId)
referencing bigquery_syncs(id, projectId) (first add a unique constraint on
bigquery_syncs(id, projectId) if needed); update the CREATE TABLE for
bigquery_sync_runs to include these constraints (names like
fk_bigquery_sync_runs_project and fk_bigquery_sync_runs_sync_project) so every
run is tied to an existing project and the syncId matches that project.

Comment on lines +69 to +73
-- AddForeignKey
ALTER TABLE "public"."bigquery_syncs" ADD CONSTRAINT "bigquery_syncs_connectionId_fkey" FOREIGN KEY ("connectionId") REFERENCES "public"."bigquery_connections"("id") ON DELETE CASCADE ON UPDATE CASCADE;

-- AddForeignKey
ALTER TABLE "public"."bigquery_syncs" ADD CONSTRAINT "bigquery_syncs_projectId_fkey" FOREIGN KEY ("projectId") REFERENCES "public"."projects"("id") ON DELETE CASCADE ON UPDATE CASCADE;

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major | 🏗️ Heavy lift

Enforce project/connection tenant consistency on bigquery_syncs.

Line 70 and Line 73 create independent foreign keys, so a sync can reference a connectionId from project B while storing projectId from project A. That breaks tenant isolation and can misroute data.

Suggested migration direction
+-- Ensure referenced columns are jointly unique
+ALTER TABLE "public"."bigquery_connections"
+  ADD CONSTRAINT "bigquery_connections_id_projectId_key" UNIQUE ("id", "projectId");
+
+-- Enforce sync belongs to the same project as its connection
+ALTER TABLE "public"."bigquery_syncs"
+  ADD CONSTRAINT "bigquery_syncs_connectionId_projectId_fkey"
+  FOREIGN KEY ("connectionId", "projectId")
+  REFERENCES "public"."bigquery_connections"("id", "projectId")
+  ON DELETE CASCADE ON UPDATE CASCADE;
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In
`@packages/db/prisma/migrations/20260608090217_add_bigquery_connector/migration.sql`
around lines 69 - 73, The two separate FKs allow mismatched project vs
connection tenants on bigquery_syncs; drop the existing
bigquery_syncs_connectionId_fkey and replace it with a composite foreign key
(e.g. bigquery_syncs_projectId_connectionId_fkey) on (projectId, connectionId)
that REFERENCES "public"."bigquery_connections"(projectId, id) WITH ON DELETE
CASCADE ON UPDATE CASCADE so the referenced connection must belong to the same
project; keep or leave the existing projectId -> projects FK
(bigquery_syncs_projectId_fkey) as-is.

@Shrotriya-lalit Shrotriya-lalit force-pushed the feat/bigquery-connector-phase1 branch from 154e5e2 to 7920219 Compare June 8, 2026 10:24

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In
`@packages/db/prisma/migrations/20260608091000_bigquery_multi_connection/migration.sql`:
- Around line 6-9: The migration creates bigquery_connections.name with an
empty-string backfill which leaves existing rows with '' and still allows future
empty-string inserts; update the migration to backfill a meaningful non-empty
value for existing rows (e.g., update "bigquery_connections" set "name" =
concat('connection_', id) or another deterministic non-empty token for rows
where name = '') and then add a DB-level constraint to prevent empty names
(e.g., ALTER TABLE "bigquery_connections" ADD CONSTRAINT ... CHECK
(char_length(name) > 0) or name <> '') so future inserts cannot use ''. Ensure
the ALTER that drops the default comes after the backfill and the CHECK
constraint is added as part of the migration so both existing and new rows are
validated.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: ce3b42d9-fd05-4483-8001-e2ff1812b45c

📥 Commits

Reviewing files that changed from the base of the PR and between 154e5e2 and 7920219.

⛔ Files ignored due to path filters (1)
  • pnpm-lock.yaml is excluded by !**/pnpm-lock.yaml
📒 Files selected for processing (8)
  • packages/db/package.json
  • packages/db/prisma/migrations/20260607120000_add_event_meta_description/migration.sql
  • packages/db/prisma/migrations/20260608090217_add_bigquery_connector/migration.sql
  • packages/db/prisma/migrations/20260608091000_bigquery_multi_connection/migration.sql
  • packages/db/prisma/migrations/20260608120000_bigquery_harden/migration.sql
  • packages/db/prisma/schema.prisma
  • packages/db/src/types.ts
  • packages/validation/src/index.ts
✅ Files skipped from review due to trivial changes (1)
  • packages/db/src/types.ts
🚧 Files skipped from review as they are similar to previous changes (6)
  • packages/db/package.json
  • packages/db/prisma/migrations/20260607120000_add_event_meta_description/migration.sql
  • packages/db/prisma/schema.prisma
  • packages/validation/src/index.ts
  • packages/db/prisma/migrations/20260608090217_add_bigquery_connector/migration.sql
  • packages/db/prisma/migrations/20260608120000_bigquery_harden/migration.sql

Comment on lines +6 to +9
ALTER TABLE "public"."bigquery_connections" ADD COLUMN "name" TEXT NOT NULL DEFAULT '';

-- Remove the default now that column exists
ALTER TABLE "public"."bigquery_connections" ALTER COLUMN "name" DROP DEFAULT;

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major | ⚡ Quick win

Backfill leaves invalid empty names and the DB still permits future empty-string inserts.

Line 6 seeds existing rows with '', and after Line 9 those rows remain empty. That conflicts with the non-empty connection-name contract in validation and can leak invalid records into future flows. Please backfill to a non-empty value and enforce non-empty at the database layer.

Suggested migration adjustment
-ALTER TABLE "public"."bigquery_connections" ADD COLUMN "name" TEXT NOT NULL DEFAULT '';
-
--- Remove the default now that column exists
-ALTER TABLE "public"."bigquery_connections" ALTER COLUMN "name" DROP DEFAULT;
+ALTER TABLE "public"."bigquery_connections" ADD COLUMN "name" TEXT;
+UPDATE "public"."bigquery_connections"
+SET "name" = 'default'
+WHERE "name" IS NULL OR btrim("name") = '';
+ALTER TABLE "public"."bigquery_connections" ALTER COLUMN "name" SET NOT NULL;
+ALTER TABLE "public"."bigquery_connections"
+ADD CONSTRAINT "bigquery_connections_name_nonempty_chk"
+CHECK (btrim("name") <> '');
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
ALTER TABLE "public"."bigquery_connections" ADD COLUMN "name" TEXT NOT NULL DEFAULT '';
-- Remove the default now that column exists
ALTER TABLE "public"."bigquery_connections" ALTER COLUMN "name" DROP DEFAULT;
ALTER TABLE "public"."bigquery_connections" ADD COLUMN "name" TEXT;
UPDATE "public"."bigquery_connections"
SET "name" = 'default'
WHERE "name" IS NULL OR btrim("name") = '';
ALTER TABLE "public"."bigquery_connections" ALTER COLUMN "name" SET NOT NULL;
ALTER TABLE "public"."bigquery_connections"
ADD CONSTRAINT "bigquery_connections_name_nonempty_chk"
CHECK (btrim("name") <> '');
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In
`@packages/db/prisma/migrations/20260608091000_bigquery_multi_connection/migration.sql`
around lines 6 - 9, The migration creates bigquery_connections.name with an
empty-string backfill which leaves existing rows with '' and still allows future
empty-string inserts; update the migration to backfill a meaningful non-empty
value for existing rows (e.g., update "bigquery_connections" set "name" =
concat('connection_', id) or another deterministic non-empty token for rows
where name = '') and then add a DB-level constraint to prevent empty names
(e.g., ALTER TABLE "bigquery_connections" ADD CONSTRAINT ... CHECK
(char_length(name) > 0) or name <> '') so future inserts cannot use ''. Ensure
the ALTER that drops the default comes after the backfill and the CHECK
constraint is added as part of the migration so both existing and new rows are
validated.

…d dependency upgrade

- Upgrade @google-cloud/bigquery from ^7.9.1 to ^8.3.1 (latest stable)
- Add FK bigquery_sync_runs.projectId -> projects(id) (was missing, allowing orphan runs)
- Add composite FK bigquery_syncs(projectId, connectionId) -> bigquery_connections(projectId, id)
  to prevent cross-tenant data: a sync can no longer reference a connection from a different project
- Add UNIQUE INDEX bigquery_connections(projectId, id) to back the composite FK
- Add CHECK(char_length(name) > 0) on bigquery_connections to enforce non-empty names at DB level
- Backfill any dev rows with empty name using concat('connection_', id)
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