pgbeam 0.4.20 → 0.5.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.
@@ -122,6 +122,26 @@
122
122
  replayPolicy: {
123
123
  method: "POST",
124
124
  path: "/v1/projects/{project_id}/policy-replays"
125
+ },
126
+ listQueryTemplates: {
127
+ method: "GET",
128
+ path: "/v1/projects/{project_id}/query-templates"
129
+ },
130
+ createQueryTemplate: {
131
+ method: "POST",
132
+ path: "/v1/projects/{project_id}/query-templates"
133
+ },
134
+ getQueryTemplate: {
135
+ method: "GET",
136
+ path: "/v1/projects/{project_id}/query-templates/{query_template_id}"
137
+ },
138
+ updateQueryTemplate: {
139
+ method: "PUT",
140
+ path: "/v1/projects/{project_id}/query-templates/{query_template_id}"
141
+ },
142
+ deleteQueryTemplate: {
143
+ method: "DELETE",
144
+ path: "/v1/projects/{project_id}/query-templates/{query_template_id}"
125
145
  }
126
146
  },
127
147
  anomalies: {
@@ -155,6 +175,26 @@
155
175
  }
156
176
  },
157
177
  approvals: {
178
+ listApprovalRules: {
179
+ method: "GET",
180
+ path: "/v1/projects/{project_id}/approval-rules"
181
+ },
182
+ createApprovalRule: {
183
+ method: "POST",
184
+ path: "/v1/projects/{project_id}/approval-rules"
185
+ },
186
+ getApprovalRule: {
187
+ method: "GET",
188
+ path: "/v1/projects/{project_id}/approval-rules/{approval_rule_id}"
189
+ },
190
+ updateApprovalRule: {
191
+ method: "PUT",
192
+ path: "/v1/projects/{project_id}/approval-rules/{approval_rule_id}"
193
+ },
194
+ deleteApprovalRule: {
195
+ method: "DELETE",
196
+ path: "/v1/projects/{project_id}/approval-rules/{approval_rule_id}"
197
+ },
158
198
  listApprovalRequests: {
159
199
  method: "GET",
160
200
  path: "/v1/projects/{project_id}/approvals"
@@ -355,7 +395,8 @@
355
395
  },
356
396
  scanText: {
357
397
  method: "POST",
358
- path: "/v1/scan/text"
398
+ path: "/v1/scan/text",
399
+ refusesIdempotencyKey: true
359
400
  }
360
401
  },
361
402
  honeytokens: {
@@ -432,12 +473,6 @@
432
473
  path: "/v1/organizations/{org_id}/support/cases/{case_id}/messages"
433
474
  }
434
475
  },
435
- internal: {
436
- handleSlackSupportEvent: {
437
- method: "POST",
438
- path: "/v1/internal/support/slack-event"
439
- }
440
- },
441
476
  webhooks: {
442
477
  listWebhookEndpoints: {
443
478
  method: "GET",
@@ -541,6 +576,31 @@ const operationsByPath = {
541
576
  path: "/v1/projects/{project_id}/anomaly-rules/{anomaly_rule_id}",
542
577
  operationId: "deleteAnomalyRule"
543
578
  },
579
+ "GET /v1/projects/{project_id}/approval-rules": {
580
+ method: "GET",
581
+ path: "/v1/projects/{project_id}/approval-rules",
582
+ operationId: "listApprovalRules"
583
+ },
584
+ "POST /v1/projects/{project_id}/approval-rules": {
585
+ method: "POST",
586
+ path: "/v1/projects/{project_id}/approval-rules",
587
+ operationId: "createApprovalRule"
588
+ },
589
+ "GET /v1/projects/{project_id}/approval-rules/{approval_rule_id}": {
590
+ method: "GET",
591
+ path: "/v1/projects/{project_id}/approval-rules/{approval_rule_id}",
592
+ operationId: "getApprovalRule"
593
+ },
594
+ "PUT /v1/projects/{project_id}/approval-rules/{approval_rule_id}": {
595
+ method: "PUT",
596
+ path: "/v1/projects/{project_id}/approval-rules/{approval_rule_id}",
597
+ operationId: "updateApprovalRule"
598
+ },
599
+ "DELETE /v1/projects/{project_id}/approval-rules/{approval_rule_id}": {
600
+ method: "DELETE",
601
+ path: "/v1/projects/{project_id}/approval-rules/{approval_rule_id}",
602
+ operationId: "deleteApprovalRule"
603
+ },
544
604
  "GET /v1/projects/{project_id}/approvals": {
545
605
  method: "GET",
546
606
  path: "/v1/projects/{project_id}/approvals",
@@ -861,6 +921,31 @@ const operationsByPath = {
861
921
  path: "/v1/projects/{project_id}/metrics",
862
922
  operationId: "getProjectMetrics"
863
923
  },
924
+ "GET /v1/projects/{project_id}/query-templates": {
925
+ method: "GET",
926
+ path: "/v1/projects/{project_id}/query-templates",
927
+ operationId: "listQueryTemplates"
928
+ },
929
+ "POST /v1/projects/{project_id}/query-templates": {
930
+ method: "POST",
931
+ path: "/v1/projects/{project_id}/query-templates",
932
+ operationId: "createQueryTemplate"
933
+ },
934
+ "GET /v1/projects/{project_id}/query-templates/{query_template_id}": {
935
+ method: "GET",
936
+ path: "/v1/projects/{project_id}/query-templates/{query_template_id}",
937
+ operationId: "getQueryTemplate"
938
+ },
939
+ "PUT /v1/projects/{project_id}/query-templates/{query_template_id}": {
940
+ method: "PUT",
941
+ path: "/v1/projects/{project_id}/query-templates/{query_template_id}",
942
+ operationId: "updateQueryTemplate"
943
+ },
944
+ "DELETE /v1/projects/{project_id}/query-templates/{query_template_id}": {
945
+ method: "DELETE",
946
+ path: "/v1/projects/{project_id}/query-templates/{query_template_id}",
947
+ operationId: "deleteQueryTemplate"
948
+ },
864
949
  "GET /v1/regions": {
865
950
  method: "GET",
866
951
  path: "/v1/regions",
@@ -941,15 +1026,11 @@ const operationsByPath = {
941
1026
  path: "/v1/organizations/{org_id}/support/cases/{case_id}/messages",
942
1027
  operationId: "createSupportMessage"
943
1028
  },
944
- "POST /v1/internal/support/slack-event": {
945
- method: "POST",
946
- path: "/v1/internal/support/slack-event",
947
- operationId: "handleSlackSupportEvent"
948
- },
949
1029
  "POST /v1/scan/text": {
950
1030
  method: "POST",
951
1031
  path: "/v1/scan/text",
952
- operationId: "scanText"
1032
+ operationId: "scanText",
1033
+ refusesIdempotencyKey: true
953
1034
  },
954
1035
  "GET /v1/organizations/{org_id}/usage": {
955
1036
  method: "GET",
@@ -1,6 +1,6 @@
1
1
  Object.defineProperty(exports, '__esModule', { value: true });
2
2
 
3
- var operationsMap_gen = require('./operations-map.gen-j3jalb8e.cjs');
3
+ var operationsMap_gen = require('./operations-map.gen-fayr6b1o.cjs');
4
4
 
5
5
  /**
6
6
  * Generated by generate-sdk-ts-maps.ts from backend/openapi/bundles/public.yaml — do not edit manually.
@@ -251,7 +251,7 @@ var operationsMap_gen = require('./operations-map.gen-j3jalb8e.cjs');
251
251
  ],
252
252
  "requestBodyType": "{ limit?: number; lookback_days?: number }",
253
253
  "requestBodyRequired": false,
254
- "responseType": "{ candidate?: { access_mode?: \"read_only\" | \"read_write\"; approval_auto_max_rows?: number; approval_mode?: \"off\" | \"writes\" | \"ddl\" | \"all\"; approval_timeout_seconds?: number; budget_queries_per_day?: number; budget_queries_per_hour?: number; content_scan_max_bytes?: number; content_scan_mode?: \"off\" | \"annotate\" | \"block\"; egress_bytes_per_day?: number; masking_rules?: ({ column: string; kind: \"redact\" | \"null\" | \"hash\"; table: string })[]; max_affected_rows?: number; max_rows?: number; migration_safety?: \"off\" | \"warn\" | \"block\"; name: string; row_filters?: ({ predicate: string; table: string })[]; statement_rules?: { allow?: string[]; deny?: string[] }; statement_timeout_ms?: number; table_allowlist?: string[]; table_denylist?: string[]; write_mode?: \"normal\" | \"rollback\" | \"sandbox\" }; message?: string; notes?: string[]; observed_entries: number; observed_queries: number; replay?: { items: ({ change: \"newly_blocked\" | \"newly_allowed\" | \"still_allowed\" | \"still_blocked\"; first_seen: string; last_seen: string; occurrences: number; query_hash: string; recorded_event: string; recorded_rule?: string; result: { hint?: string; masked_columns?: ({ column: string; kind: \"redact\" | \"null\" | \"hash\" })[]; notes?: string[]; reason: string; rewritten_sql?: string; row_filter_predicate?: string; rule: string; verdict: \"allow\" | \"block\" | \"mask\" | \"row-filter\" }; sql: string; statement_kind?: string })[]; summary: { bound_credentials?: number; distinct_queries: number; entries_scanned: number; evaluated: number; newly_allowed: number; newly_blocked: number; skipped_unparseable: number; traffic_scope: \"project\" | \"bound_credentials\"; truncated: boolean; would_allow: number; would_block: number; would_mask: number; would_row_filter: number } }; sufficient_history: boolean; window_end: string; window_start: string }",
254
+ "responseType": "{ candidate?: { access_mode?: \"read_only\" | \"read_write\"; approval_auto_max_rows?: number; approval_mode?: \"off\" | \"writes\" | \"ddl\" | \"all\"; approval_timeout_seconds?: number; budget_queries_per_day?: number; budget_queries_per_hour?: number; content_scan_max_bytes?: number; content_scan_mode?: \"off\" | \"annotate\" | \"block\"; egress_bytes_per_day?: number; masking_rules?: ({ column: string; kind: \"redact\" | \"null\" | \"hash\"; table: string })[]; max_affected_rows?: number; max_rows?: number; migration_safety?: \"off\" | \"warn\" | \"block\"; name: string; row_filters?: ({ predicate: string; table: string })[]; statement_rules?: { allow?: string[]; deny?: string[] }; statement_timeout_ms?: number; table_allowlist?: string[]; table_denylist?: string[]; write_mode?: \"normal\" | \"rollback\" | \"sandbox\" }; message?: string; notes?: string[]; observed_entries: number; observed_queries: number; replay?: { items: ({ change: \"newly_blocked\" | \"newly_allowed\" | \"still_allowed\" | \"still_blocked\"; first_seen: string; last_seen: string; occurrences: number; query_hash: string; recorded_event: string; recorded_rule?: string; result: { hint?: string; masked_columns?: ({ column: string; kind: \"redact\" | \"null\" | \"hash\" })[]; notes?: string[]; reason: string; rewritten_sql?: string; row_filter_predicate?: string; rule: string; template?: string; verdict: \"allow\" | \"block\" | \"mask\" | \"row-filter\" }; sql: string; statement_kind?: string })[]; summary: { bound_credentials?: number; distinct_queries: number; entries_scanned: number; evaluated: number; newly_allowed: number; newly_blocked: number; skipped_unparseable: number; traffic_scope: \"project\" | \"bound_credentials\"; truncated: boolean; would_allow: number; would_block: number; would_mask: number; would_row_filter: number } }; sufficient_history: boolean; window_end: string; window_start: string }",
255
255
  "responseStatus": "200"
256
256
  },
257
257
  "listAnomalyAlerts": {
@@ -499,6 +499,169 @@ var operationsMap_gen = require('./operations-map.gen-j3jalb8e.cjs');
499
499
  "responseType": "",
500
500
  "responseStatus": "204"
501
501
  },
502
+ "listApprovalRules": {
503
+ "operationId": "listApprovalRules",
504
+ "method": "GET",
505
+ "path": "/v1/projects/{project_id}/approval-rules",
506
+ "summary": "List approval rules",
507
+ "description": "Lists the project's approval rules, including disabled ones.",
508
+ "parameters": [
509
+ {
510
+ "name": "project_id",
511
+ "in": "path",
512
+ "required": true,
513
+ "type": "string",
514
+ "description": "Unique project identifier (prefixed, e.g. prj_xxx)."
515
+ },
516
+ {
517
+ "name": "page_size",
518
+ "in": "query",
519
+ "required": false,
520
+ "type": "number",
521
+ "description": "Maximum number of items to return (1-100, default 20)."
522
+ },
523
+ {
524
+ "name": "page_token",
525
+ "in": "query",
526
+ "required": false,
527
+ "type": "string",
528
+ "description": "Opaque token for cursor-based pagination."
529
+ },
530
+ {
531
+ "name": "If-None-Match",
532
+ "in": "header",
533
+ "required": false,
534
+ "type": "string",
535
+ "description": "Entity tag the client already holds, taken from the `ETag` of an earlier response. When it still matches the current representation the server answers `304 Not Modified` with no body, so a poll that finds nothing changed costs a round trip rather than a transfer.\n\nA comma-separated list is accepted, and `*` matches any current representation."
536
+ }
537
+ ],
538
+ "requestBodyType": "",
539
+ "requestBodyRequired": false,
540
+ "responseType": "{ approval_rules: ({ created_at: string; enabled: boolean; id: string; min_affected_rows?: number; name: string; project_id: string; relation_name?: string; schema_name?: string; statement_kinds: (\"insert\" | \"update\" | \"delete\" | \"ddl\")[]; updated_at: string })[]; next_page_token?: string }",
541
+ "responseStatus": "200"
542
+ },
543
+ "createApprovalRule": {
544
+ "operationId": "createApprovalRule",
545
+ "method": "POST",
546
+ "path": "/v1/projects/{project_id}/approval-rules",
547
+ "summary": "Create an approval rule",
548
+ "description": "Sends the agent statements the rule matches to a human for approval,\nwhatever the policy profile's approval_mode says. A rule can only add\napproval; nothing here can exempt a statement from approval_mode.\n\nThe rule is pushed to connected data planes when it is written. A\nreviewer sees its name on every approval request it holds.\n\nReturns 409 for an enabled rule while the organization has a live\nself-hosted data plane enrollment, because PgBeam cannot yet confirm\nthat a self-hosted proxy runs a build that enforces approval rules. A\nrule with enabled set to false is still accepted.\n",
549
+ "parameters": [
550
+ {
551
+ "name": "project_id",
552
+ "in": "path",
553
+ "required": true,
554
+ "type": "string",
555
+ "description": "Unique project identifier (prefixed, e.g. prj_xxx)."
556
+ },
557
+ {
558
+ "name": "Idempotency-Key",
559
+ "in": "header",
560
+ "required": false,
561
+ "type": "string",
562
+ "description": "Client-generated key that makes a retry of this request safe. The first request carrying a given key executes normally and its response (status, content type and body) is stored for 24 hours; a later request with the same key returns that stored response without running the operation again, so a retry after a lost or timed-out response cannot create a second resource.\n\nReusing a key with a different request body returns `409 Conflict`: a key is a promise about one specific request, so a changed body is a client bug rather than a retry. Keys are scoped to the calling organization (or to the user, for account-scoped tokens), so one tenant can never read another's stored response.\n\nA `5xx`, `408` or `429` is never stored, because those describe a request that produced no settled answer and the next attempt with the same key must run for real. A `4xx` is stored: it is the server's settled answer about this exact request.\n\nUse a fresh UUID per logical operation. The PgBeam SDKs generate one per call and reuse it across their own automatic retries."
563
+ }
564
+ ],
565
+ "requestBodyType": "{ enabled?: boolean; min_affected_rows?: number; name: string; relation_name?: string; schema_name?: string; statement_kinds?: (\"insert\" | \"update\" | \"delete\" | \"ddl\")[] }",
566
+ "requestBodyRequired": true,
567
+ "responseType": "{ created_at: string; enabled: boolean; id: string; min_affected_rows?: number; name: string; project_id: string; relation_name?: string; schema_name?: string; statement_kinds: (\"insert\" | \"update\" | \"delete\" | \"ddl\")[]; updated_at: string }",
568
+ "responseStatus": "201"
569
+ },
570
+ "getApprovalRule": {
571
+ "operationId": "getApprovalRule",
572
+ "method": "GET",
573
+ "path": "/v1/projects/{project_id}/approval-rules/{approval_rule_id}",
574
+ "summary": "Get an approval rule",
575
+ "description": "Returns a single approval rule by ID.",
576
+ "parameters": [
577
+ {
578
+ "name": "project_id",
579
+ "in": "path",
580
+ "required": true,
581
+ "type": "string",
582
+ "description": "Unique project identifier (prefixed, e.g. prj_xxx)."
583
+ },
584
+ {
585
+ "name": "approval_rule_id",
586
+ "in": "path",
587
+ "required": true,
588
+ "type": "string",
589
+ "description": "Unique approval rule identifier (prefixed, e.g. apl_xxx)."
590
+ },
591
+ {
592
+ "name": "If-None-Match",
593
+ "in": "header",
594
+ "required": false,
595
+ "type": "string",
596
+ "description": "Entity tag the client already holds, taken from the `ETag` of an earlier response. When it still matches the current representation the server answers `304 Not Modified` with no body, so a poll that finds nothing changed costs a round trip rather than a transfer.\n\nA comma-separated list is accepted, and `*` matches any current representation."
597
+ }
598
+ ],
599
+ "requestBodyType": "",
600
+ "requestBodyRequired": false,
601
+ "responseType": "{ created_at: string; enabled: boolean; id: string; min_affected_rows?: number; name: string; project_id: string; relation_name?: string; schema_name?: string; statement_kinds: (\"insert\" | \"update\" | \"delete\" | \"ddl\")[]; updated_at: string }",
602
+ "responseStatus": "200"
603
+ },
604
+ "updateApprovalRule": {
605
+ "operationId": "updateApprovalRule",
606
+ "method": "PUT",
607
+ "path": "/v1/projects/{project_id}/approval-rules/{approval_rule_id}",
608
+ "summary": "Update an approval rule",
609
+ "description": "Replaces the rule's name, statement kinds, scope, row threshold and\nenabled flag. An approval request already held keeps the name it was\nheld under.\n\nReturns 409 when the update leaves the rule enabled while the\norganization has a live self-hosted data plane enrollment, for the same\nreason as create. Setting enabled to false is still accepted.\n",
610
+ "parameters": [
611
+ {
612
+ "name": "project_id",
613
+ "in": "path",
614
+ "required": true,
615
+ "type": "string",
616
+ "description": "Unique project identifier (prefixed, e.g. prj_xxx)."
617
+ },
618
+ {
619
+ "name": "approval_rule_id",
620
+ "in": "path",
621
+ "required": true,
622
+ "type": "string",
623
+ "description": "Unique approval rule identifier (prefixed, e.g. apl_xxx)."
624
+ },
625
+ {
626
+ "name": "If-Match",
627
+ "in": "header",
628
+ "required": false,
629
+ "type": "string",
630
+ "description": "Entity tag the write is based on, taken from the `ETag` of the read that produced the values being sent. The write proceeds only if it still matches the current representation; otherwise it is refused with `412 Precondition Failed` and nothing is changed.\n\nThis is what makes a read-modify-write safe. Without it the last writer wins and a concurrent edit is silently discarded, which is the failure an agent is most likely to cause and least likely to notice. The `412` response carries the current `ETag`, so a caller can re-read, re-apply its change and retry.\n\nOmitting the header keeps the old unconditional behaviour. `*` matches any current representation, which asserts only that the resource exists."
631
+ }
632
+ ],
633
+ "requestBodyType": "{ enabled?: boolean; min_affected_rows?: number; name: string; relation_name?: string; schema_name?: string; statement_kinds?: (\"insert\" | \"update\" | \"delete\" | \"ddl\")[] }",
634
+ "requestBodyRequired": true,
635
+ "responseType": "{ created_at: string; enabled: boolean; id: string; min_affected_rows?: number; name: string; project_id: string; relation_name?: string; schema_name?: string; statement_kinds: (\"insert\" | \"update\" | \"delete\" | \"ddl\")[]; updated_at: string }",
636
+ "responseStatus": "200"
637
+ },
638
+ "deleteApprovalRule": {
639
+ "operationId": "deleteApprovalRule",
640
+ "method": "DELETE",
641
+ "path": "/v1/projects/{project_id}/approval-rules/{approval_rule_id}",
642
+ "summary": "Delete an approval rule",
643
+ "description": "Removes the rule, so the statements it matched are held only if the\npolicy profile's approval_mode holds them. Approval requests it already\nheld are not affected.\n",
644
+ "parameters": [
645
+ {
646
+ "name": "project_id",
647
+ "in": "path",
648
+ "required": true,
649
+ "type": "string",
650
+ "description": "Unique project identifier (prefixed, e.g. prj_xxx)."
651
+ },
652
+ {
653
+ "name": "approval_rule_id",
654
+ "in": "path",
655
+ "required": true,
656
+ "type": "string",
657
+ "description": "Unique approval rule identifier (prefixed, e.g. apl_xxx)."
658
+ }
659
+ ],
660
+ "requestBodyType": "",
661
+ "requestBodyRequired": false,
662
+ "responseType": "",
663
+ "responseStatus": "204"
664
+ },
502
665
  "listApprovalRequests": {
503
666
  "operationId": "listApprovalRequests",
504
667
  "method": "GET",
@@ -2270,7 +2433,7 @@ var operationsMap_gen = require('./operations-map.gen-j3jalb8e.cjs');
2270
2433
  ],
2271
2434
  "requestBodyType": "{ policy?: { access_mode?: \"read_only\" | \"read_write\"; approval_auto_max_rows?: number; approval_mode?: \"off\" | \"writes\" | \"ddl\" | \"all\"; approval_timeout_seconds?: number; budget_queries_per_day?: number; budget_queries_per_hour?: number; content_scan_max_bytes?: number; content_scan_mode?: \"off\" | \"annotate\" | \"block\"; egress_bytes_per_day?: number; masking_rules?: ({ column: string; kind: \"redact\" | \"null\" | \"hash\"; table: string })[]; max_affected_rows?: number; max_rows?: number; migration_safety?: \"off\" | \"warn\" | \"block\"; name: string; row_filters?: ({ predicate: string; table: string })[]; statement_rules?: { allow?: string[]; deny?: string[] }; statement_timeout_ms?: number; table_allowlist?: string[]; table_denylist?: string[]; write_mode?: \"normal\" | \"rollback\" | \"sandbox\" }; policy_id?: string; sql: string }",
2272
2435
  "requestBodyRequired": true,
2273
- "responseType": "{ hint?: string; masked_columns?: ({ column: string; kind: \"redact\" | \"null\" | \"hash\" })[]; notes?: string[]; reason: string; rewritten_sql?: string; row_filter_predicate?: string; rule: string; verdict: \"allow\" | \"block\" | \"mask\" | \"row-filter\" }",
2436
+ "responseType": "{ hint?: string; masked_columns?: ({ column: string; kind: \"redact\" | \"null\" | \"hash\" })[]; notes?: string[]; reason: string; rewritten_sql?: string; row_filter_predicate?: string; rule: string; template?: string; verdict: \"allow\" | \"block\" | \"mask\" | \"row-filter\" }",
2274
2437
  "responseStatus": "200"
2275
2438
  },
2276
2439
  "replayPolicy": {
@@ -2290,7 +2453,7 @@ var operationsMap_gen = require('./operations-map.gen-j3jalb8e.cjs');
2290
2453
  ],
2291
2454
  "requestBodyType": "{ bound_policy_id?: string; credential_id?: string; end_ts?: string; limit?: number; policy?: { access_mode?: \"read_only\" | \"read_write\"; approval_auto_max_rows?: number; approval_mode?: \"off\" | \"writes\" | \"ddl\" | \"all\"; approval_timeout_seconds?: number; budget_queries_per_day?: number; budget_queries_per_hour?: number; content_scan_max_bytes?: number; content_scan_mode?: \"off\" | \"annotate\" | \"block\"; egress_bytes_per_day?: number; masking_rules?: ({ column: string; kind: \"redact\" | \"null\" | \"hash\"; table: string })[]; max_affected_rows?: number; max_rows?: number; migration_safety?: \"off\" | \"warn\" | \"block\"; name: string; row_filters?: ({ predicate: string; table: string })[]; statement_rules?: { allow?: string[]; deny?: string[] }; statement_timeout_ms?: number; table_allowlist?: string[]; table_denylist?: string[]; write_mode?: \"normal\" | \"rollback\" | \"sandbox\" }; policy_id?: string; start_ts?: string }",
2292
2455
  "requestBodyRequired": true,
2293
- "responseType": "{ items: ({ change: \"newly_blocked\" | \"newly_allowed\" | \"still_allowed\" | \"still_blocked\"; first_seen: string; last_seen: string; occurrences: number; query_hash: string; recorded_event: string; recorded_rule?: string; result: { hint?: string; masked_columns?: ({ column: string; kind: \"redact\" | \"null\" | \"hash\" })[]; notes?: string[]; reason: string; rewritten_sql?: string; row_filter_predicate?: string; rule: string; verdict: \"allow\" | \"block\" | \"mask\" | \"row-filter\" }; sql: string; statement_kind?: string })[]; summary: { bound_credentials?: number; distinct_queries: number; entries_scanned: number; evaluated: number; newly_allowed: number; newly_blocked: number; skipped_unparseable: number; traffic_scope: \"project\" | \"bound_credentials\"; truncated: boolean; would_allow: number; would_block: number; would_mask: number; would_row_filter: number } }",
2456
+ "responseType": "{ items: ({ change: \"newly_blocked\" | \"newly_allowed\" | \"still_allowed\" | \"still_blocked\"; first_seen: string; last_seen: string; occurrences: number; query_hash: string; recorded_event: string; recorded_rule?: string; result: { hint?: string; masked_columns?: ({ column: string; kind: \"redact\" | \"null\" | \"hash\" })[]; notes?: string[]; reason: string; rewritten_sql?: string; row_filter_predicate?: string; rule: string; template?: string; verdict: \"allow\" | \"block\" | \"mask\" | \"row-filter\" }; sql: string; statement_kind?: string })[]; summary: { bound_credentials?: number; distinct_queries: number; entries_scanned: number; evaluated: number; newly_allowed: number; newly_blocked: number; skipped_unparseable: number; traffic_scope: \"project\" | \"bound_credentials\"; truncated: boolean; would_allow: number; would_block: number; would_mask: number; would_row_filter: number } }",
2294
2457
  "responseStatus": "200"
2295
2458
  },
2296
2459
  "listProjects": {
@@ -2476,6 +2639,169 @@ var operationsMap_gen = require('./operations-map.gen-j3jalb8e.cjs');
2476
2639
  "responseType": "{ snapshots: ({ active_connections: number; avg_connect_ms?: number; avg_latency_ms: number; avg_query_ms?: number; cache_hits: number; cache_misses: number; created_at: string; id: string; p99_latency_ms: number; project_id: string; queries_total: number; region: string })[] }",
2477
2640
  "responseStatus": "200"
2478
2641
  },
2642
+ "listQueryTemplates": {
2643
+ "operationId": "listQueryTemplates",
2644
+ "method": "GET",
2645
+ "path": "/v1/projects/{project_id}/query-templates",
2646
+ "summary": "List query templates",
2647
+ "description": "Lists the project's query templates, including disabled ones.",
2648
+ "parameters": [
2649
+ {
2650
+ "name": "project_id",
2651
+ "in": "path",
2652
+ "required": true,
2653
+ "type": "string",
2654
+ "description": "Unique project identifier (prefixed, e.g. prj_xxx)."
2655
+ },
2656
+ {
2657
+ "name": "page_size",
2658
+ "in": "query",
2659
+ "required": false,
2660
+ "type": "number",
2661
+ "description": "Maximum number of items to return (1-100, default 20)."
2662
+ },
2663
+ {
2664
+ "name": "page_token",
2665
+ "in": "query",
2666
+ "required": false,
2667
+ "type": "string",
2668
+ "description": "Opaque token for cursor-based pagination."
2669
+ },
2670
+ {
2671
+ "name": "If-None-Match",
2672
+ "in": "header",
2673
+ "required": false,
2674
+ "type": "string",
2675
+ "description": "Entity tag the client already holds, taken from the `ETag` of an earlier response. When it still matches the current representation the server answers `304 Not Modified` with no body, so a poll that finds nothing changed costs a round trip rather than a transfer.\n\nA comma-separated list is accepted, and `*` matches any current representation."
2676
+ }
2677
+ ],
2678
+ "requestBodyType": "",
2679
+ "requestBodyRequired": false,
2680
+ "responseType": "{ next_page_token?: string; query_templates: ({ created_at: string; description: string; enabled: boolean; id: string; include_sql: boolean; name: string; params: ({ name: string; nullable?: boolean; type: \"text\" | \"integer\" | \"bigint\" | \"double precision\" | \"numeric\" | \"boolean\" | \"uuid\" | \"date\" | \"timestamptz\" | \"jsonb\" })[]; project_id: string; sql: string; statement_kind?: \"select\" | \"insert\" | \"update\" | \"delete\"; updated_at: string })[] }",
2681
+ "responseStatus": "200"
2682
+ },
2683
+ "createQueryTemplate": {
2684
+ "operationId": "createQueryTemplate",
2685
+ "method": "POST",
2686
+ "path": "/v1/projects/{project_id}/query-templates",
2687
+ "summary": "Create a query template",
2688
+ "description": "Adds a named, parameterized statement to the project. A template admits\na statement for a policy profile that runs templates only; it never\ngrants access, and the statement still meets the credential's whole\npolicy.\n\nThe SQL is parsed and checked when it is written: exactly one SELECT,\nINSERT, UPDATE or DELETE, placeholders $1 to $n, one declared parameter\nfor each. A template that fails is refused with 400 and a message\nnaming the problem. Returns 409 when the project already has a template\nof that name.\n\nThe template is pushed to connected data planes when it is written.\n\nReturns 409 for an enabled template while the organization has a live\nself-hosted data plane enrollment, because PgBeam cannot yet confirm\nthat a self-hosted proxy runs a build that enforces templates. A\ntemplate with enabled set to false is still accepted.\n",
2689
+ "parameters": [
2690
+ {
2691
+ "name": "project_id",
2692
+ "in": "path",
2693
+ "required": true,
2694
+ "type": "string",
2695
+ "description": "Unique project identifier (prefixed, e.g. prj_xxx)."
2696
+ },
2697
+ {
2698
+ "name": "Idempotency-Key",
2699
+ "in": "header",
2700
+ "required": false,
2701
+ "type": "string",
2702
+ "description": "Client-generated key that makes a retry of this request safe. The first request carrying a given key executes normally and its response (status, content type and body) is stored for 24 hours; a later request with the same key returns that stored response without running the operation again, so a retry after a lost or timed-out response cannot create a second resource.\n\nReusing a key with a different request body returns `409 Conflict`: a key is a promise about one specific request, so a changed body is a client bug rather than a retry. Keys are scoped to the calling organization (or to the user, for account-scoped tokens), so one tenant can never read another's stored response.\n\nA `5xx`, `408` or `429` is never stored, because those describe a request that produced no settled answer and the next attempt with the same key must run for real. A `4xx` is stored: it is the server's settled answer about this exact request.\n\nUse a fresh UUID per logical operation. The PgBeam SDKs generate one per call and reuse it across their own automatic retries."
2703
+ }
2704
+ ],
2705
+ "requestBodyType": "{ description?: string; enabled?: boolean; include_sql?: boolean; name: string; params?: ({ name: string; nullable?: boolean; type: \"text\" | \"integer\" | \"bigint\" | \"double precision\" | \"numeric\" | \"boolean\" | \"uuid\" | \"date\" | \"timestamptz\" | \"jsonb\" })[]; sql: string }",
2706
+ "requestBodyRequired": true,
2707
+ "responseType": "{ created_at: string; description: string; enabled: boolean; id: string; include_sql: boolean; name: string; params: ({ name: string; nullable?: boolean; type: \"text\" | \"integer\" | \"bigint\" | \"double precision\" | \"numeric\" | \"boolean\" | \"uuid\" | \"date\" | \"timestamptz\" | \"jsonb\" })[]; project_id: string; sql: string; statement_kind?: \"select\" | \"insert\" | \"update\" | \"delete\"; updated_at: string }",
2708
+ "responseStatus": "201"
2709
+ },
2710
+ "getQueryTemplate": {
2711
+ "operationId": "getQueryTemplate",
2712
+ "method": "GET",
2713
+ "path": "/v1/projects/{project_id}/query-templates/{query_template_id}",
2714
+ "summary": "Get a query template",
2715
+ "description": "Returns a single query template by ID.",
2716
+ "parameters": [
2717
+ {
2718
+ "name": "project_id",
2719
+ "in": "path",
2720
+ "required": true,
2721
+ "type": "string",
2722
+ "description": "Unique project identifier (prefixed, e.g. prj_xxx)."
2723
+ },
2724
+ {
2725
+ "name": "query_template_id",
2726
+ "in": "path",
2727
+ "required": true,
2728
+ "type": "string",
2729
+ "description": "Unique query template identifier (prefixed, e.g. qtp_xxx)."
2730
+ },
2731
+ {
2732
+ "name": "If-None-Match",
2733
+ "in": "header",
2734
+ "required": false,
2735
+ "type": "string",
2736
+ "description": "Entity tag the client already holds, taken from the `ETag` of an earlier response. When it still matches the current representation the server answers `304 Not Modified` with no body, so a poll that finds nothing changed costs a round trip rather than a transfer.\n\nA comma-separated list is accepted, and `*` matches any current representation."
2737
+ }
2738
+ ],
2739
+ "requestBodyType": "",
2740
+ "requestBodyRequired": false,
2741
+ "responseType": "{ created_at: string; description: string; enabled: boolean; id: string; include_sql: boolean; name: string; params: ({ name: string; nullable?: boolean; type: \"text\" | \"integer\" | \"bigint\" | \"double precision\" | \"numeric\" | \"boolean\" | \"uuid\" | \"date\" | \"timestamptz\" | \"jsonb\" })[]; project_id: string; sql: string; statement_kind?: \"select\" | \"insert\" | \"update\" | \"delete\"; updated_at: string }",
2742
+ "responseStatus": "200"
2743
+ },
2744
+ "updateQueryTemplate": {
2745
+ "operationId": "updateQueryTemplate",
2746
+ "method": "PUT",
2747
+ "path": "/v1/projects/{project_id}/query-templates/{query_template_id}",
2748
+ "summary": "Update a query template",
2749
+ "description": "Replaces the template's name, description, SQL, parameters, include_sql\nand enabled flag. The SQL is checked as on create. A statement already\nadmitted under the old template is not affected; the next one is\nmatched against the new text.\n\nReturns 409 on a rename to a name the project already uses, and when\nthe update leaves the template enabled while the organization has a\nlive self-hosted data plane enrollment, for the same reason as create.\nSetting enabled to false is still accepted.\n",
2750
+ "parameters": [
2751
+ {
2752
+ "name": "project_id",
2753
+ "in": "path",
2754
+ "required": true,
2755
+ "type": "string",
2756
+ "description": "Unique project identifier (prefixed, e.g. prj_xxx)."
2757
+ },
2758
+ {
2759
+ "name": "query_template_id",
2760
+ "in": "path",
2761
+ "required": true,
2762
+ "type": "string",
2763
+ "description": "Unique query template identifier (prefixed, e.g. qtp_xxx)."
2764
+ },
2765
+ {
2766
+ "name": "If-Match",
2767
+ "in": "header",
2768
+ "required": false,
2769
+ "type": "string",
2770
+ "description": "Entity tag the write is based on, taken from the `ETag` of the read that produced the values being sent. The write proceeds only if it still matches the current representation; otherwise it is refused with `412 Precondition Failed` and nothing is changed.\n\nThis is what makes a read-modify-write safe. Without it the last writer wins and a concurrent edit is silently discarded, which is the failure an agent is most likely to cause and least likely to notice. The `412` response carries the current `ETag`, so a caller can re-read, re-apply its change and retry.\n\nOmitting the header keeps the old unconditional behaviour. `*` matches any current representation, which asserts only that the resource exists."
2771
+ }
2772
+ ],
2773
+ "requestBodyType": "{ description?: string; enabled?: boolean; include_sql?: boolean; name: string; params?: ({ name: string; nullable?: boolean; type: \"text\" | \"integer\" | \"bigint\" | \"double precision\" | \"numeric\" | \"boolean\" | \"uuid\" | \"date\" | \"timestamptz\" | \"jsonb\" })[]; sql: string }",
2774
+ "requestBodyRequired": true,
2775
+ "responseType": "{ created_at: string; description: string; enabled: boolean; id: string; include_sql: boolean; name: string; params: ({ name: string; nullable?: boolean; type: \"text\" | \"integer\" | \"bigint\" | \"double precision\" | \"numeric\" | \"boolean\" | \"uuid\" | \"date\" | \"timestamptz\" | \"jsonb\" })[]; project_id: string; sql: string; statement_kind?: \"select\" | \"insert\" | \"update\" | \"delete\"; updated_at: string }",
2776
+ "responseStatus": "200"
2777
+ },
2778
+ "deleteQueryTemplate": {
2779
+ "operationId": "deleteQueryTemplate",
2780
+ "method": "DELETE",
2781
+ "path": "/v1/projects/{project_id}/query-templates/{query_template_id}",
2782
+ "summary": "Delete a query template",
2783
+ "description": "Removes the template, so a profile that runs templates only stops\nadmitting its statement. Deleting the last template is allowed: such a\nprofile then admits nothing, which is the intended way to withdraw\naccess in an incident.\n",
2784
+ "parameters": [
2785
+ {
2786
+ "name": "project_id",
2787
+ "in": "path",
2788
+ "required": true,
2789
+ "type": "string",
2790
+ "description": "Unique project identifier (prefixed, e.g. prj_xxx)."
2791
+ },
2792
+ {
2793
+ "name": "query_template_id",
2794
+ "in": "path",
2795
+ "required": true,
2796
+ "type": "string",
2797
+ "description": "Unique query template identifier (prefixed, e.g. qtp_xxx)."
2798
+ }
2799
+ ],
2800
+ "requestBodyType": "",
2801
+ "requestBodyRequired": false,
2802
+ "responseType": "",
2803
+ "responseStatus": "204"
2804
+ },
2479
2805
  "listRegions": {
2480
2806
  "operationId": "listRegions",
2481
2807
  "method": "GET",
@@ -2739,7 +3065,7 @@ var operationsMap_gen = require('./operations-map.gen-j3jalb8e.cjs');
2739
3065
  "method": "POST",
2740
3066
  "path": "/v1/organizations/{org_id}/self-host-enrollments",
2741
3067
  "summary": "Issue a self-host enrollment token",
2742
- "description": "Issues an enrollment token a self-hosted (BYOC) proxy uses to authenticate to the control plane's config/audit gRPC stream. The token is returned once and cannot be retrieved again. Requires the Scale or enterprise plan.",
3068
+ "description": "Issues an enrollment token a self-hosted (BYOC) proxy uses to authenticate to the control plane's config/audit gRPC stream. The token is returned once and cannot be retrieved again. Requires the Scale or enterprise plan.\nReturns 409 while any project in the organization has an enabled approval rule, because PgBeam cannot yet confirm that a self-hosted proxy runs a build that enforces approval rules. Disable those rules first; they can be saved with enabled set to false.",
2743
3069
  "parameters": [
2744
3070
  {
2745
3071
  "name": "org_id",
@@ -3006,18 +3332,6 @@ var operationsMap_gen = require('./operations-map.gen-j3jalb8e.cjs');
3006
3332
  "responseType": "{ author_image?: string; author_name: string; body: string; case_id: string; created_at: string; id: string; slack_user_id?: string; source: \"user\" | \"slack\" }",
3007
3333
  "responseStatus": "201"
3008
3334
  },
3009
- "handleSlackSupportEvent": {
3010
- "operationId": "handleSlackSupportEvent",
3011
- "method": "POST",
3012
- "path": "/v1/internal/support/slack-event",
3013
- "summary": "Handle a Slack support event",
3014
- "description": "Receives a forwarded Slack event from the dashboard webhook handler and creates a support message.",
3015
- "parameters": [],
3016
- "requestBodyType": "{ channel_id: string; text: string; thread_ts: string; user_id: string }",
3017
- "requestBodyRequired": true,
3018
- "responseType": "",
3019
- "responseStatus": "200"
3020
- },
3021
3335
  "scanText": {
3022
3336
  "operationId": "scanText",
3023
3337
  "method": "POST",
@@ -1,4 +1,4 @@
1
- export { z3 as ApiOperations, z4 as ApiTag, z5 as RequestMap, z6 as Route, z7 as operationsByPath, z8 as operationsByTag } from './operations-map.gen-hnc5e145.js';
1
+ export { Ba as ApiOperations, Bb as ApiTag, Bc as RequestMap, Bd as Route, Be as operationsByPath, Bf as operationsByTag } from './operations-map.gen-g8h39ajx.js';
2
2
 
3
3
  /**
4
4
  * Generated by generate-sdk-ts-maps.ts from backend/openapi/bundles/public.yaml — do not edit manually.
@@ -1,4 +1,4 @@
1
- export { z3 as ApiOperations, z4 as ApiTag, z5 as RequestMap, z6 as Route, z7 as operationsByPath, z8 as operationsByTag } from './operations-map.gen-hnc5e145.js';
1
+ export { Ba as ApiOperations, Bb as ApiTag, Bc as RequestMap, Bd as Route, Be as operationsByPath, Bf as operationsByTag } from './operations-map.gen-g8h39ajx.js';
2
2
 
3
3
  /**
4
4
  * Generated by generate-sdk-ts-maps.ts from backend/openapi/bundles/public.yaml — do not edit manually.