openship 0.1.0 → 0.1.7
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.ts +1 -0
- package/dist/index.js +5786 -0
- package/dist/server/index.js +324319 -0
- package/dist/server/migrations/0000_init.sql +666 -0
- package/dist/server/migrations/0001_brief_tomorrow_man.sql +47 -0
- package/dist/server/migrations/0002_funny_dazzler.sql +2 -0
- package/dist/server/migrations/0003_third_killer_shrike.sql +1 -0
- package/dist/server/migrations/0004_session_active_org_not_null.sql +10 -0
- package/dist/server/migrations/0005_warm_amazoness.sql +3 -0
- package/dist/server/migrations/0006_lumpy_joystick.sql +1 -0
- package/dist/server/migrations/0007_outgoing_maginty.sql +2 -0
- package/dist/server/migrations/0008_frozen_cutover.sql +3 -0
- package/dist/server/migrations/0009_credits_billing.sql +142 -0
- package/dist/server/migrations/0010_credit_grant_dedupe.sql +14 -0
- package/dist/server/migrations/0011_remove_credit_ledger.sql +23 -0
- package/dist/server/migrations/0012_smart_deploys_and_git_rollback.sql +81 -0
- package/dist/server/migrations/0013_fix_check_run_rollup_unique.sql +38 -0
- package/dist/server/migrations/0014_default_rollback_git.sql +9 -0
- package/dist/server/migrations/0015_billing_idempotency_grants.sql +41 -0
- package/dist/server/migrations/0016_github_auth_high_findings.sql +30 -0
- package/dist/server/migrations/0017_spooky_rumiko_fujikawa.sql +6 -0
- package/dist/server/migrations/0018_calm_shatterstar.sql +1 -0
- package/dist/server/migrations/0019_rename_workspace_install_to_prepare.sql +1 -0
- package/dist/server/migrations/0020_uneven_the_renegades.sql +13 -0
- package/dist/server/migrations/0021_shiny_firestar.sql +2 -0
- package/dist/server/migrations/0022_version_on_success_backfill.sql +6 -0
- package/dist/server/migrations/0023_productive_gorilla_man.sql +17 -0
- package/dist/server/migrations/0024_sleepy_peter_quill.sql +2 -0
- package/dist/server/migrations/0025_smooth_blue_shield.sql +1 -0
- package/dist/server/migrations/0026_mail_backup_source.sql +11 -0
- package/dist/server/migrations/0027_opposite_anthem.sql +6 -0
- package/dist/server/migrations/0028_stale_rogue.sql +18 -0
- package/dist/server/migrations/0029_bouncy_loners.sql +16 -0
- package/dist/server/migrations/0030_bright_darkstar.sql +6 -0
- package/dist/server/migrations/0031_conscious_catseye.sql +13 -0
- package/dist/server/migrations/0032_wet_mimic.sql +51 -0
- package/dist/server/migrations/0033_eminent_molly_hayes.sql +2 -0
- package/dist/server/migrations/meta/0000_snapshot.json +5110 -0
- package/dist/server/migrations/meta/0001_snapshot.json +5257 -0
- package/dist/server/migrations/meta/0002_snapshot.json +5279 -0
- package/dist/server/migrations/meta/0003_snapshot.json +5286 -0
- package/dist/server/migrations/meta/0004_snapshot.json +5286 -0
- package/dist/server/migrations/meta/0005_snapshot.json +5305 -0
- package/dist/server/migrations/meta/0006_snapshot.json +5311 -0
- package/dist/server/migrations/meta/0007_snapshot.json +5323 -0
- package/dist/server/migrations/meta/0016_snapshot.json +6345 -0
- package/dist/server/migrations/meta/0017_snapshot.json +6383 -0
- package/dist/server/migrations/meta/0018_snapshot.json +6390 -0
- package/dist/server/migrations/meta/0019_snapshot.json +6390 -0
- package/dist/server/migrations/meta/0020_snapshot.json +6497 -0
- package/dist/server/migrations/meta/0021_snapshot.json +6509 -0
- package/dist/server/migrations/meta/0022_snapshot.json +6509 -0
- package/dist/server/migrations/meta/0023_snapshot.json +6629 -0
- package/dist/server/migrations/meta/0024_snapshot.json +6641 -0
- package/dist/server/migrations/meta/0025_snapshot.json +6648 -0
- package/dist/server/migrations/meta/0026_snapshot.json +6750 -0
- package/dist/server/migrations/meta/0027_snapshot.json +6757 -0
- package/dist/server/migrations/meta/0028_snapshot.json +6895 -0
- package/dist/server/migrations/meta/0029_snapshot.json +7028 -0
- package/dist/server/migrations/meta/0030_snapshot.json +7066 -0
- package/dist/server/migrations/meta/0031_snapshot.json +7181 -0
- package/dist/server/migrations/meta/0032_snapshot.json +7570 -0
- package/dist/server/migrations/meta/0033_snapshot.json +7597 -0
- package/dist/server/migrations/meta/_journal.json +244 -0
- package/dist/server/pglite/pglite.data +0 -0
- package/dist/server/pglite/pglite.wasm +0 -0
- package/package.json +33 -21
- package/.env.example +0 -22
- package/.nvmrc +0 -1
- package/.prettierrc +0 -7
- package/CONTRIBUTING.md +0 -40
- package/README.md +0 -164
- package/apps/api/.env.example +0 -30
- package/apps/api/Dockerfile +0 -24
- package/apps/api/package.json +0 -37
- package/apps/api/src/app.ts +0 -26
- package/apps/api/src/config/env.ts +0 -39
- package/apps/api/src/config/index.ts +0 -1
- package/apps/api/src/index.ts +0 -8
- package/apps/api/src/middleware/auth.ts +0 -24
- package/apps/api/src/middleware/error-handler.ts +0 -21
- package/apps/api/src/middleware/index.ts +0 -3
- package/apps/api/src/middleware/rate-limiter.ts +0 -26
- package/apps/api/src/modules/auth/auth.controller.ts +0 -26
- package/apps/api/src/modules/auth/auth.routes.ts +0 -10
- package/apps/api/src/modules/auth/auth.schema.ts +0 -12
- package/apps/api/src/modules/auth/auth.service.ts +0 -23
- package/apps/api/src/modules/billing/billing.controller.ts +0 -60
- package/apps/api/src/modules/billing/billing.routes.ts +0 -26
- package/apps/api/src/modules/billing/billing.schema.ts +0 -9
- package/apps/api/src/modules/billing/billing.service.ts +0 -33
- package/apps/api/src/modules/deployments/deployment.controller.ts +0 -35
- package/apps/api/src/modules/deployments/deployment.routes.ts +0 -11
- package/apps/api/src/modules/deployments/deployment.schema.ts +0 -7
- package/apps/api/src/modules/deployments/deployment.service.ts +0 -23
- package/apps/api/src/modules/domains/domain.controller.ts +0 -21
- package/apps/api/src/modules/domains/domain.routes.ts +0 -9
- package/apps/api/src/modules/domains/domain.service.ts +0 -19
- package/apps/api/src/modules/health/health.routes.ts +0 -10
- package/apps/api/src/modules/projects/project.controller.ts +0 -29
- package/apps/api/src/modules/projects/project.routes.ts +0 -10
- package/apps/api/src/modules/projects/project.schema.ts +0 -9
- package/apps/api/src/modules/projects/project.service.ts +0 -23
- package/apps/api/src/modules/webhooks/webhook.controller.ts +0 -22
- package/apps/api/src/modules/webhooks/webhook.routes.ts +0 -12
- package/apps/api/src/modules/webhooks/webhook.service.ts +0 -11
- package/apps/api/tsconfig.json +0 -12
- package/apps/cli/package.json +0 -28
- package/apps/cli/src/commands/deploy.ts +0 -11
- package/apps/cli/src/commands/init.ts +0 -8
- package/apps/cli/src/commands/login.ts +0 -8
- package/apps/cli/src/commands/logs.ts +0 -9
- package/apps/cli/src/index.ts +0 -21
- package/apps/cli/src/lib/api-client.ts +0 -35
- package/apps/cli/tsconfig.json +0 -12
- package/apps/dashboard/Dockerfile +0 -24
- package/apps/dashboard/next.config.mjs +0 -6
- package/apps/dashboard/package.json +0 -28
- package/apps/dashboard/src/app/(auth)/layout.tsx +0 -6
- package/apps/dashboard/src/app/(auth)/login/page.tsx +0 -11
- package/apps/dashboard/src/app/(auth)/register/page.tsx +0 -10
- package/apps/dashboard/src/app/(dashboard)/billing/page.tsx +0 -10
- package/apps/dashboard/src/app/(dashboard)/deployments/page.tsx +0 -8
- package/apps/dashboard/src/app/(dashboard)/domains/page.tsx +0 -8
- package/apps/dashboard/src/app/(dashboard)/layout.tsx +0 -37
- package/apps/dashboard/src/app/(dashboard)/monitoring/page.tsx +0 -8
- package/apps/dashboard/src/app/(dashboard)/projects/page.tsx +0 -8
- package/apps/dashboard/src/app/(dashboard)/settings/page.tsx +0 -8
- package/apps/dashboard/src/app/globals.css +0 -3
- package/apps/dashboard/src/app/layout.tsx +0 -15
- package/apps/dashboard/src/app/page.tsx +0 -6
- package/apps/dashboard/tsconfig.json +0 -11
- package/apps/web/Dockerfile +0 -24
- package/apps/web/next.config.mjs +0 -6
- package/apps/web/package.json +0 -26
- package/apps/web/src/app/(marketing)/docs/page.tsx +0 -10
- package/apps/web/src/app/(marketing)/layout.tsx +0 -24
- package/apps/web/src/app/(marketing)/page.tsx +0 -2
- package/apps/web/src/app/(marketing)/pricing/page.tsx +0 -10
- package/apps/web/src/app/globals.css +0 -3
- package/apps/web/src/app/layout.tsx +0 -16
- package/apps/web/src/app/page.tsx +0 -10
- package/apps/web/tsconfig.json +0 -11
- package/docker-compose.yml +0 -87
- package/packages/adapters/package.json +0 -27
- package/packages/adapters/src/base-adapter.ts +0 -49
- package/packages/adapters/src/docker-adapter.ts +0 -43
- package/packages/adapters/src/index.ts +0 -4
- package/packages/adapters/src/oblien-adapter.ts +0 -46
- package/packages/adapters/src/registry.ts +0 -22
- package/packages/adapters/tsconfig.json +0 -9
- package/packages/core/package.json +0 -27
- package/packages/core/src/constants.ts +0 -28
- package/packages/core/src/errors.ts +0 -49
- package/packages/core/src/index.ts +0 -4
- package/packages/core/src/types.ts +0 -47
- package/packages/core/src/utils.ts +0 -35
- package/packages/core/tsconfig.json +0 -9
- package/packages/db/package.json +0 -32
- package/packages/db/prisma/schema.prisma +0 -160
- package/packages/db/src/index.ts +0 -11
- package/packages/db/tsconfig.json +0 -9
- package/packages/ui/package.json +0 -38
- package/packages/ui/src/components/badge.tsx +0 -29
- package/packages/ui/src/components/button.tsx +0 -44
- package/packages/ui/src/components/card.tsx +0 -26
- package/packages/ui/src/components/status-dot.tsx +0 -25
- package/packages/ui/src/globals.css +0 -18
- package/packages/ui/src/index.tsx +0 -8
- package/packages/ui/src/lib/cn.ts +0 -7
- package/packages/ui/tsconfig.json +0 -9
- package/pnpm-workspace.yaml +0 -4
- package/tooling/tsconfig/base.json +0 -19
- package/tooling/tsconfig/nextjs.json +0 -10
- package/tooling/tsconfig/node.json +0 -10
- package/tooling/tsconfig/package.json +0 -7
- package/turbo.json +0 -32
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
-- Schema hardening: drop legacy organization_meta (folded into organization.is_team),
|
|
2
|
+
-- add missing FKs + indexes flagged by the enterprise audit, and the partial
|
|
3
|
+
-- unique index that race-guards concurrent deployment creation.
|
|
4
|
+
--
|
|
5
|
+
-- All statements are idempotent so re-running on DBs already partway through
|
|
6
|
+
-- the consolidation succeeds. Greenfield installs apply the same SQL with the
|
|
7
|
+
-- IF (NOT) EXISTS guards as no-op when conditions are met.
|
|
8
|
+
|
|
9
|
+
DROP TABLE IF EXISTS "organization_meta" CASCADE;--> statement-breakpoint
|
|
10
|
+
ALTER TABLE "organization" ADD COLUMN IF NOT EXISTS "is_team" boolean DEFAULT false NOT NULL;--> statement-breakpoint
|
|
11
|
+
|
|
12
|
+
-- FK: domain.service_id → service.id (CASCADE delete to prevent stale routing)
|
|
13
|
+
DO $$ BEGIN
|
|
14
|
+
ALTER TABLE "domain" ADD CONSTRAINT "domain_service_id_service_id_fk"
|
|
15
|
+
FOREIGN KEY ("service_id") REFERENCES "public"."service"("id") ON DELETE cascade ON UPDATE no action;
|
|
16
|
+
EXCEPTION WHEN duplicate_object THEN NULL; END $$;--> statement-breakpoint
|
|
17
|
+
|
|
18
|
+
-- FK: env_var.service_id → service.id (CASCADE delete to prevent orphan env vars)
|
|
19
|
+
DO $$ BEGIN
|
|
20
|
+
ALTER TABLE "env_var" ADD CONSTRAINT "env_var_service_id_service_id_fk"
|
|
21
|
+
FOREIGN KEY ("service_id") REFERENCES "public"."service"("id") ON DELETE cascade ON UPDATE no action;
|
|
22
|
+
EXCEPTION WHEN duplicate_object THEN NULL; END $$;--> statement-breakpoint
|
|
23
|
+
|
|
24
|
+
-- Race guard: only one in-flight deployment per project. The race-prone
|
|
25
|
+
-- (SELECT-then-INSERT) in build.service.ts now relies on this constraint.
|
|
26
|
+
CREATE UNIQUE INDEX IF NOT EXISTS "uq_deployment_one_active_per_project"
|
|
27
|
+
ON "deployment" USING btree ("project_id")
|
|
28
|
+
WHERE status IN ('queued', 'building', 'deploying');--> statement-breakpoint
|
|
29
|
+
|
|
30
|
+
-- Routing hot path — every hostname lookup hits the (project_id) and
|
|
31
|
+
-- (project_id, hostname) indexes.
|
|
32
|
+
CREATE INDEX IF NOT EXISTS "idx_domain_project" ON "domain" USING btree ("project_id");--> statement-breakpoint
|
|
33
|
+
CREATE INDEX IF NOT EXISTS "idx_domain_project_hostname" ON "domain" USING btree ("project_id","hostname");--> statement-breakpoint
|
|
34
|
+
|
|
35
|
+
-- Env var resolution runs on every build.
|
|
36
|
+
CREATE INDEX IF NOT EXISTS "idx_env_var_project_env_service" ON "env_var" USING btree ("project_id","environment","service_id");--> statement-breakpoint
|
|
37
|
+
CREATE INDEX IF NOT EXISTS "idx_env_var_project" ON "env_var" USING btree ("project_id");--> statement-breakpoint
|
|
38
|
+
|
|
39
|
+
-- GitHub App installation lookup: unique (provider, owner, user_id) backs
|
|
40
|
+
-- atomic onConflictDoUpdate; (organization_id, provider, owner) backs the
|
|
41
|
+
-- org-scoped resolution path used by every authed request that mints an
|
|
42
|
+
-- installation token.
|
|
43
|
+
CREATE UNIQUE INDEX IF NOT EXISTS "uq_git_installation_provider_owner_user" ON "git_installation" USING btree ("provider","owner","user_id");--> statement-breakpoint
|
|
44
|
+
CREATE INDEX IF NOT EXISTS "idx_git_installation_org" ON "git_installation" USING btree ("organization_id","provider","owner");--> statement-breakpoint
|
|
45
|
+
|
|
46
|
+
-- Build pipeline + deployment setup iterate services per project.
|
|
47
|
+
CREATE INDEX IF NOT EXISTS "idx_service_project_id" ON "service" USING btree ("project_id");
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
ALTER TABLE "project" ADD COLUMN IF NOT EXISTS "cloud_workspace_id" text;--> statement-breakpoint
|
|
2
|
+
CREATE UNIQUE INDEX IF NOT EXISTS "uq_project_cloud_workspace_id" ON "project" USING btree ("cloud_workspace_id") WHERE "project"."cloud_workspace_id" IS NOT NULL AND "project"."deleted_at" IS NULL;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
ALTER TABLE "instance_settings" ADD COLUMN "invitation_mail_source" text DEFAULT 'platform' NOT NULL;
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
-- Backfill any remaining nulls (from sessions created before the
|
|
2
|
+
-- create-time hook landed) to the user's personal org. The
|
|
3
|
+
-- provisionUser convention is org_<userId>, and provisionUser
|
|
4
|
+
-- guarantees that org + owner-member row exist for every user.
|
|
5
|
+
UPDATE "session" SET "active_organization_id" = 'org_' || "user_id"
|
|
6
|
+
WHERE "active_organization_id" IS NULL;
|
|
7
|
+
--> statement-breakpoint
|
|
8
|
+
-- Promote to NOT NULL — the schema itself now enforces the
|
|
9
|
+
-- invariant. No code path can violate it.
|
|
10
|
+
ALTER TABLE "session" ALTER COLUMN "active_organization_id" SET NOT NULL;
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
ALTER TABLE "instance_settings" ADD COLUMN "team_mode" text DEFAULT 'single_user' NOT NULL;--> statement-breakpoint
|
|
2
|
+
ALTER TABLE "instance_settings" ADD COLUMN "migration_target_url" text;--> statement-breakpoint
|
|
3
|
+
ALTER TABLE "instance_settings" ADD COLUMN "migrated_at" timestamp;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
ALTER TABLE "instance_settings" ADD COLUMN "migration_server_id" text;
|
|
@@ -0,0 +1,142 @@
|
|
|
1
|
+
-- Billing & credits: add per-org plan/subscription columns and the credit
|
|
2
|
+
-- ledger tables. Idempotent (IF NOT EXISTS guards) so applying twice on a
|
|
3
|
+
-- partway-through DB is a no-op.
|
|
4
|
+
|
|
5
|
+
-- ── organization: billing columns ───────────────────────────────────────────
|
|
6
|
+
ALTER TABLE "organization" ADD COLUMN IF NOT EXISTS "plan_tier_id" text DEFAULT 'free' NOT NULL;--> statement-breakpoint
|
|
7
|
+
ALTER TABLE "organization" ADD COLUMN IF NOT EXISTS "stripe_customer_id" text;--> statement-breakpoint
|
|
8
|
+
ALTER TABLE "organization" ADD COLUMN IF NOT EXISTS "subscription_status" text DEFAULT 'active' NOT NULL;--> statement-breakpoint
|
|
9
|
+
ALTER TABLE "organization" ADD COLUMN IF NOT EXISTS "current_period_start" timestamp;--> statement-breakpoint
|
|
10
|
+
ALTER TABLE "organization" ADD COLUMN IF NOT EXISTS "current_period_end" timestamp;--> statement-breakpoint
|
|
11
|
+
ALTER TABLE "organization" ADD COLUMN IF NOT EXISTS "oblien_namespace" text;--> statement-breakpoint
|
|
12
|
+
|
|
13
|
+
-- ── billing_customer ────────────────────────────────────────────────────────
|
|
14
|
+
CREATE TABLE IF NOT EXISTS "billing_customer" (
|
|
15
|
+
"id" text PRIMARY KEY NOT NULL,
|
|
16
|
+
"organization_id" text NOT NULL,
|
|
17
|
+
"stripe_customer_id" text NOT NULL,
|
|
18
|
+
"email" text NOT NULL,
|
|
19
|
+
"created_at" timestamp DEFAULT now() NOT NULL,
|
|
20
|
+
"updated_at" timestamp DEFAULT now() NOT NULL
|
|
21
|
+
);--> statement-breakpoint
|
|
22
|
+
|
|
23
|
+
DO $$ BEGIN
|
|
24
|
+
ALTER TABLE "billing_customer" ADD CONSTRAINT "billing_customer_organization_id_organization_id_fk"
|
|
25
|
+
FOREIGN KEY ("organization_id") REFERENCES "public"."organization"("id") ON DELETE cascade ON UPDATE no action;
|
|
26
|
+
EXCEPTION WHEN duplicate_object THEN NULL; END $$;--> statement-breakpoint
|
|
27
|
+
|
|
28
|
+
CREATE UNIQUE INDEX IF NOT EXISTS "uq_billing_customer_org" ON "billing_customer" USING btree ("organization_id");--> statement-breakpoint
|
|
29
|
+
CREATE UNIQUE INDEX IF NOT EXISTS "uq_billing_customer_stripe" ON "billing_customer" USING btree ("stripe_customer_id");--> statement-breakpoint
|
|
30
|
+
|
|
31
|
+
-- ── billing_subscription ────────────────────────────────────────────────────
|
|
32
|
+
CREATE TABLE IF NOT EXISTS "billing_subscription" (
|
|
33
|
+
"id" text PRIMARY KEY NOT NULL,
|
|
34
|
+
"organization_id" text NOT NULL,
|
|
35
|
+
"stripe_subscription_id" text NOT NULL,
|
|
36
|
+
"stripe_price_id" text NOT NULL,
|
|
37
|
+
"plan_tier_id" text NOT NULL,
|
|
38
|
+
"interval" text NOT NULL,
|
|
39
|
+
"status" text NOT NULL,
|
|
40
|
+
"current_period_start" timestamp NOT NULL,
|
|
41
|
+
"current_period_end" timestamp NOT NULL,
|
|
42
|
+
"cancel_at_period_end" boolean DEFAULT false NOT NULL,
|
|
43
|
+
"created_at" timestamp DEFAULT now() NOT NULL,
|
|
44
|
+
"updated_at" timestamp DEFAULT now() NOT NULL
|
|
45
|
+
);--> statement-breakpoint
|
|
46
|
+
|
|
47
|
+
DO $$ BEGIN
|
|
48
|
+
ALTER TABLE "billing_subscription" ADD CONSTRAINT "billing_subscription_organization_id_organization_id_fk"
|
|
49
|
+
FOREIGN KEY ("organization_id") REFERENCES "public"."organization"("id") ON DELETE cascade ON UPDATE no action;
|
|
50
|
+
EXCEPTION WHEN duplicate_object THEN NULL; END $$;--> statement-breakpoint
|
|
51
|
+
|
|
52
|
+
CREATE UNIQUE INDEX IF NOT EXISTS "uq_billing_subscription_stripe" ON "billing_subscription" USING btree ("stripe_subscription_id");--> statement-breakpoint
|
|
53
|
+
CREATE INDEX IF NOT EXISTS "idx_billing_subscription_org" ON "billing_subscription" USING btree ("organization_id");--> statement-breakpoint
|
|
54
|
+
|
|
55
|
+
-- ── credit_balance ──────────────────────────────────────────────────────────
|
|
56
|
+
CREATE TABLE IF NOT EXISTS "credit_balance" (
|
|
57
|
+
"organization_id" text PRIMARY KEY NOT NULL,
|
|
58
|
+
"monthly_free_milli" bigint DEFAULT 0 NOT NULL,
|
|
59
|
+
"topup_milli" bigint DEFAULT 0 NOT NULL,
|
|
60
|
+
"updated_at" timestamp DEFAULT now() NOT NULL
|
|
61
|
+
);--> statement-breakpoint
|
|
62
|
+
|
|
63
|
+
DO $$ BEGIN
|
|
64
|
+
ALTER TABLE "credit_balance" ADD CONSTRAINT "credit_balance_organization_id_organization_id_fk"
|
|
65
|
+
FOREIGN KEY ("organization_id") REFERENCES "public"."organization"("id") ON DELETE cascade ON UPDATE no action;
|
|
66
|
+
EXCEPTION WHEN duplicate_object THEN NULL; END $$;--> statement-breakpoint
|
|
67
|
+
|
|
68
|
+
-- ── credit_grant ────────────────────────────────────────────────────────────
|
|
69
|
+
CREATE TABLE IF NOT EXISTS "credit_grant" (
|
|
70
|
+
"id" text PRIMARY KEY NOT NULL,
|
|
71
|
+
"organization_id" text NOT NULL,
|
|
72
|
+
"amount_milli" bigint NOT NULL,
|
|
73
|
+
"bucket" text NOT NULL,
|
|
74
|
+
"source" text NOT NULL,
|
|
75
|
+
"source_ref" text,
|
|
76
|
+
"expires_at" timestamp,
|
|
77
|
+
"created_at" timestamp DEFAULT now() NOT NULL
|
|
78
|
+
);--> statement-breakpoint
|
|
79
|
+
|
|
80
|
+
DO $$ BEGIN
|
|
81
|
+
ALTER TABLE "credit_grant" ADD CONSTRAINT "credit_grant_organization_id_organization_id_fk"
|
|
82
|
+
FOREIGN KEY ("organization_id") REFERENCES "public"."organization"("id") ON DELETE cascade ON UPDATE no action;
|
|
83
|
+
EXCEPTION WHEN duplicate_object THEN NULL; END $$;--> statement-breakpoint
|
|
84
|
+
|
|
85
|
+
CREATE INDEX IF NOT EXISTS "idx_credit_grant_org_created" ON "credit_grant" USING btree ("organization_id","created_at");--> statement-breakpoint
|
|
86
|
+
|
|
87
|
+
-- ── credit_consumption ──────────────────────────────────────────────────────
|
|
88
|
+
CREATE TABLE IF NOT EXISTS "credit_consumption" (
|
|
89
|
+
"id" text PRIMARY KEY NOT NULL,
|
|
90
|
+
"organization_id" text NOT NULL,
|
|
91
|
+
"oblien_event_id" text NOT NULL,
|
|
92
|
+
"resource_type" text NOT NULL,
|
|
93
|
+
"quantity_milli" bigint NOT NULL,
|
|
94
|
+
"credits_milli" bigint NOT NULL,
|
|
95
|
+
"bucket_consumed" text NOT NULL,
|
|
96
|
+
"occurred_at" timestamp NOT NULL,
|
|
97
|
+
"recorded_at" timestamp DEFAULT now() NOT NULL
|
|
98
|
+
);--> statement-breakpoint
|
|
99
|
+
|
|
100
|
+
DO $$ BEGIN
|
|
101
|
+
ALTER TABLE "credit_consumption" ADD CONSTRAINT "credit_consumption_organization_id_organization_id_fk"
|
|
102
|
+
FOREIGN KEY ("organization_id") REFERENCES "public"."organization"("id") ON DELETE cascade ON UPDATE no action;
|
|
103
|
+
EXCEPTION WHEN duplicate_object THEN NULL; END $$;--> statement-breakpoint
|
|
104
|
+
|
|
105
|
+
CREATE UNIQUE INDEX IF NOT EXISTS "uq_credit_consumption_org_event" ON "credit_consumption" USING btree ("organization_id","oblien_event_id");--> statement-breakpoint
|
|
106
|
+
CREATE INDEX IF NOT EXISTS "idx_credit_consumption_org_occurred" ON "credit_consumption" USING btree ("organization_id","occurred_at");--> statement-breakpoint
|
|
107
|
+
|
|
108
|
+
-- ── credit_pack ─────────────────────────────────────────────────────────────
|
|
109
|
+
CREATE TABLE IF NOT EXISTS "credit_pack" (
|
|
110
|
+
"id" text PRIMARY KEY NOT NULL,
|
|
111
|
+
"name" text NOT NULL,
|
|
112
|
+
"credits_milli" bigint NOT NULL,
|
|
113
|
+
"price_cents" integer NOT NULL,
|
|
114
|
+
"stripe_product_id" text NOT NULL,
|
|
115
|
+
"stripe_price_id" text NOT NULL,
|
|
116
|
+
"active" boolean DEFAULT true NOT NULL,
|
|
117
|
+
"sort_order" integer DEFAULT 0 NOT NULL
|
|
118
|
+
);--> statement-breakpoint
|
|
119
|
+
|
|
120
|
+
CREATE UNIQUE INDEX IF NOT EXISTS "uq_credit_pack_stripe_price" ON "credit_pack" USING btree ("stripe_price_id");--> statement-breakpoint
|
|
121
|
+
|
|
122
|
+
-- ── oblien_usage_cursor ─────────────────────────────────────────────────────
|
|
123
|
+
CREATE TABLE IF NOT EXISTS "oblien_usage_cursor" (
|
|
124
|
+
"organization_id" text PRIMARY KEY NOT NULL,
|
|
125
|
+
"oblien_namespace" text NOT NULL,
|
|
126
|
+
"last_synced_at" timestamp NOT NULL,
|
|
127
|
+
"last_sync_run_at" timestamp NOT NULL,
|
|
128
|
+
"consecutive_failures" integer DEFAULT 0 NOT NULL
|
|
129
|
+
);--> statement-breakpoint
|
|
130
|
+
|
|
131
|
+
DO $$ BEGIN
|
|
132
|
+
ALTER TABLE "oblien_usage_cursor" ADD CONSTRAINT "oblien_usage_cursor_organization_id_organization_id_fk"
|
|
133
|
+
FOREIGN KEY ("organization_id") REFERENCES "public"."organization"("id") ON DELETE cascade ON UPDATE no action;
|
|
134
|
+
EXCEPTION WHEN duplicate_object THEN NULL; END $$;--> statement-breakpoint
|
|
135
|
+
|
|
136
|
+
-- ── stripe_webhook_event ────────────────────────────────────────────────────
|
|
137
|
+
CREATE TABLE IF NOT EXISTS "stripe_webhook_event" (
|
|
138
|
+
"stripe_event_id" text PRIMARY KEY NOT NULL,
|
|
139
|
+
"event_type" text NOT NULL,
|
|
140
|
+
"received_at" timestamp DEFAULT now() NOT NULL,
|
|
141
|
+
"processed_at" timestamp
|
|
142
|
+
);
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
-- Partial unique index on credit_grant (organization_id, source, source_ref)
|
|
2
|
+
-- where source_ref IS NOT NULL. Closes the race between the Stripe webhook
|
|
3
|
+
-- and the monthly-reset cron: both used to mint a tier_grant for the same
|
|
4
|
+
-- period boundary, producing two ledger rows + a doubled allowance in the
|
|
5
|
+
-- cache. The unique index makes the second insert a conflict; the writers
|
|
6
|
+
-- use ON CONFLICT DO NOTHING and skip the cache delta when no row landed.
|
|
7
|
+
--
|
|
8
|
+
-- Partial (source_ref IS NOT NULL) so admin/refund grants minted with a
|
|
9
|
+
-- null source_ref are not coerced into uniqueness — those are intentionally
|
|
10
|
+
-- distinct ledger rows.
|
|
11
|
+
|
|
12
|
+
CREATE UNIQUE INDEX IF NOT EXISTS "uq_credit_grant_org_source_ref"
|
|
13
|
+
ON "credit_grant" USING btree ("organization_id", "source", "source_ref")
|
|
14
|
+
WHERE "source_ref" IS NOT NULL;
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
-- Demolish the local credit ledger.
|
|
2
|
+
--
|
|
3
|
+
-- Quota is now owned by Oblien (the runtime meters consumption directly and
|
|
4
|
+
-- enforces `setQuota` limits). The local grant/consume/balance triplet and
|
|
5
|
+
-- the Oblien pull-sync cursor are obsolete. The Stripe-side state lives on
|
|
6
|
+
-- in billing_customer / billing_subscription / credit_pack / stripe_webhook_event.
|
|
7
|
+
--
|
|
8
|
+
-- Order matters: drop indexes first (defensive — DROP TABLE drops them too,
|
|
9
|
+
-- but being explicit keeps the diff easy to audit), then the tables in
|
|
10
|
+
-- dependency order. There are no FKs between the four dropped tables, but
|
|
11
|
+
-- credit_consumption + credit_grant + credit_balance + oblien_usage_cursor
|
|
12
|
+
-- all reference organization.id with ON DELETE CASCADE, which postgres
|
|
13
|
+
-- handles cleanly regardless of drop order.
|
|
14
|
+
|
|
15
|
+
DROP INDEX IF EXISTS "uq_credit_grant_org_source_ref";--> statement-breakpoint
|
|
16
|
+
DROP INDEX IF EXISTS "idx_credit_grant_org_created";--> statement-breakpoint
|
|
17
|
+
DROP INDEX IF EXISTS "uq_credit_consumption_org_event";--> statement-breakpoint
|
|
18
|
+
DROP INDEX IF EXISTS "idx_credit_consumption_org_occurred";--> statement-breakpoint
|
|
19
|
+
|
|
20
|
+
DROP TABLE IF EXISTS "credit_consumption";--> statement-breakpoint
|
|
21
|
+
DROP TABLE IF EXISTS "credit_balance";--> statement-breakpoint
|
|
22
|
+
DROP TABLE IF EXISTS "credit_grant";--> statement-breakpoint
|
|
23
|
+
DROP TABLE IF EXISTS "oblien_usage_cursor";
|
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
-- Smart per-service deploys + git-strategy rollback
|
|
2
|
+
--
|
|
3
|
+
-- Adds the schema surface for two related features:
|
|
4
|
+
--
|
|
5
|
+
-- 1. Smart per-service deploys — record which paths changed between
|
|
6
|
+
-- the previous successful deploy and this one (`changed_paths`),
|
|
7
|
+
-- let the build pipeline skip services whose root_directory was
|
|
8
|
+
-- untouched, and surface the result per-service in the existing
|
|
9
|
+
-- service_deployment table.
|
|
10
|
+
--
|
|
11
|
+
-- 2. Git-strategy rollback — instead of always archiving each
|
|
12
|
+
-- deploy's image + workspace snapshot, projects can opt to roll
|
|
13
|
+
-- back by checking out the prior commit and rebuilding
|
|
14
|
+
-- (`rollback_strategy = "git"`). Cheaper on disk, slower to
|
|
15
|
+
-- restore. Snapshotted per-deployment via `commit_sha_before`.
|
|
16
|
+
--
|
|
17
|
+
-- Idempotent (IF NOT EXISTS guards) so a partial re-apply is safe.
|
|
18
|
+
|
|
19
|
+
-- ── deployment ───────────────────────────────────────────────────────────────
|
|
20
|
+
ALTER TABLE "deployment" ADD COLUMN IF NOT EXISTS "commit_sha_before" text;--> statement-breakpoint
|
|
21
|
+
ALTER TABLE "deployment" ADD COLUMN IF NOT EXISTS "changed_paths" jsonb;--> statement-breakpoint
|
|
22
|
+
ALTER TABLE "deployment" ADD COLUMN IF NOT EXISTS "changed_paths_truncated" boolean DEFAULT false NOT NULL;--> statement-breakpoint
|
|
23
|
+
ALTER TABLE "deployment" ADD COLUMN IF NOT EXISTS "force_all" boolean DEFAULT false NOT NULL;--> statement-breakpoint
|
|
24
|
+
ALTER TABLE "deployment" ADD COLUMN IF NOT EXISTS "rollback_strategy" text DEFAULT 'snapshot' NOT NULL;--> statement-breakpoint
|
|
25
|
+
|
|
26
|
+
-- ── project ──────────────────────────────────────────────────────────────────
|
|
27
|
+
ALTER TABLE "project" ADD COLUMN IF NOT EXISTS "default_rollback_strategy" text DEFAULT 'snapshot' NOT NULL;--> statement-breakpoint
|
|
28
|
+
ALTER TABLE "project" ADD COLUMN IF NOT EXISTS "force_deploy_next" boolean DEFAULT false NOT NULL;--> statement-breakpoint
|
|
29
|
+
ALTER TABLE "project" ADD COLUMN IF NOT EXISTS "monorepo_shared_paths" jsonb;--> statement-breakpoint
|
|
30
|
+
ALTER TABLE "project" ADD COLUMN IF NOT EXISTS "always_rebuild_paths" jsonb;--> statement-breakpoint
|
|
31
|
+
|
|
32
|
+
-- ── service ──────────────────────────────────────────────────────────────────
|
|
33
|
+
ALTER TABLE "service" ADD COLUMN IF NOT EXISTS "always_rebuild_globs" jsonb;--> statement-breakpoint
|
|
34
|
+
|
|
35
|
+
-- ── service_deployment: smart-deploy tracking columns ───────────────────────
|
|
36
|
+
ALTER TABLE "service_deployment" ADD COLUMN IF NOT EXISTS "service_name" text;--> statement-breakpoint
|
|
37
|
+
ALTER TABLE "service_deployment" ADD COLUMN IF NOT EXISTS "reason" text;--> statement-breakpoint
|
|
38
|
+
ALTER TABLE "service_deployment" ADD COLUMN IF NOT EXISTS "reason_skipped" text;--> statement-breakpoint
|
|
39
|
+
ALTER TABLE "service_deployment" ADD COLUMN IF NOT EXISTS "url" text;--> statement-breakpoint
|
|
40
|
+
ALTER TABLE "service_deployment" ADD COLUMN IF NOT EXISTS "started_at" timestamp;--> statement-breakpoint
|
|
41
|
+
ALTER TABLE "service_deployment" ADD COLUMN IF NOT EXISTS "finished_at" timestamp;--> statement-breakpoint
|
|
42
|
+
ALTER TABLE "service_deployment" ADD COLUMN IF NOT EXISTS "duration_ms" integer;--> statement-breakpoint
|
|
43
|
+
ALTER TABLE "service_deployment" ADD COLUMN IF NOT EXISTS "error_message" text;--> statement-breakpoint
|
|
44
|
+
ALTER TABLE "service_deployment" ADD COLUMN IF NOT EXISTS "error" text;--> statement-breakpoint
|
|
45
|
+
ALTER TABLE "service_deployment" ADD COLUMN IF NOT EXISTS "check_run_id" bigint;--> statement-breakpoint
|
|
46
|
+
ALTER TABLE "service_deployment" ADD COLUMN IF NOT EXISTS "check_run_url" text;--> statement-breakpoint
|
|
47
|
+
ALTER TABLE "service_deployment" ADD COLUMN IF NOT EXISTS "artifact_retained_at" timestamp;--> statement-breakpoint
|
|
48
|
+
ALTER TABLE "service_deployment" ADD COLUMN IF NOT EXISTS "logs_ref" text;--> statement-breakpoint
|
|
49
|
+
|
|
50
|
+
-- service_deployment indexes
|
|
51
|
+
CREATE UNIQUE INDEX IF NOT EXISTS "uq_service_deployment_dep_svc" ON "service_deployment" USING btree ("deployment_id","service_id");--> statement-breakpoint
|
|
52
|
+
CREATE INDEX IF NOT EXISTS "ix_service_deployment_deployment" ON "service_deployment" USING btree ("deployment_id");--> statement-breakpoint
|
|
53
|
+
CREATE INDEX IF NOT EXISTS "ix_service_deployment_service_status" ON "service_deployment" USING btree ("service_id","status");--> statement-breakpoint
|
|
54
|
+
CREATE INDEX IF NOT EXISTS "ix_service_deployment_service_created" ON "service_deployment" USING btree ("service_id","created_at");--> statement-breakpoint
|
|
55
|
+
|
|
56
|
+
-- ── deployment_check_run ─────────────────────────────────────────────────────
|
|
57
|
+
CREATE TABLE IF NOT EXISTS "deployment_check_run" (
|
|
58
|
+
"id" text PRIMARY KEY NOT NULL,
|
|
59
|
+
"deployment_id" text NOT NULL,
|
|
60
|
+
"check_run_id" bigint NOT NULL,
|
|
61
|
+
"name" text NOT NULL,
|
|
62
|
+
"kind" text NOT NULL,
|
|
63
|
+
"service_deployment_id" text,
|
|
64
|
+
"status" text NOT NULL,
|
|
65
|
+
"conclusion" text,
|
|
66
|
+
"created_at" timestamp DEFAULT now() NOT NULL,
|
|
67
|
+
"updated_at" timestamp DEFAULT now() NOT NULL
|
|
68
|
+
);--> statement-breakpoint
|
|
69
|
+
|
|
70
|
+
DO $$ BEGIN
|
|
71
|
+
ALTER TABLE "deployment_check_run" ADD CONSTRAINT "deployment_check_run_deployment_id_deployment_id_fk"
|
|
72
|
+
FOREIGN KEY ("deployment_id") REFERENCES "public"."deployment"("id") ON DELETE cascade ON UPDATE no action;
|
|
73
|
+
EXCEPTION WHEN duplicate_object THEN NULL; END $$;--> statement-breakpoint
|
|
74
|
+
|
|
75
|
+
DO $$ BEGIN
|
|
76
|
+
ALTER TABLE "deployment_check_run" ADD CONSTRAINT "deployment_check_run_service_deployment_id_service_deployment_id_fk"
|
|
77
|
+
FOREIGN KEY ("service_deployment_id") REFERENCES "public"."service_deployment"("id") ON DELETE cascade ON UPDATE no action;
|
|
78
|
+
EXCEPTION WHEN duplicate_object THEN NULL; END $$;--> statement-breakpoint
|
|
79
|
+
|
|
80
|
+
CREATE UNIQUE INDEX IF NOT EXISTS "uq_deployment_check_run_per_kind" ON "deployment_check_run" USING btree ("deployment_id","kind","service_deployment_id");--> statement-breakpoint
|
|
81
|
+
CREATE INDEX IF NOT EXISTS "ix_deployment_check_run_deployment" ON "deployment_check_run" USING btree ("deployment_id");
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
-- ── Fix deployment_check_run uniqueness for rollup rows ─────────────────────
|
|
2
|
+
--
|
|
3
|
+
-- The previous `uq_deployment_check_run_per_kind` index covers
|
|
4
|
+
-- (deployment_id, kind, service_deployment_id). PostgreSQL treats NULLs
|
|
5
|
+
-- as distinct in unique indexes by default, so multiple rows with
|
|
6
|
+
-- (deployment_id, 'rollup', NULL) could coexist — the rollup invariant
|
|
7
|
+
-- of "one rollup row per deployment" was never actually enforced.
|
|
8
|
+
--
|
|
9
|
+
-- This migration replaces that single non-effective index with two
|
|
10
|
+
-- partial unique indexes that match the actual data shapes:
|
|
11
|
+
--
|
|
12
|
+
-- - rollup rows (kind = 'rollup', service_deployment_id IS NULL):
|
|
13
|
+
-- unique on (deployment_id)
|
|
14
|
+
--
|
|
15
|
+
-- - service rows (service_deployment_id IS NOT NULL):
|
|
16
|
+
-- unique on (deployment_id, service_deployment_id)
|
|
17
|
+
--
|
|
18
|
+
-- Also drops a couple of redundant secondary indexes whose lookups are
|
|
19
|
+
-- already covered by the leading column of an existing unique index.
|
|
20
|
+
|
|
21
|
+
DROP INDEX IF EXISTS "uq_deployment_check_run_per_kind";--> statement-breakpoint
|
|
22
|
+
|
|
23
|
+
CREATE UNIQUE INDEX IF NOT EXISTS "uq_deployment_check_run_rollup"
|
|
24
|
+
ON "deployment_check_run" ("deployment_id")
|
|
25
|
+
WHERE "kind" = 'rollup';--> statement-breakpoint
|
|
26
|
+
|
|
27
|
+
CREATE UNIQUE INDEX IF NOT EXISTS "uq_deployment_check_run_service"
|
|
28
|
+
ON "deployment_check_run" ("deployment_id", "service_deployment_id")
|
|
29
|
+
WHERE "service_deployment_id" IS NOT NULL;--> statement-breakpoint
|
|
30
|
+
|
|
31
|
+
-- Redundant: covered by `uq_deployment_check_run_rollup` /
|
|
32
|
+
-- `uq_deployment_check_run_service` (both have deployment_id as the
|
|
33
|
+
-- leading column), so a separate ix on deployment_id buys nothing.
|
|
34
|
+
DROP INDEX IF EXISTS "ix_deployment_check_run_deployment";--> statement-breakpoint
|
|
35
|
+
|
|
36
|
+
-- Redundant: covered by `uq_service_deployment_dep_svc` whose leading
|
|
37
|
+
-- column is deployment_id.
|
|
38
|
+
DROP INDEX IF EXISTS "ix_service_deployment_deployment";
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
-- Flip the default rollback strategy for NEW projects from "snapshot" to
|
|
2
|
+
-- "git". Existing rows are not touched — they keep whatever they were
|
|
3
|
+
-- created with (a previously-deployed project relying on snapshot
|
|
4
|
+
-- rollback should not silently lose its snapshots).
|
|
5
|
+
--
|
|
6
|
+
-- Users can change the per-project setting via the dashboard's git
|
|
7
|
+
-- settings page.
|
|
8
|
+
|
|
9
|
+
ALTER TABLE "project" ALTER COLUMN "default_rollback_strategy" SET DEFAULT 'git';
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
-- Billing idempotency: per-checkout-session topup grants + per-period
|
|
2
|
+
-- anniversary cron grants. Both protect read-modify-write Oblien quota
|
|
3
|
+
-- mutations from being re-applied when their upstream driver retries:
|
|
4
|
+
-- - stripe_topup_grant Stripe webhook redelivery of checkout.session.completed
|
|
5
|
+
-- would otherwise call addQuota twice → double-credit.
|
|
6
|
+
-- - billing_anniversary_grant Cron crash between Oblien resetQuota and the
|
|
7
|
+
-- local period UPDATE would let the next tick
|
|
8
|
+
-- re-zero quota_used on the new period.
|
|
9
|
+
-- Idempotent (IF NOT EXISTS guards) so applying twice on a partway-through
|
|
10
|
+
-- DB is a no-op.
|
|
11
|
+
|
|
12
|
+
CREATE TABLE IF NOT EXISTS "stripe_topup_grant" (
|
|
13
|
+
"id" text PRIMARY KEY NOT NULL,
|
|
14
|
+
"checkout_session_id" text NOT NULL,
|
|
15
|
+
"organization_id" text NOT NULL,
|
|
16
|
+
"pack_id" text NOT NULL,
|
|
17
|
+
"credits_milli" bigint NOT NULL,
|
|
18
|
+
"granted_at" timestamp DEFAULT now() NOT NULL
|
|
19
|
+
);--> statement-breakpoint
|
|
20
|
+
|
|
21
|
+
DO $$ BEGIN
|
|
22
|
+
ALTER TABLE "stripe_topup_grant" ADD CONSTRAINT "stripe_topup_grant_organization_id_organization_id_fk"
|
|
23
|
+
FOREIGN KEY ("organization_id") REFERENCES "public"."organization"("id") ON DELETE cascade ON UPDATE no action;
|
|
24
|
+
EXCEPTION WHEN duplicate_object THEN NULL; END $$;--> statement-breakpoint
|
|
25
|
+
|
|
26
|
+
CREATE UNIQUE INDEX IF NOT EXISTS "uq_stripe_topup_grant_session" ON "stripe_topup_grant" USING btree ("checkout_session_id");--> statement-breakpoint
|
|
27
|
+
CREATE INDEX IF NOT EXISTS "idx_stripe_topup_grant_org" ON "stripe_topup_grant" USING btree ("organization_id");--> statement-breakpoint
|
|
28
|
+
|
|
29
|
+
CREATE TABLE IF NOT EXISTS "billing_anniversary_grant" (
|
|
30
|
+
"id" text PRIMARY KEY NOT NULL,
|
|
31
|
+
"organization_id" text NOT NULL,
|
|
32
|
+
"period_start" timestamp NOT NULL,
|
|
33
|
+
"granted_at" timestamp DEFAULT now() NOT NULL
|
|
34
|
+
);--> statement-breakpoint
|
|
35
|
+
|
|
36
|
+
DO $$ BEGIN
|
|
37
|
+
ALTER TABLE "billing_anniversary_grant" ADD CONSTRAINT "billing_anniversary_grant_organization_id_organization_id_fk"
|
|
38
|
+
FOREIGN KEY ("organization_id") REFERENCES "public"."organization"("id") ON DELETE cascade ON UPDATE no action;
|
|
39
|
+
EXCEPTION WHEN duplicate_object THEN NULL; END $$;--> statement-breakpoint
|
|
40
|
+
|
|
41
|
+
CREATE UNIQUE INDEX IF NOT EXISTS "uq_billing_anniversary_grant_org_period" ON "billing_anniversary_grant" USING btree ("organization_id","period_start");
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
-- HIGH-finding fixes for GitHub auth surface (audit, June 2026).
|
|
2
|
+
--
|
|
3
|
+
-- HIGH #6 — github_install_state: short-TTL nonces that bind the install
|
|
4
|
+
-- URL the SaaS hands back to a specific local user/org. Resolves the
|
|
5
|
+
-- "echo-back state with no local binding" hole in the install flow.
|
|
6
|
+
CREATE TABLE "github_install_state" (
|
|
7
|
+
"id" text PRIMARY KEY NOT NULL,
|
|
8
|
+
"state" text NOT NULL,
|
|
9
|
+
"user_id" text NOT NULL,
|
|
10
|
+
"organization_id" text,
|
|
11
|
+
"expires_at" timestamp NOT NULL,
|
|
12
|
+
"created_at" timestamp DEFAULT now() NOT NULL,
|
|
13
|
+
CONSTRAINT "github_install_state_state_unique" UNIQUE("state")
|
|
14
|
+
);
|
|
15
|
+
--> statement-breakpoint
|
|
16
|
+
CREATE INDEX "github_install_state_expires_idx" ON "github_install_state" USING btree ("expires_at");--> statement-breakpoint
|
|
17
|
+
CREATE INDEX "github_install_state_user_idx" ON "github_install_state" USING btree ("user_id");--> statement-breakpoint
|
|
18
|
+
|
|
19
|
+
-- HIGH #9 — per-project webhook signing secret (encrypted via lib/encryption).
|
|
20
|
+
-- Null on legacy rows; verifier falls back to env.GITHUB_WEBHOOK_SECRET there.
|
|
21
|
+
ALTER TABLE "project" ADD COLUMN "webhook_secret" text;--> statement-breakpoint
|
|
22
|
+
|
|
23
|
+
-- HIGH #7 — explicit operator opt-in for the gh CLI escape hatch.
|
|
24
|
+
-- Without this, "owner of any org" gated transitive access to the
|
|
25
|
+
-- operator's broad-scope PAT.
|
|
26
|
+
ALTER TABLE "user_settings" ADD COLUMN "gh_cli_operator_opted_in" boolean DEFAULT false NOT NULL;--> statement-breakpoint
|
|
27
|
+
|
|
28
|
+
-- HIGH #10 — PAT scope cached from inspectPatScope so we can re-validate
|
|
29
|
+
-- at use time without re-issuing `GET /user`.
|
|
30
|
+
ALTER TABLE "user_settings" ADD COLUMN "pat_scope" jsonb;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
ALTER TABLE "project" ADD COLUMN "deletion_in_progress" boolean DEFAULT false NOT NULL;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
ALTER TABLE "project" RENAME COLUMN "workspace_install_command" TO "workspace_prepare_command";
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
CREATE TABLE "server_tunnels" (
|
|
2
|
+
"id" text PRIMARY KEY NOT NULL,
|
|
3
|
+
"server_id" text NOT NULL,
|
|
4
|
+
"remote_port" integer NOT NULL,
|
|
5
|
+
"remote_host" text DEFAULT '127.0.0.1' NOT NULL,
|
|
6
|
+
"local_port" integer,
|
|
7
|
+
"auto_start" boolean DEFAULT false NOT NULL,
|
|
8
|
+
"created_at" timestamp DEFAULT now() NOT NULL,
|
|
9
|
+
"updated_at" timestamp DEFAULT now() NOT NULL
|
|
10
|
+
);
|
|
11
|
+
--> statement-breakpoint
|
|
12
|
+
ALTER TABLE "server_tunnels" ADD CONSTRAINT "server_tunnels_server_id_servers_id_fk" FOREIGN KEY ("server_id") REFERENCES "public"."servers"("id") ON DELETE cascade ON UPDATE no action;--> statement-breakpoint
|
|
13
|
+
CREATE UNIQUE INDEX "uq_server_tunnel_target" ON "server_tunnels" USING btree ("server_id","remote_port","remote_host");
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
-- Versions now represent shipped releases: a deployment gets its version number
|
|
2
|
+
-- in onSuccess (per-commit), not at create. Clear the per-attempt numbers that
|
|
3
|
+
-- the old MAX(version)+1-at-create logic assigned to non-successful deploys so
|
|
4
|
+
-- failed/in-flight rows stop showing a stale vN badge. Successful (ready) rows
|
|
5
|
+
-- keep their existing numbers.
|
|
6
|
+
UPDATE "deployment" SET "version" = NULL WHERE "status" <> 'ready';
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
CREATE TABLE "personal_access_token" (
|
|
2
|
+
"id" text PRIMARY KEY NOT NULL,
|
|
3
|
+
"user_id" text NOT NULL,
|
|
4
|
+
"organization_id" text,
|
|
5
|
+
"name" text NOT NULL,
|
|
6
|
+
"token_prefix" text NOT NULL,
|
|
7
|
+
"token_hash" text NOT NULL,
|
|
8
|
+
"read_only" boolean DEFAULT false NOT NULL,
|
|
9
|
+
"expires_at" timestamp,
|
|
10
|
+
"last_used_at" timestamp,
|
|
11
|
+
"revoked_at" timestamp,
|
|
12
|
+
"created_at" timestamp DEFAULT now() NOT NULL,
|
|
13
|
+
CONSTRAINT "personal_access_token_token_hash_unique" UNIQUE("token_hash")
|
|
14
|
+
);
|
|
15
|
+
--> statement-breakpoint
|
|
16
|
+
CREATE INDEX "personal_access_token_user_idx" ON "personal_access_token" USING btree ("user_id");--> statement-breakpoint
|
|
17
|
+
CREATE INDEX "personal_access_token_prefix_idx" ON "personal_access_token" USING btree ("token_prefix");
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
ALTER TABLE "service" ADD COLUMN "advanced" jsonb DEFAULT '{}'::jsonb;
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
ALTER TABLE "backup_policy" ALTER COLUMN "project_id" DROP NOT NULL;--> statement-breakpoint
|
|
2
|
+
ALTER TABLE "backup_policy" ADD COLUMN "source_kind" text DEFAULT 'service' NOT NULL;--> statement-breakpoint
|
|
3
|
+
ALTER TABLE "backup_policy" ADD COLUMN "mail_server_id" text;--> statement-breakpoint
|
|
4
|
+
ALTER TABLE "backup_restore" ADD COLUMN "fork_mail_server_id" text;--> statement-breakpoint
|
|
5
|
+
ALTER TABLE "backup_run" ADD COLUMN "source_kind" text DEFAULT 'service' NOT NULL;--> statement-breakpoint
|
|
6
|
+
ALTER TABLE "backup_run" ADD COLUMN "mail_server_id" text;--> statement-breakpoint
|
|
7
|
+
ALTER TABLE "backup_policy" ADD CONSTRAINT "backup_policy_mail_server_id_mail_servers_server_id_fk" FOREIGN KEY ("mail_server_id") REFERENCES "public"."mail_servers"("server_id") ON DELETE cascade ON UPDATE no action;--> statement-breakpoint
|
|
8
|
+
ALTER TABLE "backup_restore" ADD CONSTRAINT "backup_restore_fork_mail_server_id_mail_servers_server_id_fk" FOREIGN KEY ("fork_mail_server_id") REFERENCES "public"."mail_servers"("server_id") ON DELETE set null ON UPDATE no action;--> statement-breakpoint
|
|
9
|
+
ALTER TABLE "backup_run" ADD CONSTRAINT "backup_run_mail_server_id_mail_servers_server_id_fk" FOREIGN KEY ("mail_server_id") REFERENCES "public"."mail_servers"("server_id") ON DELETE set null ON UPDATE no action;--> statement-breakpoint
|
|
10
|
+
CREATE UNIQUE INDEX "uq_backup_policy_mail_server" ON "backup_policy" USING btree ("mail_server_id") WHERE "backup_policy"."mail_server_id" IS NOT NULL AND "backup_policy"."deleted_at" IS NULL;--> statement-breakpoint
|
|
11
|
+
CREATE INDEX "idx_backup_policy_mail_server" ON "backup_policy" USING btree ("mail_server_id");
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
ALTER TABLE "service" ADD COLUMN "namespace_volumes" boolean DEFAULT true NOT NULL;--> statement-breakpoint
|
|
2
|
+
-- Grandfather every EXISTING service to bare (un-scoped) volume names so their
|
|
3
|
+
-- on-disk data is not orphaned. Rows created AFTER this migration take the
|
|
4
|
+
-- column default (true) and get project-scoped volumes. Load-bearing: without
|
|
5
|
+
-- it, ADD COLUMN DEFAULT true would scope existing services and lose their data.
|
|
6
|
+
UPDATE "service" SET "namespace_volumes" = false;
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
CREATE TABLE "orphaned_resource" (
|
|
2
|
+
"id" text PRIMARY KEY NOT NULL,
|
|
3
|
+
"organization_id" text NOT NULL,
|
|
4
|
+
"server_id" text,
|
|
5
|
+
"resource_type" text NOT NULL,
|
|
6
|
+
"ref" text NOT NULL,
|
|
7
|
+
"project_id" text,
|
|
8
|
+
"label" text,
|
|
9
|
+
"runtime_mode" text,
|
|
10
|
+
"payload" jsonb,
|
|
11
|
+
"attempts" integer DEFAULT 0 NOT NULL,
|
|
12
|
+
"last_attempt_at" timestamp,
|
|
13
|
+
"created_at" timestamp DEFAULT now() NOT NULL
|
|
14
|
+
);
|
|
15
|
+
--> statement-breakpoint
|
|
16
|
+
ALTER TABLE "orphaned_resource" ADD CONSTRAINT "orphaned_resource_organization_id_organization_id_fk" FOREIGN KEY ("organization_id") REFERENCES "public"."organization"("id") ON DELETE cascade ON UPDATE no action;--> statement-breakpoint
|
|
17
|
+
CREATE INDEX "orphaned_resource_server_idx" ON "orphaned_resource" USING btree ("server_id");--> statement-breakpoint
|
|
18
|
+
CREATE INDEX "orphaned_resource_org_created_idx" ON "orphaned_resource" USING btree ("organization_id","created_at");
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
CREATE TABLE "cloud_webhook_binding" (
|
|
2
|
+
"id" text PRIMARY KEY NOT NULL,
|
|
3
|
+
"organization_id" text NOT NULL,
|
|
4
|
+
"cloud_project_id" text NOT NULL,
|
|
5
|
+
"git_owner" text NOT NULL,
|
|
6
|
+
"git_repo" text NOT NULL,
|
|
7
|
+
"git_branch" text DEFAULT '' NOT NULL,
|
|
8
|
+
"webhook_id" integer,
|
|
9
|
+
"webhook_secret" text,
|
|
10
|
+
"created_at" timestamp DEFAULT now() NOT NULL,
|
|
11
|
+
"updated_at" timestamp DEFAULT now() NOT NULL
|
|
12
|
+
);
|
|
13
|
+
--> statement-breakpoint
|
|
14
|
+
ALTER TABLE "cloud_webhook_binding" ADD CONSTRAINT "cloud_webhook_binding_organization_id_organization_id_fk" FOREIGN KEY ("organization_id") REFERENCES "public"."organization"("id") ON DELETE cascade ON UPDATE no action;--> statement-breakpoint
|
|
15
|
+
CREATE UNIQUE INDEX "uq_cloud_webhook_binding_repo_branch" ON "cloud_webhook_binding" USING btree ("git_owner","git_repo","git_branch");--> statement-breakpoint
|
|
16
|
+
CREATE INDEX "idx_cloud_webhook_binding_cloud_project" ON "cloud_webhook_binding" USING btree ("cloud_project_id");
|