@secondlayer/shared 1.1.0 → 2.1.0

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.
Files changed (67) hide show
  1. package/dist/src/db/index.d.ts +89 -6
  2. package/dist/src/db/index.js +53 -29
  3. package/dist/src/db/index.js.map +4 -4
  4. package/dist/src/db/jsonb.js.map +2 -2
  5. package/dist/src/db/queries/accounts.d.ts +58 -2
  6. package/dist/src/db/queries/integrity.d.ts +58 -2
  7. package/dist/src/db/queries/projects.d.ts +58 -2
  8. package/dist/src/db/queries/projects.js.map +2 -2
  9. package/dist/src/db/queries/{marketplace.d.ts → provisioning-audit.d.ts} +79 -56
  10. package/dist/src/db/queries/provisioning-audit.js +40 -0
  11. package/dist/src/db/queries/provisioning-audit.js.map +10 -0
  12. package/dist/src/db/queries/subgraph-gaps.d.ts +58 -2
  13. package/dist/src/db/queries/subgraphs.d.ts +62 -5
  14. package/dist/src/db/queries/subgraphs.js +3 -9
  15. package/dist/src/db/queries/subgraphs.js.map +4 -4
  16. package/dist/src/db/queries/tenants.d.ts +527 -0
  17. package/dist/src/db/queries/tenants.js +220 -0
  18. package/dist/src/db/queries/tenants.js.map +11 -0
  19. package/dist/src/db/queries/usage.d.ts +58 -2
  20. package/dist/src/db/queries/usage.js +3 -3
  21. package/dist/src/db/queries/usage.js.map +3 -3
  22. package/dist/src/db/queries/workflows.d.ts +58 -2
  23. package/dist/src/db/queries/workflows.js +31 -3
  24. package/dist/src/db/queries/workflows.js.map +4 -4
  25. package/dist/src/db/schema.d.ts +67 -3
  26. package/dist/src/env.d.ts +10 -0
  27. package/dist/src/env.js +3 -1
  28. package/dist/src/env.js.map +3 -3
  29. package/dist/src/errors.d.ts +17 -3
  30. package/dist/src/errors.js +34 -3
  31. package/dist/src/errors.js.map +3 -3
  32. package/dist/src/index.d.ts +142 -84
  33. package/dist/src/index.js +146 -99
  34. package/dist/src/index.js.map +8 -8
  35. package/dist/src/logger.js +3 -1
  36. package/dist/src/logger.js.map +3 -3
  37. package/dist/src/mode.d.ts +29 -0
  38. package/dist/src/mode.js +43 -0
  39. package/dist/src/mode.js.map +10 -0
  40. package/dist/src/node/archive-client.js +3 -1
  41. package/dist/src/node/archive-client.js.map +3 -3
  42. package/dist/src/node/hiro-client.js +3 -1
  43. package/dist/src/node/hiro-client.js.map +3 -3
  44. package/dist/src/node/local-client.d.ts +58 -2
  45. package/dist/src/queue/listener.d.ts +11 -2
  46. package/dist/src/queue/listener.js +11 -12
  47. package/dist/src/queue/listener.js.map +3 -3
  48. package/dist/src/schemas/accounts.d.ts +14 -0
  49. package/dist/src/schemas/{marketplace.js → accounts.js} +4 -14
  50. package/dist/src/schemas/accounts.js.map +10 -0
  51. package/dist/src/schemas/index.d.ts +28 -77
  52. package/dist/src/schemas/index.js +59 -69
  53. package/dist/src/schemas/index.js.map +4 -4
  54. package/dist/src/types.d.ts +10 -0
  55. package/migrations/0037_nullable_api_key.ts +35 -0
  56. package/migrations/0038_drop_workflow_tables.ts +46 -0
  57. package/migrations/0039_tenants.ts +66 -0
  58. package/migrations/0040_tenant_key_generations.ts +29 -0
  59. package/migrations/0041_subgraphs_drop_api_key_id.ts +49 -0
  60. package/migrations/0042_tenant_project_id.ts +25 -0
  61. package/migrations/0043_tenant_usage_monthly.ts +36 -0
  62. package/migrations/0044_provisioning_audit_log.ts +40 -0
  63. package/package.json +15 -7
  64. package/dist/src/db/queries/marketplace.js +0 -142
  65. package/dist/src/db/queries/marketplace.js.map +0 -10
  66. package/dist/src/schemas/marketplace.d.ts +0 -63
  67. package/dist/src/schemas/marketplace.js.map +0 -10
@@ -1,4 +1,17 @@
1
1
  import { z } from "zod/v4";
2
+ /**
3
+ * Account profile shapes. Unrelated to marketplace — previously lived in
4
+ * schemas/marketplace.ts alongside public-directory types. Kept here now
5
+ * that marketplace is gone so the profile fields (display_name, bio, slug)
6
+ * have a stable home.
7
+ */
8
+ interface UpdateProfileRequest {
9
+ display_name?: string;
10
+ bio?: string;
11
+ slug?: string;
12
+ }
13
+ declare const UpdateProfileRequestSchema: z.ZodType<UpdateProfileRequest>;
14
+ import { z as z2 } from "zod/v4";
2
15
  interface StxTransferFilter {
3
16
  type: "stx_transfer";
4
17
  sender?: string;
@@ -77,82 +90,20 @@ interface PrintEventFilter {
77
90
  contains?: string;
78
91
  }
79
92
  type EventFilter = StxTransferFilter | StxMintFilter | StxBurnFilter | StxLockFilter | FtTransferFilter | FtMintFilter | FtBurnFilter | NftTransferFilter | NftMintFilter | NftBurnFilter | ContractCallFilter | ContractDeployFilter | PrintEventFilter;
80
- declare const StxTransferFilterSchema: z.ZodType<StxTransferFilter>;
81
- declare const StxMintFilterSchema: z.ZodType<StxMintFilter>;
82
- declare const StxBurnFilterSchema: z.ZodType<StxBurnFilter>;
83
- declare const StxLockFilterSchema: z.ZodType<StxLockFilter>;
84
- declare const FtTransferFilterSchema: z.ZodType<FtTransferFilter>;
85
- declare const FtMintFilterSchema: z.ZodType<FtMintFilter>;
86
- declare const FtBurnFilterSchema: z.ZodType<FtBurnFilter>;
87
- declare const NftTransferFilterSchema: z.ZodType<NftTransferFilter>;
88
- declare const NftMintFilterSchema: z.ZodType<NftMintFilter>;
89
- declare const NftBurnFilterSchema: z.ZodType<NftBurnFilter>;
90
- declare const ContractCallFilterSchema: z.ZodType<ContractCallFilter>;
91
- declare const ContractDeployFilterSchema: z.ZodType<ContractDeployFilter>;
92
- declare const PrintEventFilterSchema: z.ZodType<PrintEventFilter>;
93
- declare const EventFilterSchema: z.ZodType<EventFilter>;
94
- import { z as z2 } from "zod/v4";
95
- interface PublishSubgraphRequest {
96
- tags?: string[];
97
- description?: string;
98
- }
99
- interface UpdateProfileRequest {
100
- display_name?: string;
101
- bio?: string;
102
- slug?: string;
103
- }
104
- interface ForkSubgraphRequest {
105
- sourceSubgraphName: string;
106
- newName?: string;
107
- }
108
- declare const PublishSubgraphRequestSchema: z2.ZodType<PublishSubgraphRequest>;
109
- declare const UpdateProfileRequestSchema: z2.ZodType<UpdateProfileRequest>;
110
- declare const ForkSubgraphRequestSchema: z2.ZodType<ForkSubgraphRequest>;
111
- interface MarketplaceCreator {
112
- displayName: string | null;
113
- slug: string | null;
114
- }
115
- interface MarketplaceSubgraphSummary {
116
- name: string;
117
- description: string | null;
118
- tags: string[];
119
- creator: MarketplaceCreator;
120
- status: string;
121
- version: string;
122
- tables: string[];
123
- totalQueries7d: number;
124
- progress: number;
125
- createdAt: string;
126
- }
127
- interface MarketplaceSubgraphDetail extends MarketplaceSubgraphSummary {
128
- tableSchemas: Record<string, {
129
- columns: Record<string, {
130
- type: string
131
- nullable?: boolean
132
- }>
133
- rowCount: number
134
- endpoint: string
135
- }>;
136
- sources: Record<string, unknown>;
137
- startBlock: number;
138
- lastProcessedBlock: number;
139
- forkedFrom: string | null;
140
- usage: {
141
- totalQueries7d: number
142
- totalQueries30d: number
143
- daily: Array<{
144
- date: string
145
- count: number
146
- }>
147
- };
148
- }
149
- interface CreatorProfile {
150
- displayName: string | null;
151
- bio: string | null;
152
- avatarUrl: string | null;
153
- slug: string | null;
154
- subgraphs: MarketplaceSubgraphSummary[];
155
- }
93
+ declare const StxTransferFilterSchema: z2.ZodType<StxTransferFilter>;
94
+ declare const StxMintFilterSchema: z2.ZodType<StxMintFilter>;
95
+ declare const StxBurnFilterSchema: z2.ZodType<StxBurnFilter>;
96
+ declare const StxLockFilterSchema: z2.ZodType<StxLockFilter>;
97
+ declare const FtTransferFilterSchema: z2.ZodType<FtTransferFilter>;
98
+ declare const FtMintFilterSchema: z2.ZodType<FtMintFilter>;
99
+ declare const FtBurnFilterSchema: z2.ZodType<FtBurnFilter>;
100
+ declare const NftTransferFilterSchema: z2.ZodType<NftTransferFilter>;
101
+ declare const NftMintFilterSchema: z2.ZodType<NftMintFilter>;
102
+ declare const NftBurnFilterSchema: z2.ZodType<NftBurnFilter>;
103
+ declare const ContractCallFilterSchema: z2.ZodType<ContractCallFilter>;
104
+ declare const ContractDeployFilterSchema: z2.ZodType<ContractDeployFilter>;
105
+ declare const PrintEventFilterSchema: z2.ZodType<PrintEventFilter>;
106
+ declare const EventFilterSchema: z2.ZodType<EventFilter>;
156
107
  import { z as z3 } from "zod/v4";
157
108
  interface DeploySubgraphRequest {
158
109
  name: string;
@@ -268,4 +219,4 @@ interface SubgraphQueryParams {
268
219
  fields?: string;
269
220
  filters?: Record<string, string>;
270
221
  }
271
- export { UpdateProfileRequestSchema, UpdateProfileRequest, SubgraphSyncInfo, SubgraphSummary, SubgraphQueryParams, SubgraphGapsResponse, SubgraphGapRange, SubgraphGapEntry, SubgraphDetail, StxTransferFilterSchema, StxTransferFilter, StxMintFilterSchema, StxMintFilter, StxLockFilterSchema, StxLockFilter, StxBurnFilterSchema, StxBurnFilter, ReindexResponse, PublishSubgraphRequestSchema, PublishSubgraphRequest, PrintEventFilterSchema, PrintEventFilter, NftTransferFilterSchema, NftTransferFilter, NftMintFilterSchema, NftMintFilter, NftBurnFilterSchema, NftBurnFilter, MarketplaceSubgraphSummary, MarketplaceSubgraphDetail, MarketplaceCreator, FtTransferFilterSchema, FtTransferFilter, FtMintFilterSchema, FtMintFilter, FtBurnFilterSchema, FtBurnFilter, ForkSubgraphRequestSchema, ForkSubgraphRequest, EventFilterSchema, EventFilter, DeploySubgraphResponse, DeploySubgraphRequestSchema, DeploySubgraphRequest, CreatorProfile, ContractDeployFilterSchema, ContractDeployFilter, ContractCallFilterSchema, ContractCallFilter };
222
+ export { UpdateProfileRequestSchema, UpdateProfileRequest, SubgraphSyncInfo, SubgraphSummary, SubgraphQueryParams, SubgraphGapsResponse, SubgraphGapRange, SubgraphGapEntry, SubgraphDetail, StxTransferFilterSchema, StxTransferFilter, StxMintFilterSchema, StxMintFilter, StxLockFilterSchema, StxLockFilter, StxBurnFilterSchema, StxBurnFilter, ReindexResponse, PrintEventFilterSchema, PrintEventFilter, NftTransferFilterSchema, NftTransferFilter, NftMintFilterSchema, NftMintFilter, NftBurnFilterSchema, NftBurnFilter, FtTransferFilterSchema, FtTransferFilter, FtMintFilterSchema, FtMintFilter, FtBurnFilterSchema, FtBurnFilter, EventFilterSchema, EventFilter, DeploySubgraphResponse, DeploySubgraphRequestSchema, DeploySubgraphRequest, ContractDeployFilterSchema, ContractDeployFilter, ContractCallFilterSchema, ContractCallFilter };
@@ -14,11 +14,19 @@ var __export = (target, all) => {
14
14
  });
15
15
  };
16
16
 
17
+ // src/schemas/accounts.ts
18
+ import { z } from "zod/v4";
19
+ var UpdateProfileRequestSchema = z.object({
20
+ display_name: z.string().max(50).optional(),
21
+ bio: z.string().max(300).optional(),
22
+ slug: z.string().regex(/^[a-z0-9-]+$/, "lowercase alphanumeric + hyphens only").min(3).max(30).optional()
23
+ });
24
+
17
25
  // src/schemas/filters.ts
18
26
  import { isValidAddress as _isValidAddress } from "@secondlayer/stacks";
19
- import { z } from "zod/v4";
27
+ import { z as z2 } from "zod/v4";
20
28
  var isValidAddress = _isValidAddress;
21
- var stacksPrincipal = z.string().refine((val) => {
29
+ var stacksPrincipal = z2.string().refine((val) => {
22
30
  const parts = val.split(".");
23
31
  if (parts.length > 2)
24
32
  return false;
@@ -28,81 +36,81 @@ var baseFilter = {
28
36
  sender: stacksPrincipal.optional(),
29
37
  recipient: stacksPrincipal.optional()
30
38
  };
31
- var StxTransferFilterSchema = z.object({
32
- type: z.literal("stx_transfer"),
39
+ var StxTransferFilterSchema = z2.object({
40
+ type: z2.literal("stx_transfer"),
33
41
  ...baseFilter,
34
- minAmount: z.coerce.number().int().positive().optional(),
35
- maxAmount: z.coerce.number().int().positive().optional()
42
+ minAmount: z2.coerce.number().int().positive().optional(),
43
+ maxAmount: z2.coerce.number().int().positive().optional()
36
44
  });
37
- var StxMintFilterSchema = z.object({
38
- type: z.literal("stx_mint"),
45
+ var StxMintFilterSchema = z2.object({
46
+ type: z2.literal("stx_mint"),
39
47
  recipient: stacksPrincipal.optional(),
40
- minAmount: z.coerce.number().int().positive().optional()
48
+ minAmount: z2.coerce.number().int().positive().optional()
41
49
  });
42
- var StxBurnFilterSchema = z.object({
43
- type: z.literal("stx_burn"),
50
+ var StxBurnFilterSchema = z2.object({
51
+ type: z2.literal("stx_burn"),
44
52
  sender: stacksPrincipal.optional(),
45
- minAmount: z.coerce.number().int().positive().optional()
53
+ minAmount: z2.coerce.number().int().positive().optional()
46
54
  });
47
- var StxLockFilterSchema = z.object({
48
- type: z.literal("stx_lock"),
55
+ var StxLockFilterSchema = z2.object({
56
+ type: z2.literal("stx_lock"),
49
57
  lockedAddress: stacksPrincipal.optional(),
50
- minAmount: z.coerce.number().int().positive().optional()
58
+ minAmount: z2.coerce.number().int().positive().optional()
51
59
  });
52
- var FtTransferFilterSchema = z.object({
53
- type: z.literal("ft_transfer"),
60
+ var FtTransferFilterSchema = z2.object({
61
+ type: z2.literal("ft_transfer"),
54
62
  ...baseFilter,
55
- assetIdentifier: z.string().optional(),
56
- minAmount: z.coerce.number().int().positive().optional()
63
+ assetIdentifier: z2.string().optional(),
64
+ minAmount: z2.coerce.number().int().positive().optional()
57
65
  });
58
- var FtMintFilterSchema = z.object({
59
- type: z.literal("ft_mint"),
66
+ var FtMintFilterSchema = z2.object({
67
+ type: z2.literal("ft_mint"),
60
68
  recipient: stacksPrincipal.optional(),
61
- assetIdentifier: z.string().optional(),
62
- minAmount: z.coerce.number().int().positive().optional()
69
+ assetIdentifier: z2.string().optional(),
70
+ minAmount: z2.coerce.number().int().positive().optional()
63
71
  });
64
- var FtBurnFilterSchema = z.object({
65
- type: z.literal("ft_burn"),
72
+ var FtBurnFilterSchema = z2.object({
73
+ type: z2.literal("ft_burn"),
66
74
  sender: stacksPrincipal.optional(),
67
- assetIdentifier: z.string().optional(),
68
- minAmount: z.coerce.number().int().positive().optional()
75
+ assetIdentifier: z2.string().optional(),
76
+ minAmount: z2.coerce.number().int().positive().optional()
69
77
  });
70
- var NftTransferFilterSchema = z.object({
71
- type: z.literal("nft_transfer"),
78
+ var NftTransferFilterSchema = z2.object({
79
+ type: z2.literal("nft_transfer"),
72
80
  ...baseFilter,
73
- assetIdentifier: z.string().optional(),
74
- tokenId: z.string().optional()
81
+ assetIdentifier: z2.string().optional(),
82
+ tokenId: z2.string().optional()
75
83
  });
76
- var NftMintFilterSchema = z.object({
77
- type: z.literal("nft_mint"),
84
+ var NftMintFilterSchema = z2.object({
85
+ type: z2.literal("nft_mint"),
78
86
  recipient: stacksPrincipal.optional(),
79
- assetIdentifier: z.string().optional(),
80
- tokenId: z.string().optional()
87
+ assetIdentifier: z2.string().optional(),
88
+ tokenId: z2.string().optional()
81
89
  });
82
- var NftBurnFilterSchema = z.object({
83
- type: z.literal("nft_burn"),
90
+ var NftBurnFilterSchema = z2.object({
91
+ type: z2.literal("nft_burn"),
84
92
  sender: stacksPrincipal.optional(),
85
- assetIdentifier: z.string().optional(),
86
- tokenId: z.string().optional()
93
+ assetIdentifier: z2.string().optional(),
94
+ tokenId: z2.string().optional()
87
95
  });
88
- var ContractCallFilterSchema = z.object({
89
- type: z.literal("contract_call"),
96
+ var ContractCallFilterSchema = z2.object({
97
+ type: z2.literal("contract_call"),
90
98
  contractId: stacksPrincipal.optional(),
91
- functionName: z.string().optional(),
99
+ functionName: z2.string().optional(),
92
100
  caller: stacksPrincipal.optional()
93
101
  });
94
- var ContractDeployFilterSchema = z.object({
95
- type: z.literal("contract_deploy"),
102
+ var ContractDeployFilterSchema = z2.object({
103
+ type: z2.literal("contract_deploy"),
96
104
  deployer: stacksPrincipal.optional(),
97
- contractName: z.string().optional()
105
+ contractName: z2.string().optional()
98
106
  });
99
- var PrintEventFilterSchema = z.object({
100
- type: z.literal("print_event"),
107
+ var PrintEventFilterSchema = z2.object({
108
+ type: z2.literal("print_event"),
101
109
  contractId: stacksPrincipal.optional(),
102
- topic: z.string().optional(),
103
- contains: z.string().optional()
110
+ topic: z2.string().optional(),
111
+ contains: z2.string().optional()
104
112
  });
105
- var EventFilterSchema = z.discriminatedUnion("type", [
113
+ var EventFilterSchema = z2.discriminatedUnion("type", [
106
114
  StxTransferFilterSchema,
107
115
  StxMintFilterSchema,
108
116
  StxBurnFilterSchema,
@@ -118,22 +126,6 @@ var EventFilterSchema = z.discriminatedUnion("type", [
118
126
  PrintEventFilterSchema
119
127
  ]);
120
128
 
121
- // src/schemas/marketplace.ts
122
- import { z as z2 } from "zod/v4";
123
- var PublishSubgraphRequestSchema = z2.object({
124
- tags: z2.array(z2.string().max(30)).max(5).optional(),
125
- description: z2.string().max(500).optional()
126
- });
127
- var UpdateProfileRequestSchema = z2.object({
128
- display_name: z2.string().max(50).optional(),
129
- bio: z2.string().max(300).optional(),
130
- slug: z2.string().regex(/^[a-z0-9-]+$/, "lowercase alphanumeric + hyphens only").min(3).max(30).optional()
131
- });
132
- var ForkSubgraphRequestSchema = z2.object({
133
- sourceSubgraphName: z2.string(),
134
- newName: z2.string().regex(/^[a-z0-9-]+$/, "lowercase alphanumeric + hyphens only").max(63).optional()
135
- });
136
-
137
129
  // src/schemas/subgraphs.ts
138
130
  import { z as z3 } from "zod/v4";
139
131
  var DeploySubgraphRequestSchema = z3.object({
@@ -152,7 +144,6 @@ export {
152
144
  StxMintFilterSchema,
153
145
  StxLockFilterSchema,
154
146
  StxBurnFilterSchema,
155
- PublishSubgraphRequestSchema,
156
147
  PrintEventFilterSchema,
157
148
  NftTransferFilterSchema,
158
149
  NftMintFilterSchema,
@@ -160,12 +151,11 @@ export {
160
151
  FtTransferFilterSchema,
161
152
  FtMintFilterSchema,
162
153
  FtBurnFilterSchema,
163
- ForkSubgraphRequestSchema,
164
154
  EventFilterSchema,
165
155
  DeploySubgraphRequestSchema,
166
156
  ContractDeployFilterSchema,
167
157
  ContractCallFilterSchema
168
158
  };
169
159
 
170
- //# debugId=5D7DE4BF80FFC83364756E2164756E21
160
+ //# debugId=C2E332004F21E1EA64756E2164756E21
171
161
  //# sourceMappingURL=index.js.map
@@ -1,12 +1,12 @@
1
1
  {
2
2
  "version": 3,
3
- "sources": ["../src/schemas/filters.ts", "../src/schemas/marketplace.ts", "../src/schemas/subgraphs.ts"],
3
+ "sources": ["../src/schemas/accounts.ts", "../src/schemas/filters.ts", "../src/schemas/subgraphs.ts"],
4
4
  "sourcesContent": [
5
+ "import { z } from \"zod/v4\";\n\n/**\n * Account profile shapes. Unrelated to marketplace — previously lived in\n * schemas/marketplace.ts alongside public-directory types. Kept here now\n * that marketplace is gone so the profile fields (display_name, bio, slug)\n * have a stable home.\n */\n\nexport interface UpdateProfileRequest {\n\tdisplay_name?: string;\n\tbio?: string;\n\tslug?: string;\n}\n\nexport const UpdateProfileRequestSchema: z.ZodType<UpdateProfileRequest> =\n\tz.object({\n\t\tdisplay_name: z.string().max(50).optional(),\n\t\tbio: z.string().max(300).optional(),\n\t\tslug: z\n\t\t\t.string()\n\t\t\t.regex(/^[a-z0-9-]+$/, \"lowercase alphanumeric + hyphens only\")\n\t\t\t.min(3)\n\t\t\t.max(30)\n\t\t\t.optional(),\n\t});\n",
5
6
  "import { isValidAddress as _isValidAddress } from \"@secondlayer/stacks\";\nimport { z } from \"zod/v4\";\n\nconst isValidAddress = _isValidAddress as (addr: string) => boolean;\n\n/** Validate a Stacks principal (standard or contract, e.g. SP2J...ABC or SP2J...ABC.contract-name) */\nconst stacksPrincipal = z.string().refine((val) => {\n\tconst parts = val.split(\".\");\n\tif (parts.length > 2) return false;\n\treturn isValidAddress(parts[0]!);\n}, \"Invalid Stacks principal address\");\n\n// Base filter with common fields\nconst baseFilter = {\n\t// Optional: filter by sender\n\tsender: stacksPrincipal.optional(),\n\t// Optional: filter by recipient\n\trecipient: stacksPrincipal.optional(),\n};\n\n// Type exports — defined first so they can annotate schemas\nexport interface StxTransferFilter {\n\ttype: \"stx_transfer\";\n\tsender?: string;\n\trecipient?: string;\n\tminAmount?: number;\n\tmaxAmount?: number;\n}\n\nexport interface StxMintFilter {\n\ttype: \"stx_mint\";\n\trecipient?: string;\n\tminAmount?: number;\n}\n\nexport interface StxBurnFilter {\n\ttype: \"stx_burn\";\n\tsender?: string;\n\tminAmount?: number;\n}\n\nexport interface StxLockFilter {\n\ttype: \"stx_lock\";\n\tlockedAddress?: string;\n\tminAmount?: number;\n}\n\nexport interface FtTransferFilter {\n\ttype: \"ft_transfer\";\n\tsender?: string;\n\trecipient?: string;\n\tassetIdentifier?: string;\n\tminAmount?: number;\n}\n\nexport interface FtMintFilter {\n\ttype: \"ft_mint\";\n\trecipient?: string;\n\tassetIdentifier?: string;\n\tminAmount?: number;\n}\n\nexport interface FtBurnFilter {\n\ttype: \"ft_burn\";\n\tsender?: string;\n\tassetIdentifier?: string;\n\tminAmount?: number;\n}\n\nexport interface NftTransferFilter {\n\ttype: \"nft_transfer\";\n\tsender?: string;\n\trecipient?: string;\n\tassetIdentifier?: string;\n\ttokenId?: string;\n}\n\nexport interface NftMintFilter {\n\ttype: \"nft_mint\";\n\trecipient?: string;\n\tassetIdentifier?: string;\n\ttokenId?: string;\n}\n\nexport interface NftBurnFilter {\n\ttype: \"nft_burn\";\n\tsender?: string;\n\tassetIdentifier?: string;\n\ttokenId?: string;\n}\n\nexport interface ContractCallFilter {\n\ttype: \"contract_call\";\n\tcontractId?: string;\n\tfunctionName?: string;\n\tcaller?: string;\n}\n\nexport interface ContractDeployFilter {\n\ttype: \"contract_deploy\";\n\tdeployer?: string;\n\tcontractName?: string;\n}\n\nexport interface PrintEventFilter {\n\ttype: \"print_event\";\n\tcontractId?: string;\n\ttopic?: string;\n\tcontains?: string;\n}\n\nexport type EventFilter =\n\t| StxTransferFilter\n\t| StxMintFilter\n\t| StxBurnFilter\n\t| StxLockFilter\n\t| FtTransferFilter\n\t| FtMintFilter\n\t| FtBurnFilter\n\t| NftTransferFilter\n\t| NftMintFilter\n\t| NftBurnFilter\n\t| ContractCallFilter\n\t| ContractDeployFilter\n\t| PrintEventFilter;\n\n// STX Transfer Filter\nexport const StxTransferFilterSchema: z.ZodType<StxTransferFilter> = z.object({\n\ttype: z.literal(\"stx_transfer\"),\n\t...baseFilter,\n\t// Optional: minimum amount in microSTX\n\tminAmount: z.coerce.number().int().positive().optional(),\n\t// Optional: maximum amount in microSTX\n\tmaxAmount: z.coerce.number().int().positive().optional(),\n});\n\n// STX Mint Filter\nexport const StxMintFilterSchema: z.ZodType<StxMintFilter> = z.object({\n\ttype: z.literal(\"stx_mint\"),\n\trecipient: stacksPrincipal.optional(),\n\tminAmount: z.coerce.number().int().positive().optional(),\n});\n\n// STX Burn Filter\nexport const StxBurnFilterSchema: z.ZodType<StxBurnFilter> = z.object({\n\ttype: z.literal(\"stx_burn\"),\n\tsender: stacksPrincipal.optional(),\n\tminAmount: z.coerce.number().int().positive().optional(),\n});\n\n// STX Lock Filter\nexport const StxLockFilterSchema: z.ZodType<StxLockFilter> = z.object({\n\ttype: z.literal(\"stx_lock\"),\n\tlockedAddress: stacksPrincipal.optional(),\n\tminAmount: z.coerce.number().int().positive().optional(),\n});\n\n// FT Transfer Filter\nexport const FtTransferFilterSchema: z.ZodType<FtTransferFilter> = z.object({\n\ttype: z.literal(\"ft_transfer\"),\n\t...baseFilter,\n\t// Contract that defines the token (e.g., SP3K8BC0PPEVCV7NZ6QSRWPQ2JE9E5B6N3PA0KBR9.token-wstx)\n\tassetIdentifier: z.string().optional(),\n\tminAmount: z.coerce.number().int().positive().optional(),\n});\n\n// FT Mint Filter\nexport const FtMintFilterSchema: z.ZodType<FtMintFilter> = z.object({\n\ttype: z.literal(\"ft_mint\"),\n\trecipient: stacksPrincipal.optional(),\n\tassetIdentifier: z.string().optional(),\n\tminAmount: z.coerce.number().int().positive().optional(),\n});\n\n// FT Burn Filter\nexport const FtBurnFilterSchema: z.ZodType<FtBurnFilter> = z.object({\n\ttype: z.literal(\"ft_burn\"),\n\tsender: stacksPrincipal.optional(),\n\tassetIdentifier: z.string().optional(),\n\tminAmount: z.coerce.number().int().positive().optional(),\n});\n\n// NFT Transfer Filter\nexport const NftTransferFilterSchema: z.ZodType<NftTransferFilter> = z.object({\n\ttype: z.literal(\"nft_transfer\"),\n\t...baseFilter,\n\tassetIdentifier: z.string().optional(),\n\t// Optional: filter by specific token ID (Clarity value as hex)\n\ttokenId: z.string().optional(),\n});\n\n// NFT Mint Filter\nexport const NftMintFilterSchema: z.ZodType<NftMintFilter> = z.object({\n\ttype: z.literal(\"nft_mint\"),\n\trecipient: stacksPrincipal.optional(),\n\tassetIdentifier: z.string().optional(),\n\ttokenId: z.string().optional(),\n});\n\n// NFT Burn Filter\nexport const NftBurnFilterSchema: z.ZodType<NftBurnFilter> = z.object({\n\ttype: z.literal(\"nft_burn\"),\n\tsender: stacksPrincipal.optional(),\n\tassetIdentifier: z.string().optional(),\n\ttokenId: z.string().optional(),\n});\n\n// Contract Call Filter\nexport const ContractCallFilterSchema: z.ZodType<ContractCallFilter> = z.object(\n\t{\n\t\ttype: z.literal(\"contract_call\"),\n\t\t// Contract being called\n\t\tcontractId: stacksPrincipal.optional(),\n\t\t// Function name (supports wildcards with *)\n\t\tfunctionName: z.string().optional(),\n\t\t// Caller address\n\t\tcaller: stacksPrincipal.optional(),\n\t},\n);\n\n// Contract Deploy Filter\nexport const ContractDeployFilterSchema: z.ZodType<ContractDeployFilter> =\n\tz.object({\n\t\ttype: z.literal(\"contract_deploy\"),\n\t\t// Deployer address\n\t\tdeployer: stacksPrincipal.optional(),\n\t\t// Contract name pattern (supports wildcards)\n\t\tcontractName: z.string().optional(),\n\t});\n\n// Print Event Filter (smart contract events)\nexport const PrintEventFilterSchema: z.ZodType<PrintEventFilter> = z.object({\n\ttype: z.literal(\"print_event\"),\n\t// Contract emitting the event\n\tcontractId: stacksPrincipal.optional(),\n\t// Topic/name of the event\n\ttopic: z.string().optional(),\n\t// Search for substring in event data\n\tcontains: z.string().optional(),\n});\n\n// Union of all filter types\nexport const EventFilterSchema: z.ZodType<EventFilter> = z.discriminatedUnion(\n\t\"type\",\n\t[\n\t\tStxTransferFilterSchema as any,\n\t\tStxMintFilterSchema as any,\n\t\tStxBurnFilterSchema as any,\n\t\tStxLockFilterSchema as any,\n\t\tFtTransferFilterSchema as any,\n\t\tFtMintFilterSchema as any,\n\t\tFtBurnFilterSchema as any,\n\t\tNftTransferFilterSchema as any,\n\t\tNftMintFilterSchema as any,\n\t\tNftBurnFilterSchema as any,\n\t\tContractCallFilterSchema as any,\n\t\tContractDeployFilterSchema as any,\n\t\tPrintEventFilterSchema as any,\n\t],\n);\n",
6
- "import { z } from \"zod/v4\";\n\n// ── Request Types ────────────────────────────────────────────────────\n\nexport interface PublishSubgraphRequest {\n\ttags?: string[];\n\tdescription?: string;\n}\n\nexport interface UpdateProfileRequest {\n\tdisplay_name?: string;\n\tbio?: string;\n\tslug?: string;\n}\n\nexport interface ForkSubgraphRequest {\n\tsourceSubgraphName: string;\n\tnewName?: string;\n}\n\n// ── Request Schemas ───────────────────────────────────────────────────\n\nexport const PublishSubgraphRequestSchema: z.ZodType<PublishSubgraphRequest> =\n\tz.object({\n\t\ttags: z.array(z.string().max(30)).max(5).optional(),\n\t\tdescription: z.string().max(500).optional(),\n\t});\n\nexport const UpdateProfileRequestSchema: z.ZodType<UpdateProfileRequest> =\n\tz.object({\n\t\tdisplay_name: z.string().max(50).optional(),\n\t\tbio: z.string().max(300).optional(),\n\t\tslug: z\n\t\t\t.string()\n\t\t\t.regex(/^[a-z0-9-]+$/, \"lowercase alphanumeric + hyphens only\")\n\t\t\t.min(3)\n\t\t\t.max(30)\n\t\t\t.optional(),\n\t});\n\nexport const ForkSubgraphRequestSchema: z.ZodType<ForkSubgraphRequest> =\n\tz.object({\n\t\tsourceSubgraphName: z.string(),\n\t\tnewName: z\n\t\t\t.string()\n\t\t\t.regex(/^[a-z0-9-]+$/, \"lowercase alphanumeric + hyphens only\")\n\t\t\t.max(63)\n\t\t\t.optional(),\n\t});\n\n// ── Response Types ────────────────────────────────────────────────────\n\nexport interface MarketplaceCreator {\n\tdisplayName: string | null;\n\tslug: string | null;\n}\n\nexport interface MarketplaceSubgraphSummary {\n\tname: string;\n\tdescription: string | null;\n\ttags: string[];\n\tcreator: MarketplaceCreator;\n\tstatus: string;\n\tversion: string;\n\ttables: string[];\n\ttotalQueries7d: number;\n\tprogress: number;\n\tcreatedAt: string;\n}\n\nexport interface MarketplaceSubgraphDetail extends MarketplaceSubgraphSummary {\n\ttableSchemas: Record<\n\t\tstring,\n\t\t{\n\t\t\tcolumns: Record<string, { type: string; nullable?: boolean }>;\n\t\t\trowCount: number;\n\t\t\tendpoint: string;\n\t\t}\n\t>;\n\tsources: Record<string, unknown>;\n\tstartBlock: number;\n\tlastProcessedBlock: number;\n\tforkedFrom: string | null;\n\tusage: {\n\t\ttotalQueries7d: number;\n\t\ttotalQueries30d: number;\n\t\tdaily: Array<{ date: string; count: number }>;\n\t};\n}\n\nexport interface CreatorProfile {\n\tdisplayName: string | null;\n\tbio: string | null;\n\tavatarUrl: string | null;\n\tslug: string | null;\n\tsubgraphs: MarketplaceSubgraphSummary[];\n}\n",
7
7
  "import { z } from \"zod/v4\";\n\n// ── Deploy Subgraph Request ─────────────────────────────────────────────────\n\nexport interface DeploySubgraphRequest {\n\tname: string;\n\tversion?: string;\n\tdescription?: string;\n\tsources: Record<string, Record<string, unknown>>;\n\tschema: Record<string, unknown>;\n\thandlerCode: string;\n\t/** Original TypeScript source, persisted so chat can read/diff/edit later. */\n\tsourceCode?: string;\n\t/** @deprecated Use server auto-reindex on breaking changes instead */\n\treindex?: boolean;\n}\n\nexport const DeploySubgraphRequestSchema: z.ZodType<DeploySubgraphRequest> =\n\tz.object({\n\t\tname: z\n\t\t\t.string()\n\t\t\t.regex(/^[a-z0-9-]+$/, \"lowercase alphanumeric + hyphens only\")\n\t\t\t.max(63),\n\t\tversion: z.string().optional(),\n\t\tdescription: z.string().optional(),\n\t\tsources: z\n\t\t\t.record(z.string(), z.record(z.string(), z.unknown()))\n\t\t\t.refine(\n\t\t\t\t(s) => Object.keys(s).length > 0,\n\t\t\t\t\"Must have at least one source\",\n\t\t\t),\n\t\tschema: z.record(z.string(), z.unknown()),\n\t\thandlerCode: z.string().max(1_048_576, \"handler code exceeds 1MB limit\"),\n\t\tsourceCode: z\n\t\t\t.string()\n\t\t\t.max(1_048_576, \"source code exceeds 1MB limit\")\n\t\t\t.optional(),\n\t\treindex: z.boolean().optional(),\n\t});\n\nexport interface DeploySubgraphResponse {\n\taction: \"created\" | \"unchanged\" | \"updated\" | \"reindexed\";\n\tsubgraphId: string;\n\tversion: string;\n\tmessage: string;\n\tdiff?: {\n\t\taddedTables: string[];\n\t\tremovedTables: string[];\n\t\taddedColumns: Record<string, string[]>;\n\t\tbreakingChanges: string[];\n\t};\n}\n\n// Subgraph API response types\n\nexport interface SubgraphSummary {\n\tname: string;\n\tversion: string;\n\tstatus: string;\n\tlastProcessedBlock: number;\n\ttotalProcessed: number;\n\ttotalErrors: number;\n\ttables: string[];\n\tchainTip: number;\n\tprogress: number;\n\tgapCount: number;\n\tintegrity: \"complete\" | \"gaps_detected\";\n\tcreatedAt: string;\n}\n\nexport interface SubgraphGapRange {\n\tstart: number;\n\tend: number;\n\tsize: number;\n\treason: string;\n}\n\nexport interface SubgraphSyncInfo {\n\tstatus: \"synced\" | \"catching_up\" | \"reindexing\" | \"error\";\n\tstartBlock: number;\n\tlastProcessedBlock: number;\n\tchainTip: number;\n\tblocksRemaining: number;\n\tprogress: number;\n\tgaps: {\n\t\tcount: number;\n\t\ttotalMissingBlocks: number;\n\t\tranges: SubgraphGapRange[];\n\t};\n\tintegrity: \"complete\" | \"gaps_detected\";\n}\n\nexport interface SubgraphDetail {\n\tname: string;\n\tversion: string;\n\tstatus: string;\n\tlastProcessedBlock: number;\n\thealth: {\n\t\ttotalProcessed: number;\n\t\ttotalErrors: number;\n\t\terrorRate: number;\n\t\tlastError: string | null;\n\t\tlastErrorAt: string | null;\n\t};\n\tsync: SubgraphSyncInfo;\n\ttables: Record<\n\t\tstring,\n\t\t{\n\t\t\tendpoint: string;\n\t\t\tcolumns: Record<string, { type: string; nullable?: boolean }>;\n\t\t\trowCount: number;\n\t\t\texample: string;\n\t\t}\n\t>;\n\tcreatedAt: string;\n\tupdatedAt: string;\n}\n\nexport interface SubgraphGapEntry {\n\tstart: number;\n\tend: number;\n\tsize: number;\n\treason: string;\n\tdetectedAt: string;\n\tresolvedAt: string | null;\n}\n\nexport interface SubgraphGapsResponse {\n\tdata: SubgraphGapEntry[];\n\tmeta: {\n\t\ttotal: number;\n\t\ttotalMissingBlocks: number;\n\t\tlimit: number;\n\t\toffset: number;\n\t};\n}\n\nexport interface ReindexResponse {\n\tmessage: string;\n\tfromBlock: number;\n\ttoBlock: number | string;\n}\n\nexport interface SubgraphQueryParams {\n\tsort?: string;\n\torder?: string;\n\tlimit?: number;\n\toffset?: number;\n\tfields?: string;\n\tfilters?: Record<string, string>;\n}\n"
8
8
  ],
9
- "mappings": "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",
10
- "debugId": "5D7DE4BF80FFC83364756E2164756E21",
9
+ "mappings": "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",
10
+ "debugId": "C2E332004F21E1EA64756E2164756E21",
11
11
  "names": []
12
12
  }
@@ -48,6 +48,16 @@ type IndexProgress = Selectable<IndexProgressTable>;
48
48
  type InsertIndexProgress = Insertable<IndexProgressTable>;
49
49
  interface EnvSchemaOutput {
50
50
  DATABASE_URL?: string;
51
+ /**
52
+ * Shared indexer DB (blocks/txs/events). Falls back to DATABASE_URL.
53
+ * Set this alongside TARGET_DATABASE_URL to enable dual-DB mode.
54
+ */
55
+ SOURCE_DATABASE_URL?: string;
56
+ /**
57
+ * Tenant DB (subgraph schemas + subgraphs table). Falls back to DATABASE_URL.
58
+ * Set this alongside SOURCE_DATABASE_URL to enable dual-DB mode.
59
+ */
60
+ TARGET_DATABASE_URL?: string;
51
61
  NETWORK?: "mainnet" | "testnet";
52
62
  NETWORKS?: ("mainnet" | "testnet")[];
53
63
  LOG_LEVEL: "debug" | "info" | "warn" | "error";
@@ -0,0 +1,35 @@
1
+ import { type Kysely, sql } from "kysely";
2
+
3
+ /**
4
+ * Make `subgraphs.api_key_id` nullable to support oss/dedicated modes where
5
+ * there's no per-tenant API key concept. In platform mode the column stays
6
+ * populated on every insert; in oss/dedicated it's NULL.
7
+ *
8
+ * A partial unique index on `(name) WHERE api_key_id IS NULL` enforces the
9
+ * single-tenant constraint: within a non-platform instance, subgraph names
10
+ * are globally unique (there's only one "tenant"). Platform mode's existing
11
+ * uniqueness constraint on `(api_key_id, name)` stays in place for the
12
+ * multi-tenant case.
13
+ */
14
+ export async function up(db: Kysely<unknown>): Promise<void> {
15
+ // Fail fast instead of hanging when a live service holds ACCESS SHARE on
16
+ // `subgraphs` (e.g. subgraph-processor's 5s poll). Deploy script stops
17
+ // dependent services before running migrations — this is a safety net.
18
+ await sql`SET lock_timeout = '30s'`.execute(db);
19
+
20
+ await sql`ALTER TABLE subgraphs ALTER COLUMN api_key_id DROP NOT NULL`.execute(
21
+ db,
22
+ );
23
+ await sql`
24
+ CREATE UNIQUE INDEX IF NOT EXISTS subgraphs_name_unique_no_key
25
+ ON subgraphs (name)
26
+ WHERE api_key_id IS NULL
27
+ `.execute(db);
28
+ }
29
+
30
+ export async function down(db: Kysely<unknown>): Promise<void> {
31
+ await sql`DROP INDEX IF EXISTS subgraphs_name_unique_no_key`.execute(db);
32
+ // Intentionally does NOT re-add NOT NULL — any rows inserted while the
33
+ // constraint was relaxed would break the migration. Operators should
34
+ // backfill api_key_id before re-applying NOT NULL manually if desired.
35
+ }
@@ -0,0 +1,46 @@
1
+ import { type Kysely, sql } from "kysely";
2
+
3
+ /**
4
+ * Drops all workflow-related tables + the `tx_confirmed_notify` trigger.
5
+ *
6
+ * Workflows are going on the back burner while we ship dedicated-hosted
7
+ * subgraphs. We've learned enough from building the subgraph tenant model
8
+ * that reviving workflows later can follow the same dedicated-per-tenant
9
+ * pattern with a fresh schema designed for that architecture — no reason
10
+ * to keep dormant tables on the shared platform DB.
11
+ *
12
+ * Tables dropped (in FK-safe order via CASCADE):
13
+ * workflow_steps, workflow_runs, workflow_queue, workflow_schedules,
14
+ * workflow_cursors, workflow_signer_secrets, workflow_budgets,
15
+ * workflow_definitions
16
+ *
17
+ * Also drops `tx_confirmed_notify` — nobody listens on `tx:confirmed` now
18
+ * that workflow-runner is unmounted. The trigger fires on every
19
+ * transactions insert (indexer hot path), so leaving it is wasted work.
20
+ *
21
+ * `down` is intentionally a no-op. When workflows revive, they get fresh
22
+ * migrations designed for the tenant model — don't try to reverse into the
23
+ * old platform-shared schema.
24
+ */
25
+ export async function up(db: Kysely<unknown>): Promise<void> {
26
+ await sql`SET lock_timeout = '30s'`.execute(db);
27
+
28
+ await sql`DROP TRIGGER IF EXISTS tx_confirmed_notify ON transactions`.execute(
29
+ db,
30
+ );
31
+ await sql`DROP FUNCTION IF EXISTS notify_tx_confirmed()`.execute(db);
32
+
33
+ await sql`DROP TABLE IF EXISTS workflow_steps CASCADE`.execute(db);
34
+ await sql`DROP TABLE IF EXISTS workflow_runs CASCADE`.execute(db);
35
+ await sql`DROP TABLE IF EXISTS workflow_queue CASCADE`.execute(db);
36
+ await sql`DROP TABLE IF EXISTS workflow_schedules CASCADE`.execute(db);
37
+ await sql`DROP TABLE IF EXISTS workflow_cursors CASCADE`.execute(db);
38
+ await sql`DROP TABLE IF EXISTS workflow_signer_secrets CASCADE`.execute(db);
39
+ await sql`DROP TABLE IF EXISTS workflow_budgets CASCADE`.execute(db);
40
+ await sql`DROP TABLE IF EXISTS workflow_definitions CASCADE`.execute(db);
41
+ }
42
+
43
+ export async function down(_db: Kysely<unknown>): Promise<void> {
44
+ // Intentional no-op. Revived workflows will use fresh migrations sized
45
+ // for the tenant-per-customer model.
46
+ }
@@ -0,0 +1,66 @@
1
+ import { type Kysely, sql } from "kysely";
2
+
3
+ /**
4
+ * Dedicated-hosting tenant registry.
5
+ *
6
+ * One row per customer instance. Provisioner is stateless — it does Docker
7
+ * ops + returns values; control plane (this table) owns the persistent
8
+ * mapping between accounts and their per-tenant stack.
9
+ *
10
+ * Encrypted fields use `packages/shared/src/crypto/secrets.ts` (AES-GCM
11
+ * envelope keyed by `SECONDLAYER_SECRETS_KEY`). Never log them in plaintext.
12
+ *
13
+ * Storage is soft-enforced: `storage_used_mb` is updated by the health
14
+ * cron; alerts + overage billing live in the control plane, not the DB.
15
+ */
16
+ export async function up(db: Kysely<unknown>): Promise<void> {
17
+ await sql`SET lock_timeout = '30s'`.execute(db);
18
+
19
+ await sql`
20
+ CREATE TABLE tenants (
21
+ id uuid PRIMARY KEY DEFAULT gen_random_uuid(),
22
+ account_id uuid NOT NULL REFERENCES accounts(id) ON DELETE RESTRICT,
23
+ slug text NOT NULL UNIQUE,
24
+ status text NOT NULL DEFAULT 'provisioning',
25
+
26
+ plan text NOT NULL,
27
+ cpus numeric(4,2) NOT NULL,
28
+ memory_mb integer NOT NULL,
29
+ storage_limit_mb integer NOT NULL,
30
+ storage_used_mb integer,
31
+
32
+ pg_container_id text,
33
+ api_container_id text,
34
+ processor_container_id text,
35
+
36
+ target_database_url_enc bytea NOT NULL,
37
+ tenant_jwt_secret_enc bytea NOT NULL,
38
+ anon_key_enc bytea NOT NULL,
39
+ service_key_enc bytea NOT NULL,
40
+
41
+ api_url_internal text NOT NULL,
42
+ api_url_public text NOT NULL,
43
+
44
+ trial_ends_at timestamptz NOT NULL,
45
+ suspended_at timestamptz,
46
+ last_health_check_at timestamptz,
47
+
48
+ created_at timestamptz NOT NULL DEFAULT now(),
49
+ updated_at timestamptz NOT NULL DEFAULT now()
50
+ )
51
+ `.execute(db);
52
+
53
+ await sql`CREATE INDEX tenants_account_idx ON tenants (account_id)`.execute(
54
+ db,
55
+ );
56
+ await sql`CREATE INDEX tenants_status_idx ON tenants (status) WHERE status <> 'deleted'`.execute(
57
+ db,
58
+ );
59
+ await sql`CREATE INDEX tenants_trial_ends_idx ON tenants (trial_ends_at) WHERE status IN ('provisioning', 'active')`.execute(
60
+ db,
61
+ );
62
+ }
63
+
64
+ export async function down(db: Kysely<unknown>): Promise<void> {
65
+ await sql`DROP TABLE IF EXISTS tenants`.execute(db);
66
+ }
@@ -0,0 +1,29 @@
1
+ import { type Kysely, sql } from "kysely";
2
+
3
+ /**
4
+ * Per-tenant key generation counters. Each JWT carries a `gen` claim; the
5
+ * tenant API rejects tokens whose `gen` doesn't match the current counter
6
+ * for that role. Bumping a counter invalidates all JWTs of that role
7
+ * immediately, without rotating the signing secret (which would force
8
+ * both keys to rotate together).
9
+ *
10
+ * UX: user can rotate service alone (leaked server-side key) OR anon alone
11
+ * (client-side embedding exposed) OR both together (offboarding panic).
12
+ */
13
+ export async function up(db: Kysely<unknown>): Promise<void> {
14
+ await sql`SET lock_timeout = '30s'`.execute(db);
15
+
16
+ await sql`
17
+ ALTER TABLE tenants
18
+ ADD COLUMN service_gen integer NOT NULL DEFAULT 1,
19
+ ADD COLUMN anon_gen integer NOT NULL DEFAULT 1
20
+ `.execute(db);
21
+ }
22
+
23
+ export async function down(db: Kysely<unknown>): Promise<void> {
24
+ await sql`
25
+ ALTER TABLE tenants
26
+ DROP COLUMN IF EXISTS service_gen,
27
+ DROP COLUMN IF EXISTS anon_gen
28
+ `.execute(db);
29
+ }
@@ -0,0 +1,49 @@
1
+ import { type Kysely, sql } from "kysely";
2
+
3
+ /**
4
+ * Post-cutover cleanup: drop `subgraphs.api_key_id` and the partial unique
5
+ * index that went with nullable-api-key-id handling. Every subgraph lives in
6
+ * a tenant DB now; tenants authenticate via JWT (TENANT_JWT_SECRET), not
7
+ * per-account API keys — so this column has been dead weight since migration
8
+ * 0037 made it nullable.
9
+ *
10
+ * Runs against BOTH the platform DB and every tenant DB (migrations share
11
+ * the same list). The platform DB's `subgraphs` table is manually dropped
12
+ * as a one-off operation AFTER this migration (see Phase 2 cutover notes).
13
+ *
14
+ * Restores the simple `UNIQUE (name)` constraint the table started with —
15
+ * tenant subgraphs were always name-unique within a tenant.
16
+ */
17
+ export async function up(db: Kysely<unknown>): Promise<void> {
18
+ await sql`SET lock_timeout = '30s'`.execute(db);
19
+
20
+ await sql`DROP INDEX IF EXISTS subgraphs_name_unique_no_key`.execute(db);
21
+ await sql`ALTER TABLE subgraphs DROP COLUMN IF EXISTS api_key_id`.execute(db);
22
+ // Re-add the simple name-unique constraint if it's not already there
23
+ // (noop if it was never dropped in a prior migration).
24
+ await sql`
25
+ DO $$
26
+ BEGIN
27
+ IF NOT EXISTS (
28
+ SELECT 1 FROM pg_constraint
29
+ WHERE conname = 'subgraphs_name_unique'
30
+ ) THEN
31
+ ALTER TABLE subgraphs ADD CONSTRAINT subgraphs_name_unique UNIQUE (name);
32
+ END IF;
33
+ END$$
34
+ `.execute(db);
35
+ }
36
+
37
+ export async function down(db: Kysely<unknown>): Promise<void> {
38
+ await sql`ALTER TABLE subgraphs DROP CONSTRAINT IF EXISTS subgraphs_name_unique`.execute(
39
+ db,
40
+ );
41
+ await sql`ALTER TABLE subgraphs ADD COLUMN IF NOT EXISTS api_key_id text`.execute(
42
+ db,
43
+ );
44
+ await sql`
45
+ CREATE UNIQUE INDEX IF NOT EXISTS subgraphs_name_unique_no_key
46
+ ON subgraphs (name)
47
+ WHERE api_key_id IS NULL
48
+ `.execute(db);
49
+ }
@@ -0,0 +1,25 @@
1
+ import { type Kysely, sql } from "kysely";
2
+
3
+ /**
4
+ * Link tenants to projects (1:1 enforced at application layer today;
5
+ * schema supports 1:N for future branching).
6
+ *
7
+ * `ON DELETE SET NULL` so a project delete doesn't cascade into tenant
8
+ * teardown — the tenant row stays (with project_id = NULL) until explicit
9
+ * teardown via the provisioner.
10
+ */
11
+ export async function up(db: Kysely<unknown>): Promise<void> {
12
+ await sql`SET lock_timeout = '30s'`.execute(db);
13
+ await sql`
14
+ ALTER TABLE tenants
15
+ ADD COLUMN project_id uuid REFERENCES projects(id) ON DELETE SET NULL
16
+ `.execute(db);
17
+ await sql`CREATE INDEX IF NOT EXISTS tenants_project_idx ON tenants (project_id)`.execute(
18
+ db,
19
+ );
20
+ }
21
+
22
+ export async function down(db: Kysely<unknown>): Promise<void> {
23
+ await sql`DROP INDEX IF EXISTS tenants_project_idx`.execute(db);
24
+ await sql`ALTER TABLE tenants DROP COLUMN IF EXISTS project_id`.execute(db);
25
+ }