postgresai 0.16.0-rc.4 → 0.16.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 (85) hide show
  1. package/README.md +154 -0
  2. package/dist/bin/postgres-ai.js +2911 -255
  3. package/package.json +12 -3
  4. package/schemas/A002.schema.json +63 -0
  5. package/schemas/A003.schema.json +73 -0
  6. package/schemas/A004.schema.json +81 -0
  7. package/schemas/A007.schema.json +71 -0
  8. package/schemas/A013.schema.json +61 -0
  9. package/schemas/D001.schema.json +71 -0
  10. package/schemas/D004.schema.json +136 -0
  11. package/schemas/F001.schema.json +73 -0
  12. package/schemas/F002.schema.json +108 -0
  13. package/schemas/F003.schema.json +138 -0
  14. package/schemas/F004.schema.json +125 -0
  15. package/schemas/F005.schema.json +131 -0
  16. package/schemas/F009.schema.json +155 -0
  17. package/schemas/G001.schema.json +135 -0
  18. package/schemas/G003.schema.json +90 -0
  19. package/schemas/H001.schema.json +141 -0
  20. package/schemas/H002.schema.json +129 -0
  21. package/schemas/H004.schema.json +128 -0
  22. package/schemas/I001.schema.json +149 -0
  23. package/schemas/K001.schema.json +161 -0
  24. package/schemas/K003.schema.json +163 -0
  25. package/schemas/K004.schema.json +110 -0
  26. package/schemas/K005.schema.json +110 -0
  27. package/schemas/K006.schema.json +110 -0
  28. package/schemas/K007.schema.json +110 -0
  29. package/schemas/K008.schema.json +110 -0
  30. package/schemas/M001.schema.json +119 -0
  31. package/schemas/M002.schema.json +110 -0
  32. package/schemas/M003.schema.json +128 -0
  33. package/schemas/N001.schema.json +161 -0
  34. package/schemas/query.schema.json +62 -0
  35. package/CHANGELOG.md +0 -11
  36. package/bin/postgres-ai.ts +0 -5578
  37. package/bun.lock +0 -258
  38. package/bunfig.toml +0 -20
  39. package/lib/aas-onboard.ts +0 -251
  40. package/lib/auth-server.ts +0 -285
  41. package/lib/checkup-api.ts +0 -526
  42. package/lib/checkup-dictionary.ts +0 -103
  43. package/lib/checkup-summary.ts +0 -338
  44. package/lib/checkup.ts +0 -2261
  45. package/lib/config.ts +0 -171
  46. package/lib/init.ts +0 -1152
  47. package/lib/instances.ts +0 -245
  48. package/lib/issues.ts +0 -1060
  49. package/lib/mcp-server.ts +0 -667
  50. package/lib/metrics-loader.ts +0 -134
  51. package/lib/pkce.ts +0 -79
  52. package/lib/reports.ts +0 -373
  53. package/lib/storage.ts +0 -367
  54. package/lib/supabase.ts +0 -826
  55. package/lib/util.ts +0 -134
  56. package/packages/postgres-ai/README.md +0 -26
  57. package/packages/postgres-ai/bin/postgres-ai.js +0 -27
  58. package/packages/postgres-ai/package.json +0 -27
  59. package/scripts/embed-checkup-dictionary.ts +0 -115
  60. package/scripts/embed-metrics.ts +0 -160
  61. package/scripts/generate-release-notes.ts +0 -668
  62. package/test/PERMISSION_CHECK_TEST_SUMMARY.md +0 -139
  63. package/test/aas-onboard.test.ts +0 -301
  64. package/test/auth.test.ts +0 -287
  65. package/test/checkup.integration.test.ts +0 -413
  66. package/test/checkup.test.ts +0 -3626
  67. package/test/compose-cmd.test.ts +0 -120
  68. package/test/config-consistency.test.ts +0 -352
  69. package/test/init.integration.test.ts +0 -438
  70. package/test/init.test.ts +0 -1816
  71. package/test/issues.cli.test.ts +0 -1162
  72. package/test/issues.test.ts +0 -456
  73. package/test/mcp-server.test.ts +0 -2530
  74. package/test/monitoring.test.ts +0 -746
  75. package/test/permission-check-sql.test.ts +0 -116
  76. package/test/reports.cli.test.ts +0 -793
  77. package/test/reports.test.ts +0 -977
  78. package/test/schema-validation.test.ts +0 -231
  79. package/test/storage.test.ts +0 -935
  80. package/test/supabase.test.ts +0 -709
  81. package/test/targets-add-config.test.ts +0 -28
  82. package/test/test-utils.ts +0 -190
  83. package/test/upgrade.test.ts +0 -1056
  84. package/test/util.test.ts +0 -44
  85. package/tsconfig.json +0 -20
@@ -1,456 +0,0 @@
1
- import { describe, test, expect, mock, beforeEach, afterEach } from "bun:test";
2
- import { createIssue, updateIssue, updateIssueComment } from "../lib/issues";
3
-
4
- // Mock fetch globally
5
- const originalFetch = globalThis.fetch;
6
-
7
- describe("createIssue", () => {
8
- afterEach(() => {
9
- globalThis.fetch = originalFetch;
10
- });
11
-
12
- test("throws when apiKey is missing", async () => {
13
- await expect(
14
- createIssue({
15
- apiKey: "",
16
- apiBaseUrl: "https://api.example.com",
17
- title: "Test Issue",
18
- orgId: 1,
19
- })
20
- ).rejects.toThrow("API key is required");
21
- });
22
-
23
- test("throws when title is missing", async () => {
24
- await expect(
25
- createIssue({
26
- apiKey: "test-key",
27
- apiBaseUrl: "https://api.example.com",
28
- title: "",
29
- orgId: 1,
30
- })
31
- ).rejects.toThrow("title is required");
32
- });
33
-
34
- test("throws when orgId is not a number", async () => {
35
- await expect(
36
- createIssue({
37
- apiKey: "test-key",
38
- apiBaseUrl: "https://api.example.com",
39
- title: "Test Issue",
40
- orgId: undefined as unknown as number,
41
- })
42
- ).rejects.toThrow("orgId is required");
43
- });
44
-
45
- test("accepts orgId=0 as valid", async () => {
46
- const mockResponse = {
47
- id: "test-id",
48
- title: "Test Issue",
49
- description: null,
50
- created_at: "2025-01-01T00:00:00Z",
51
- status: 0,
52
- project_id: null,
53
- labels: null,
54
- };
55
-
56
- globalThis.fetch = mock(() =>
57
- Promise.resolve(
58
- new Response(JSON.stringify(mockResponse), {
59
- status: 200,
60
- headers: { "Content-Type": "application/json" },
61
- })
62
- )
63
- ) as unknown as typeof fetch;
64
-
65
- const result = await createIssue({
66
- apiKey: "test-key",
67
- apiBaseUrl: "https://api.example.com",
68
- title: "Test Issue",
69
- orgId: 0,
70
- });
71
-
72
- expect(result.id).toBe("test-id");
73
- });
74
-
75
- test("makes correct API call with all parameters", async () => {
76
- const mockResponse = {
77
- id: "test-id",
78
- title: "Test Issue",
79
- description: "Test description",
80
- created_at: "2025-01-01T00:00:00Z",
81
- status: 0,
82
- project_id: 123,
83
- labels: ["bug", "urgent"],
84
- };
85
-
86
- let capturedRequest: { url: string; options: RequestInit } | null = null;
87
-
88
- globalThis.fetch = mock((url: string, options: RequestInit) => {
89
- capturedRequest = { url, options };
90
- return Promise.resolve(
91
- new Response(JSON.stringify(mockResponse), {
92
- status: 200,
93
- headers: { "Content-Type": "application/json" },
94
- })
95
- );
96
- }) as unknown as typeof fetch;
97
-
98
- const result = await createIssue({
99
- apiKey: "test-key",
100
- apiBaseUrl: "https://api.example.com",
101
- title: "Test Issue",
102
- orgId: 1,
103
- description: "Test description",
104
- projectId: 123,
105
- labels: ["bug", "urgent"],
106
- });
107
-
108
- expect(capturedRequest).not.toBeNull();
109
- expect(capturedRequest!.url).toBe("https://api.example.com/rpc/issue_create");
110
- expect(capturedRequest!.options.method).toBe("POST");
111
-
112
- const body = JSON.parse(capturedRequest!.options.body as string);
113
- expect(body.title).toBe("Test Issue");
114
- expect(body.org_id).toBe(1);
115
- expect(body.description).toBe("Test description");
116
- expect(body.project_id).toBe(123);
117
- expect(body.labels).toEqual(["bug", "urgent"]);
118
-
119
- expect(result).toEqual(mockResponse);
120
- });
121
-
122
- test("handles API error response", async () => {
123
- globalThis.fetch = mock(() =>
124
- Promise.resolve(
125
- new Response('{"message": "Unauthorized"}', {
126
- status: 401,
127
- headers: { "Content-Type": "application/json" },
128
- })
129
- )
130
- ) as unknown as typeof fetch;
131
-
132
- await expect(
133
- createIssue({
134
- apiKey: "invalid-key",
135
- apiBaseUrl: "https://api.example.com",
136
- title: "Test Issue",
137
- orgId: 1,
138
- })
139
- ).rejects.toThrow(/Failed to create issue/);
140
- });
141
- });
142
-
143
- describe("updateIssue", () => {
144
- afterEach(() => {
145
- globalThis.fetch = originalFetch;
146
- });
147
-
148
- test("throws when apiKey is missing", async () => {
149
- await expect(
150
- updateIssue({
151
- apiKey: "",
152
- apiBaseUrl: "https://api.example.com",
153
- issueId: "test-id",
154
- title: "Updated Title",
155
- })
156
- ).rejects.toThrow("API key is required");
157
- });
158
-
159
- test("throws when issueId is missing", async () => {
160
- await expect(
161
- updateIssue({
162
- apiKey: "test-key",
163
- apiBaseUrl: "https://api.example.com",
164
- issueId: "",
165
- title: "Updated Title",
166
- })
167
- ).rejects.toThrow("issueId is required");
168
- });
169
-
170
- test("throws when no update fields are provided", async () => {
171
- await expect(
172
- updateIssue({
173
- apiKey: "test-key",
174
- apiBaseUrl: "https://api.example.com",
175
- issueId: "test-id",
176
- })
177
- ).rejects.toThrow("At least one field to update is required");
178
- });
179
-
180
- test("accepts update with only title", async () => {
181
- const mockResponse = {
182
- id: "test-id",
183
- title: "Updated Title",
184
- description: null,
185
- status: 0,
186
- updated_at: "2025-01-01T00:00:00Z",
187
- labels: null,
188
- };
189
-
190
- globalThis.fetch = mock(() =>
191
- Promise.resolve(
192
- new Response(JSON.stringify(mockResponse), {
193
- status: 200,
194
- headers: { "Content-Type": "application/json" },
195
- })
196
- )
197
- ) as unknown as typeof fetch;
198
-
199
- const result = await updateIssue({
200
- apiKey: "test-key",
201
- apiBaseUrl: "https://api.example.com",
202
- issueId: "test-id",
203
- title: "Updated Title",
204
- });
205
-
206
- expect(result.title).toBe("Updated Title");
207
- });
208
-
209
- test("accepts update with only description", async () => {
210
- const mockResponse = {
211
- id: "test-id",
212
- title: "Original Title",
213
- description: "New description",
214
- status: 0,
215
- updated_at: "2025-01-01T00:00:00Z",
216
- labels: null,
217
- };
218
-
219
- globalThis.fetch = mock(() =>
220
- Promise.resolve(
221
- new Response(JSON.stringify(mockResponse), {
222
- status: 200,
223
- headers: { "Content-Type": "application/json" },
224
- })
225
- )
226
- ) as unknown as typeof fetch;
227
-
228
- const result = await updateIssue({
229
- apiKey: "test-key",
230
- apiBaseUrl: "https://api.example.com",
231
- issueId: "test-id",
232
- description: "New description",
233
- });
234
-
235
- expect(result.description).toBe("New description");
236
- });
237
-
238
- test("accepts update with only status", async () => {
239
- const mockResponse = {
240
- id: "test-id",
241
- title: "Title",
242
- description: null,
243
- status: 1,
244
- updated_at: "2025-01-01T00:00:00Z",
245
- labels: null,
246
- };
247
-
248
- globalThis.fetch = mock(() =>
249
- Promise.resolve(
250
- new Response(JSON.stringify(mockResponse), {
251
- status: 200,
252
- headers: { "Content-Type": "application/json" },
253
- })
254
- )
255
- ) as unknown as typeof fetch;
256
-
257
- const result = await updateIssue({
258
- apiKey: "test-key",
259
- apiBaseUrl: "https://api.example.com",
260
- issueId: "test-id",
261
- status: 1,
262
- });
263
-
264
- expect(result.status).toBe(1);
265
- });
266
-
267
- test("accepts update with only labels", async () => {
268
- const mockResponse = {
269
- id: "test-id",
270
- title: "Title",
271
- description: null,
272
- status: 0,
273
- updated_at: "2025-01-01T00:00:00Z",
274
- labels: ["new-label"],
275
- };
276
-
277
- globalThis.fetch = mock(() =>
278
- Promise.resolve(
279
- new Response(JSON.stringify(mockResponse), {
280
- status: 200,
281
- headers: { "Content-Type": "application/json" },
282
- })
283
- )
284
- ) as unknown as typeof fetch;
285
-
286
- const result = await updateIssue({
287
- apiKey: "test-key",
288
- apiBaseUrl: "https://api.example.com",
289
- issueId: "test-id",
290
- labels: ["new-label"],
291
- });
292
-
293
- expect(result.labels).toEqual(["new-label"]);
294
- });
295
-
296
- test("makes correct API call with all parameters", async () => {
297
- const mockResponse = {
298
- id: "test-id",
299
- title: "Updated Title",
300
- description: "Updated description",
301
- status: 1,
302
- updated_at: "2025-01-01T00:00:00Z",
303
- labels: ["bug"],
304
- };
305
-
306
- let capturedRequest: { url: string; options: RequestInit } | null = null;
307
-
308
- globalThis.fetch = mock((url: string, options: RequestInit) => {
309
- capturedRequest = { url, options };
310
- return Promise.resolve(
311
- new Response(JSON.stringify(mockResponse), {
312
- status: 200,
313
- headers: { "Content-Type": "application/json" },
314
- })
315
- );
316
- }) as unknown as typeof fetch;
317
-
318
- await updateIssue({
319
- apiKey: "test-key",
320
- apiBaseUrl: "https://api.example.com",
321
- issueId: "test-id",
322
- title: "Updated Title",
323
- description: "Updated description",
324
- status: 1,
325
- labels: ["bug"],
326
- });
327
-
328
- expect(capturedRequest).not.toBeNull();
329
- expect(capturedRequest!.url).toBe("https://api.example.com/rpc/issue_update");
330
- expect(capturedRequest!.options.method).toBe("POST");
331
-
332
- const body = JSON.parse(capturedRequest!.options.body as string);
333
- expect(body.p_id).toBe("test-id");
334
- expect(body.p_title).toBe("Updated Title");
335
- expect(body.p_description).toBe("Updated description");
336
- expect(body.p_status).toBe(1);
337
- expect(body.p_labels).toEqual(["bug"]);
338
- });
339
-
340
- test("handles API error response", async () => {
341
- globalThis.fetch = mock(() =>
342
- Promise.resolve(
343
- new Response('{"message": "Not found"}', {
344
- status: 404,
345
- headers: { "Content-Type": "application/json" },
346
- })
347
- )
348
- ) as unknown as typeof fetch;
349
-
350
- await expect(
351
- updateIssue({
352
- apiKey: "test-key",
353
- apiBaseUrl: "https://api.example.com",
354
- issueId: "nonexistent-id",
355
- title: "Updated Title",
356
- })
357
- ).rejects.toThrow(/Failed to update issue/);
358
- });
359
- });
360
-
361
- describe("updateIssueComment", () => {
362
- afterEach(() => {
363
- globalThis.fetch = originalFetch;
364
- });
365
-
366
- test("throws when apiKey is missing", async () => {
367
- await expect(
368
- updateIssueComment({
369
- apiKey: "",
370
- apiBaseUrl: "https://api.example.com",
371
- commentId: "test-id",
372
- content: "Updated content",
373
- })
374
- ).rejects.toThrow("API key is required");
375
- });
376
-
377
- test("throws when commentId is missing", async () => {
378
- await expect(
379
- updateIssueComment({
380
- apiKey: "test-key",
381
- apiBaseUrl: "https://api.example.com",
382
- commentId: "",
383
- content: "Updated content",
384
- })
385
- ).rejects.toThrow("commentId is required");
386
- });
387
-
388
- test("throws when content is missing", async () => {
389
- await expect(
390
- updateIssueComment({
391
- apiKey: "test-key",
392
- apiBaseUrl: "https://api.example.com",
393
- commentId: "test-id",
394
- content: "",
395
- })
396
- ).rejects.toThrow("content is required");
397
- });
398
-
399
- test("makes correct API call", async () => {
400
- const mockResponse = {
401
- id: "test-id",
402
- issue_id: "issue-id",
403
- content: "Updated content",
404
- updated_at: "2025-01-01T00:00:00Z",
405
- };
406
-
407
- let capturedRequest: { url: string; options: RequestInit } | null = null;
408
-
409
- globalThis.fetch = mock((url: string, options: RequestInit) => {
410
- capturedRequest = { url, options };
411
- return Promise.resolve(
412
- new Response(JSON.stringify(mockResponse), {
413
- status: 200,
414
- headers: { "Content-Type": "application/json" },
415
- })
416
- );
417
- }) as unknown as typeof fetch;
418
-
419
- const result = await updateIssueComment({
420
- apiKey: "test-key",
421
- apiBaseUrl: "https://api.example.com",
422
- commentId: "test-id",
423
- content: "Updated content",
424
- });
425
-
426
- expect(capturedRequest).not.toBeNull();
427
- expect(capturedRequest!.url).toBe("https://api.example.com/rpc/issue_comment_update");
428
- expect(capturedRequest!.options.method).toBe("POST");
429
-
430
- const body = JSON.parse(capturedRequest!.options.body as string);
431
- expect(body.p_id).toBe("test-id");
432
- expect(body.p_content).toBe("Updated content");
433
-
434
- expect(result).toEqual(mockResponse);
435
- });
436
-
437
- test("handles API error response", async () => {
438
- globalThis.fetch = mock(() =>
439
- Promise.resolve(
440
- new Response('{"message": "Not found"}', {
441
- status: 404,
442
- headers: { "Content-Type": "application/json" },
443
- })
444
- )
445
- ) as unknown as typeof fetch;
446
-
447
- await expect(
448
- updateIssueComment({
449
- apiKey: "test-key",
450
- apiBaseUrl: "https://api.example.com",
451
- commentId: "nonexistent-id",
452
- content: "Updated content",
453
- })
454
- ).rejects.toThrow(/Failed to update issue comment/);
455
- });
456
- });