@opengeni/db 0.28.1 → 0.31.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/attached-browser-devices.d.ts +42 -0
- package/dist/attempt-tool-catalogs.d.ts +16 -0
- package/dist/browser-auth.d.ts +91 -0
- package/dist/browser-identities.d.ts +128 -0
- package/dist/browser-sessions.d.ts +272 -0
- package/dist/browser-state-artifacts.d.ts +17 -0
- package/dist/capability-components.d.ts +37 -0
- package/dist/capability-integrations.d.ts +192 -0
- package/dist/chunk-F5FT7BEZ.js +3535 -0
- package/dist/chunk-F5FT7BEZ.js.map +1 -0
- package/dist/chunk-ISI2TIUG.js +639 -0
- package/dist/chunk-ISI2TIUG.js.map +1 -0
- package/dist/chunk-MWDVXQOL.js +11639 -0
- package/dist/chunk-MWDVXQOL.js.map +1 -0
- package/dist/chunk-NBE6CHRI.js +955 -0
- package/dist/chunk-NBE6CHRI.js.map +1 -0
- package/dist/{chunk-DBS5HPEW.js → chunk-YHZXQ7HP.js} +760 -11
- package/dist/chunk-YHZXQ7HP.js.map +1 -0
- package/dist/codemode-operations.d.ts +117 -0
- package/dist/codex-token-resolver.d.ts +2 -2
- package/dist/company-profile-schema.d.ts +798 -0
- package/dist/company-profile.d.ts +268 -0
- package/dist/computer-sessions.d.ts +109 -0
- package/dist/connection-token-resolver.d.ts +9 -4
- package/dist/database.d.ts +52 -3
- package/dist/editable-artifact-durable-export.d.ts +153 -0
- package/dist/editable-artifact-durable-export.js +788 -0
- package/dist/editable-artifact-durable-export.js.map +1 -0
- package/dist/editable-artifact-materialization.d.ts +123 -0
- package/dist/editable-artifacts-schema.d.ts +4152 -0
- package/dist/editable-artifacts.d.ts +610 -0
- package/dist/editable-artifacts.js +26 -0
- package/dist/editable-artifacts.js.map +1 -0
- package/dist/environment-crypto.d.ts +8 -4
- package/dist/generated-images.d.ts +139 -0
- package/dist/index.d.ts +958 -126
- package/dist/index.js +31204 -12172
- package/dist/index.js.map +1 -1
- package/dist/insights.d.ts +51 -4
- package/dist/integration-bindings.d.ts +70 -0
- package/dist/integration-features.d.ts +99 -0
- package/dist/interaction-revisions.d.ts +3 -0
- package/dist/interaction-schema.d.ts +5372 -0
- package/dist/knowledge-source-sync-schema.d.ts +1679 -0
- package/dist/knowledge-source-sync.d.ts +274 -0
- package/dist/lossless-columns.d.ts +58 -0
- package/dist/lossless-json.d.ts +39 -0
- package/dist/memory-domain.d.ts +3 -6
- package/dist/memory-governance.d.ts +2 -2
- package/dist/memory-slack-delivery.d.ts +101 -0
- package/dist/new-session-drafts.d.ts +2 -2
- package/dist/pack-components.d.ts +76 -0
- package/dist/pack-installations.d.ts +86 -0
- package/dist/persistence-errors.d.ts +7 -14
- package/dist/plugin-packages.d.ts +126 -0
- package/dist/preference-registry.d.ts +1 -1
- package/dist/provision-roles.d.ts +9 -1
- package/dist/provision-roles.js +1 -1
- package/dist/runtime-posture.d.ts +18 -6
- package/dist/schema.d.ts +19122 -8731
- package/dist/schema.js +173 -1
- package/dist/scoped-knowledge.d.ts +97 -1
- package/dist/session-control.d.ts +4 -4
- package/dist/session-queue-commands.d.ts +19 -11
- package/dist/session-realtime-context.d.ts +2 -2
- package/dist/session-realtime-ledger.d.ts +4 -4
- package/dist/session-realtime-mirror.d.ts +2 -2
- package/dist/session-realtime-state.d.ts +1 -1
- package/dist/session-realtime-terminal.d.ts +8 -1
- package/dist/session-realtime.d.ts +7 -7
- package/dist/session-tool-call-settlement.d.ts +1 -1
- package/dist/slack-user-link-access.d.ts +54 -0
- package/dist/transcription-recordings-schema.d.ts +44 -6
- package/dist/transcription-recordings.d.ts +3 -3
- package/dist/turn-initiator.d.ts +2 -2
- package/dist/video-generation.d.ts +216 -0
- package/dist/video-generation.js +66 -0
- package/dist/video-generation.js.map +1 -0
- package/dist/workspace-artifacts.d.ts +1 -1
- package/dist/workspace-instruction-policies.d.ts +1 -1
- package/dist/workspace-learning-policy-schema.d.ts +932 -0
- package/dist/workspace-learning-policy.d.ts +161 -0
- package/drizzle/0065_enrollment_credential_generation.sql +10 -0
- package/drizzle/0140_retained_screenshot_artifacts.sql +192 -0
- package/drizzle/0176_lossless_canonical_json.sql +975 -0
- package/drizzle/0177_session_events_workspace_turn_type_index.sql +5 -0
- package/drizzle/0178_permissioned_secret_reads.sql +14 -0
- package/drizzle/0179_slack_private_shortcut_delivery_gate.sql +85 -0
- package/drizzle/0180_retained_screenshot_lifecycle_fences.sql +273 -0
- package/drizzle/0181_connected_machine_removal.sql +52 -0
- package/drizzle/0182_connected_machine_remove_session_default.sql +77 -0
- package/drizzle/0183_model_call_provider_cost_estimates.sql +39 -0
- package/drizzle/0184_sandbox_drain_teardown_fence.sql +682 -0
- package/drizzle/0185_temporal_schedule_cleanup_outbox.sql +168 -0
- package/drizzle/0186_sandbox_capture_provider_contract.sql +400 -0
- package/drizzle/0187_generated_image_artifacts.sql +173 -0
- package/drizzle/0188_image_generation_retention_failure.sql +25 -0
- package/drizzle/0189_retained_session_image_formats.sql +13 -0
- package/drizzle/0190_timeline_annotations.sql +31 -0
- package/drizzle/0191_editable_artifact_engine.sql +3853 -0
- package/drizzle/0192_editable_artifact_live_tickets.sql +338 -0
- package/drizzle/0193_editable_artifact_authorization.sql +190 -0
- package/drizzle/0194_editable_artifact_durable_exports.sql +160 -0
- package/drizzle/0195_editable_artifact_import_authorization.sql +203 -0
- package/drizzle/0196_rig_provider_images.sql +152 -0
- package/drizzle/0197_knowledge_source_sync_schedules.sql +523 -0
- package/drizzle/0198_memory_slack_publication_delivery.sql +393 -0
- package/drizzle/0199_workspace_learning_policy.sql +980 -0
- package/drizzle/0201_company_profile_authority.sql +849 -0
- package/drizzle/0202_document_index_checkpoints.sql +85 -0
- package/drizzle/0203_durable_video_generation.sql +353 -0
- package/drizzle/0204_video_generation_funding.sql +44 -0
- package/drizzle/0205_attempt_tool_catalogs.sql +230 -0
- package/drizzle/0206_browser_sessions.sql +646 -0
- package/drizzle/0207_browser_identities.sql +379 -0
- package/drizzle/0208_attached_browser_devices.sql +165 -0
- package/drizzle/0209_computer_sessions.sql +575 -0
- package/drizzle/0210_browser_auth_network_interventions.sql +441 -0
- package/drizzle/0211_editable_artifact_session_links.sql +58 -0
- package/drizzle/0212_slack_installation_bindings.sql +348 -0
- package/drizzle/0213_slack_user_link_access_requests.sql +177 -0
- package/drizzle/0214_session_activity_commit_gate.sql +262 -0
- package/drizzle/0215_capabilities_platform.sql +980 -0
- package/drizzle/0216_pack_component_ownership.sql +235 -0
- package/drizzle/0217_capability_definition_delete_authority.sql +32 -0
- package/package.json +18 -5
- package/src/attached-browser-devices.ts +371 -0
- package/src/attempt-tool-catalogs.ts +131 -0
- package/src/browser-auth.ts +1896 -0
- package/src/browser-identities.ts +1168 -0
- package/src/browser-sessions.ts +2005 -0
- package/src/browser-state-artifacts.ts +59 -0
- package/src/capability-components.ts +166 -0
- package/src/capability-integrations.ts +1663 -0
- package/src/codemode-operations.ts +674 -0
- package/src/company-profile-schema.ts +143 -0
- package/src/company-profile.ts +968 -0
- package/src/computer-sessions.ts +1130 -0
- package/src/connection-token-resolver.ts +270 -25
- package/src/database.ts +434 -24
- package/src/editable-artifact-durable-export.ts +1201 -0
- package/src/editable-artifact-materialization.ts +893 -0
- package/src/editable-artifacts-schema.ts +879 -0
- package/src/editable-artifacts.ts +5404 -0
- package/src/environment-crypto.ts +22 -9
- package/src/generated-images.ts +740 -0
- package/src/index.ts +10117 -2730
- package/src/insights.ts +160 -13
- package/src/integration-bindings.ts +455 -0
- package/src/integration-features.ts +859 -0
- package/src/interaction-revisions.ts +40 -0
- package/src/interaction-schema.ts +1303 -0
- package/src/knowledge-source-sync-schema.ts +192 -0
- package/src/knowledge-source-sync.ts +1922 -0
- package/src/lossless-columns.ts +35 -0
- package/src/lossless-json.ts +322 -0
- package/src/memory-domain.ts +5 -44
- package/src/memory-slack-delivery.ts +801 -0
- package/src/pack-components.ts +954 -0
- package/src/pack-installations.ts +929 -0
- package/src/persistence-errors.ts +26 -34
- package/src/plugin-packages.ts +1186 -0
- package/src/provision-roles.ts +302 -1
- package/src/runtime-posture-cli.ts +9 -0
- package/src/runtime-posture.ts +514 -5
- package/src/schema.ts +5177 -2957
- package/src/scoped-knowledge-schema.ts +1 -1
- package/src/scoped-knowledge.ts +655 -3
- package/src/session-control.ts +133 -81
- package/src/session-queue-commands.ts +511 -247
- package/src/session-realtime-context.ts +20 -7
- package/src/session-realtime-ledger.ts +32 -10
- package/src/session-realtime-mirror.ts +4 -2
- package/src/session-realtime-terminal.ts +89 -21
- package/src/session-realtime.ts +10 -9
- package/src/session-tool-call-settlement.ts +38 -15
- package/src/slack-user-link-access.ts +702 -0
- package/src/transcription-recordings-schema.ts +5 -2
- package/src/transcription-recordings.ts +70 -40
- package/src/video-generation.ts +1452 -0
- package/src/workspace-learning-policy-schema.ts +139 -0
- package/src/workspace-learning-policy.ts +595 -0
- package/dist/chunk-DBS5HPEW.js.map +0 -1
- package/dist/chunk-HT5T62CC.js +0 -6803
- package/dist/chunk-HT5T62CC.js.map +0 -1
- package/dist/event-payload-sanitizer.d.ts +0 -32
- package/src/event-payload-sanitizer.ts +0 -377
|
@@ -0,0 +1,575 @@
|
|
|
1
|
+
-- deployment-mode: maintenance
|
|
2
|
+
-- Canonical durable ComputerSession registry. Native seat/display facts are
|
|
3
|
+
-- supplied only by the exact placement controller after physical activation.
|
|
4
|
+
SET LOCAL lock_timeout = '5s';
|
|
5
|
+
SET LOCAL statement_timeout = '30s';
|
|
6
|
+
|
|
7
|
+
CREATE TABLE "computer_sessions" (
|
|
8
|
+
"id" uuid PRIMARY KEY,
|
|
9
|
+
"account_id" uuid NOT NULL,
|
|
10
|
+
"workspace_id" uuid NOT NULL,
|
|
11
|
+
"name" text NOT NULL,
|
|
12
|
+
"lifecycle" text NOT NULL DEFAULT 'starting',
|
|
13
|
+
"placement_kind" text NOT NULL,
|
|
14
|
+
"sandbox_group_id" uuid,
|
|
15
|
+
"connected_sandbox_id" uuid,
|
|
16
|
+
"device_id" uuid,
|
|
17
|
+
"external_provider_id" text,
|
|
18
|
+
"external_placement_id" text,
|
|
19
|
+
"controller_id" text,
|
|
20
|
+
"controller_generation" text,
|
|
21
|
+
"placement_instance_id" text,
|
|
22
|
+
"token_generation" integer NOT NULL DEFAULT 1,
|
|
23
|
+
"platform" text,
|
|
24
|
+
"adapter" text,
|
|
25
|
+
"seat_id" text,
|
|
26
|
+
"display_id" text,
|
|
27
|
+
"capabilities" jsonb,
|
|
28
|
+
"create_operation_id" uuid NOT NULL,
|
|
29
|
+
"created_by_subject_id" text NOT NULL,
|
|
30
|
+
"failure_code" text,
|
|
31
|
+
"controller_heartbeat_at" timestamptz,
|
|
32
|
+
"created_at" timestamptz NOT NULL DEFAULT now(),
|
|
33
|
+
"last_used_at" timestamptz NOT NULL DEFAULT now(),
|
|
34
|
+
"updated_at" timestamptz NOT NULL DEFAULT now(),
|
|
35
|
+
CONSTRAINT "computer_sessions_workspace_account_fk"
|
|
36
|
+
FOREIGN KEY ("workspace_id", "account_id")
|
|
37
|
+
REFERENCES "workspaces"("id", "account_id") ON DELETE CASCADE,
|
|
38
|
+
CONSTRAINT "computer_sessions_create_operation_fk"
|
|
39
|
+
FOREIGN KEY ("workspace_id", "create_operation_id")
|
|
40
|
+
REFERENCES "interaction_operations"("workspace_id", "operation_id") ON DELETE RESTRICT,
|
|
41
|
+
CONSTRAINT "computer_sessions_lifecycle_check" CHECK (
|
|
42
|
+
"lifecycle" IN (
|
|
43
|
+
'starting', 'active', 'suspending', 'suspended', 'restoring',
|
|
44
|
+
'repair_required', 'lost', 'ending', 'ended', 'failed'
|
|
45
|
+
)
|
|
46
|
+
),
|
|
47
|
+
CONSTRAINT "computer_sessions_platform_check"
|
|
48
|
+
CHECK ("platform" IS NULL OR "platform" IN ('linux', 'macos', 'windows')),
|
|
49
|
+
CONSTRAINT "computer_sessions_values_check" CHECK (
|
|
50
|
+
octet_length("name") BETWEEN 1 AND 200
|
|
51
|
+
AND "name" = btrim("name")
|
|
52
|
+
AND octet_length("created_by_subject_id") BETWEEN 1 AND 1024
|
|
53
|
+
AND "token_generation" > 0
|
|
54
|
+
AND ("adapter" IS NULL OR octet_length("adapter") BETWEEN 1 AND 512)
|
|
55
|
+
AND ("seat_id" IS NULL OR octet_length("seat_id") BETWEEN 1 AND 512)
|
|
56
|
+
AND ("display_id" IS NULL OR octet_length("display_id") BETWEEN 1 AND 512)
|
|
57
|
+
AND ("capabilities" IS NULL OR (
|
|
58
|
+
jsonb_typeof("capabilities") = 'object'
|
|
59
|
+
AND octet_length("capabilities"::text) BETWEEN 2 AND 65536
|
|
60
|
+
))
|
|
61
|
+
AND ("failure_code" IS NULL OR octet_length("failure_code") BETWEEN 1 AND 512)
|
|
62
|
+
),
|
|
63
|
+
CONSTRAINT "computer_sessions_placement_check" CHECK (
|
|
64
|
+
(
|
|
65
|
+
"placement_kind" = 'sandbox_group'
|
|
66
|
+
AND "sandbox_group_id" IS NOT NULL
|
|
67
|
+
AND "connected_sandbox_id" IS NULL
|
|
68
|
+
AND "device_id" IS NULL
|
|
69
|
+
AND "external_provider_id" IS NULL
|
|
70
|
+
AND "external_placement_id" IS NULL
|
|
71
|
+
) OR (
|
|
72
|
+
"placement_kind" = 'connected_machine'
|
|
73
|
+
AND "sandbox_group_id" IS NULL
|
|
74
|
+
AND "connected_sandbox_id" IS NOT NULL
|
|
75
|
+
AND "device_id" IS NULL
|
|
76
|
+
AND "external_provider_id" IS NULL
|
|
77
|
+
AND "external_placement_id" IS NULL
|
|
78
|
+
) OR (
|
|
79
|
+
"placement_kind" = 'attached_device'
|
|
80
|
+
AND "sandbox_group_id" IS NULL
|
|
81
|
+
AND "connected_sandbox_id" IS NULL
|
|
82
|
+
AND "device_id" IS NOT NULL
|
|
83
|
+
AND "external_provider_id" IS NULL
|
|
84
|
+
AND "external_placement_id" IS NULL
|
|
85
|
+
) OR (
|
|
86
|
+
"placement_kind" = 'external_provider'
|
|
87
|
+
AND "sandbox_group_id" IS NULL
|
|
88
|
+
AND "connected_sandbox_id" IS NULL
|
|
89
|
+
AND "device_id" IS NULL
|
|
90
|
+
AND "external_provider_id" IS NOT NULL
|
|
91
|
+
AND "external_placement_id" IS NOT NULL
|
|
92
|
+
AND octet_length("external_provider_id") BETWEEN 1 AND 512
|
|
93
|
+
AND octet_length("external_placement_id") BETWEEN 1 AND 512
|
|
94
|
+
)
|
|
95
|
+
),
|
|
96
|
+
CONSTRAINT "computer_sessions_controller_check" CHECK (
|
|
97
|
+
(
|
|
98
|
+
"controller_id" IS NULL
|
|
99
|
+
AND "controller_generation" IS NULL
|
|
100
|
+
AND "placement_instance_id" IS NULL
|
|
101
|
+
AND "controller_heartbeat_at" IS NULL
|
|
102
|
+
) OR (
|
|
103
|
+
"controller_id" IS NOT NULL
|
|
104
|
+
AND octet_length("controller_id") BETWEEN 1 AND 512
|
|
105
|
+
AND "controller_generation" IS NOT NULL
|
|
106
|
+
AND octet_length("controller_generation") BETWEEN 1 AND 256
|
|
107
|
+
AND "placement_instance_id" IS NOT NULL
|
|
108
|
+
AND octet_length("placement_instance_id") BETWEEN 1 AND 512
|
|
109
|
+
AND "controller_heartbeat_at" IS NOT NULL
|
|
110
|
+
)
|
|
111
|
+
),
|
|
112
|
+
CONSTRAINT "computer_sessions_native_binding_check" CHECK (
|
|
113
|
+
(
|
|
114
|
+
"platform" IS NULL
|
|
115
|
+
AND "adapter" IS NULL
|
|
116
|
+
AND "seat_id" IS NULL
|
|
117
|
+
AND "display_id" IS NULL
|
|
118
|
+
AND "capabilities" IS NULL
|
|
119
|
+
) OR (
|
|
120
|
+
"platform" IS NOT NULL
|
|
121
|
+
AND "adapter" IS NOT NULL
|
|
122
|
+
AND "seat_id" IS NOT NULL
|
|
123
|
+
AND "display_id" IS NOT NULL
|
|
124
|
+
AND "capabilities" IS NOT NULL
|
|
125
|
+
)
|
|
126
|
+
),
|
|
127
|
+
CONSTRAINT "computer_sessions_active_binding_check" CHECK (
|
|
128
|
+
"lifecycle" <> 'active' OR (
|
|
129
|
+
"controller_id" IS NOT NULL
|
|
130
|
+
AND "platform" IS NOT NULL
|
|
131
|
+
AND "capabilities" IS NOT NULL
|
|
132
|
+
)
|
|
133
|
+
),
|
|
134
|
+
CONSTRAINT "computer_sessions_failure_check" CHECK (
|
|
135
|
+
(
|
|
136
|
+
"lifecycle" IN ('repair_required', 'lost', 'failed')
|
|
137
|
+
AND "failure_code" IS NOT NULL
|
|
138
|
+
) OR (
|
|
139
|
+
"lifecycle" NOT IN ('repair_required', 'lost', 'failed')
|
|
140
|
+
AND "failure_code" IS NULL
|
|
141
|
+
)
|
|
142
|
+
),
|
|
143
|
+
CONSTRAINT "computer_sessions_workspace_id_uq" UNIQUE ("workspace_id", "id"),
|
|
144
|
+
CONSTRAINT "computer_sessions_workspace_create_operation_uq"
|
|
145
|
+
UNIQUE ("workspace_id", "create_operation_id")
|
|
146
|
+
);
|
|
147
|
+
|
|
148
|
+
CREATE INDEX "computer_sessions_workspace_lifecycle_idx"
|
|
149
|
+
ON "computer_sessions" ("workspace_id", "lifecycle", "last_used_at", "id");
|
|
150
|
+
CREATE INDEX "computer_sessions_sandbox_group_idx"
|
|
151
|
+
ON "computer_sessions" ("workspace_id", "sandbox_group_id", "lifecycle");
|
|
152
|
+
|
|
153
|
+
CREATE TABLE "computer_session_associations" (
|
|
154
|
+
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid(),
|
|
155
|
+
"account_id" uuid NOT NULL,
|
|
156
|
+
"workspace_id" uuid NOT NULL,
|
|
157
|
+
"computer_session_id" uuid NOT NULL,
|
|
158
|
+
"session_id" uuid NOT NULL,
|
|
159
|
+
"turn_id" uuid,
|
|
160
|
+
"attempt_id" uuid,
|
|
161
|
+
"relationship" text NOT NULL,
|
|
162
|
+
"actor_subject_id" text NOT NULL,
|
|
163
|
+
"last_used_at" timestamptz NOT NULL DEFAULT now(),
|
|
164
|
+
"created_at" timestamptz NOT NULL DEFAULT now(),
|
|
165
|
+
CONSTRAINT "computer_session_associations_workspace_account_fk"
|
|
166
|
+
FOREIGN KEY ("workspace_id", "account_id")
|
|
167
|
+
REFERENCES "workspaces"("id", "account_id") ON DELETE CASCADE,
|
|
168
|
+
CONSTRAINT "computer_session_associations_resource_fk"
|
|
169
|
+
FOREIGN KEY ("workspace_id", "computer_session_id")
|
|
170
|
+
REFERENCES "computer_sessions"("workspace_id", "id") ON DELETE CASCADE,
|
|
171
|
+
CONSTRAINT "computer_session_associations_session_fk"
|
|
172
|
+
FOREIGN KEY ("workspace_id", "session_id")
|
|
173
|
+
REFERENCES "sessions"("workspace_id", "id") ON DELETE CASCADE,
|
|
174
|
+
CONSTRAINT "computer_session_associations_turn_fk"
|
|
175
|
+
FOREIGN KEY ("workspace_id", "turn_id")
|
|
176
|
+
REFERENCES "session_turns"("workspace_id", "id") ON DELETE SET NULL ("turn_id"),
|
|
177
|
+
CONSTRAINT "computer_session_associations_attempt_fk"
|
|
178
|
+
FOREIGN KEY ("workspace_id", "attempt_id")
|
|
179
|
+
REFERENCES "session_turn_attempts"("workspace_id", "id") ON DELETE SET NULL ("attempt_id"),
|
|
180
|
+
CONSTRAINT "computer_session_associations_relationship_check"
|
|
181
|
+
CHECK ("relationship" IN ('created', 'using', 'observing', 'related')),
|
|
182
|
+
CONSTRAINT "computer_session_associations_values_check" CHECK (
|
|
183
|
+
octet_length("actor_subject_id") BETWEEN 1 AND 1024
|
|
184
|
+
AND ("attempt_id" IS NULL OR "turn_id" IS NOT NULL)
|
|
185
|
+
),
|
|
186
|
+
CONSTRAINT "computer_session_associations_resource_session_relationship_uq"
|
|
187
|
+
UNIQUE ("computer_session_id", "session_id", "relationship")
|
|
188
|
+
);
|
|
189
|
+
|
|
190
|
+
CREATE INDEX "computer_session_associations_workspace_session_idx"
|
|
191
|
+
ON "computer_session_associations" ("workspace_id", "session_id", "last_used_at");
|
|
192
|
+
CREATE INDEX "computer_session_associations_resource_idx"
|
|
193
|
+
ON "computer_session_associations" ("workspace_id", "computer_session_id", "last_used_at");
|
|
194
|
+
|
|
195
|
+
ALTER TABLE "browser_sessions"
|
|
196
|
+
ADD CONSTRAINT "browser_sessions_linked_computer_session_fk"
|
|
197
|
+
FOREIGN KEY ("workspace_id", "linked_computer_session_id")
|
|
198
|
+
REFERENCES "computer_sessions"("workspace_id", "id")
|
|
199
|
+
ON DELETE SET NULL ("linked_computer_session_id");
|
|
200
|
+
|
|
201
|
+
ALTER TABLE "computer_sessions" ENABLE ROW LEVEL SECURITY;
|
|
202
|
+
ALTER TABLE "computer_sessions" FORCE ROW LEVEL SECURITY;
|
|
203
|
+
CREATE POLICY workspace_isolation ON "computer_sessions"
|
|
204
|
+
USING (opengeni_private.workspace_rls_visible("account_id", "workspace_id"))
|
|
205
|
+
WITH CHECK (opengeni_private.workspace_rls_visible("account_id", "workspace_id"));
|
|
206
|
+
|
|
207
|
+
ALTER TABLE "computer_session_associations" ENABLE ROW LEVEL SECURITY;
|
|
208
|
+
ALTER TABLE "computer_session_associations" FORCE ROW LEVEL SECURITY;
|
|
209
|
+
CREATE POLICY workspace_isolation ON "computer_session_associations"
|
|
210
|
+
USING (opengeni_private.workspace_rls_visible("account_id", "workspace_id"))
|
|
211
|
+
WITH CHECK (opengeni_private.workspace_rls_visible("account_id", "workspace_id"));
|
|
212
|
+
|
|
213
|
+
DO $grants$
|
|
214
|
+
DECLARE target_schema text := current_schema();
|
|
215
|
+
BEGIN
|
|
216
|
+
IF EXISTS (SELECT 1 FROM pg_roles WHERE rolname = 'opengeni_app') THEN
|
|
217
|
+
EXECUTE format(
|
|
218
|
+
'REVOKE ALL ON TABLE %I.computer_sessions, %I.computer_session_associations FROM opengeni_app',
|
|
219
|
+
target_schema,
|
|
220
|
+
target_schema
|
|
221
|
+
);
|
|
222
|
+
EXECUTE format(
|
|
223
|
+
'GRANT SELECT, INSERT, UPDATE ON TABLE %I.computer_sessions TO opengeni_app',
|
|
224
|
+
target_schema
|
|
225
|
+
);
|
|
226
|
+
EXECUTE format(
|
|
227
|
+
'GRANT SELECT, INSERT, UPDATE, DELETE ON TABLE %I.computer_session_associations TO opengeni_app',
|
|
228
|
+
target_schema
|
|
229
|
+
);
|
|
230
|
+
END IF;
|
|
231
|
+
END
|
|
232
|
+
$grants$;
|
|
233
|
+
|
|
234
|
+
-- Interaction holders have one shared liveness protocol. A holder remains live
|
|
235
|
+
-- only while its exact BrowserSession or ComputerSession is live on the same
|
|
236
|
+
-- sandbox-group lease. Stale controllers lose the durable resource before the
|
|
237
|
+
-- holder is removed and the placement becomes drainable.
|
|
238
|
+
DO $interaction_aware_reaper$
|
|
239
|
+
DECLARE data_schema text := current_schema();
|
|
240
|
+
BEGIN
|
|
241
|
+
EXECUTE format($create$
|
|
242
|
+
CREATE OR REPLACE FUNCTION opengeni_private.reap_sandbox_leases(
|
|
243
|
+
p_viewer_holder_ttl_ms bigint,
|
|
244
|
+
p_turn_holder_ttl_ms bigint,
|
|
245
|
+
p_interaction_holder_ttl_ms bigint,
|
|
246
|
+
p_idle_grace_ms bigint
|
|
247
|
+
)
|
|
248
|
+
RETURNS TABLE (
|
|
249
|
+
workspace_id uuid,
|
|
250
|
+
sandbox_group_id uuid,
|
|
251
|
+
instance_id text,
|
|
252
|
+
lease_epoch integer
|
|
253
|
+
)
|
|
254
|
+
LANGUAGE plpgsql
|
|
255
|
+
SECURITY DEFINER
|
|
256
|
+
SET search_path = pg_catalog
|
|
257
|
+
AS $function$
|
|
258
|
+
DECLARE
|
|
259
|
+
locked_ids uuid[];
|
|
260
|
+
stale_interaction_ids uuid[];
|
|
261
|
+
changed_interaction_workspaces uuid[];
|
|
262
|
+
BEGIN
|
|
263
|
+
PERFORM pg_catalog.set_config('opengeni.sandbox_recovery_protocol_v2', '1', true);
|
|
264
|
+
|
|
265
|
+
SELECT coalesce(pg_catalog.array_agg(candidate.id), ARRAY[]::uuid[])
|
|
266
|
+
INTO locked_ids
|
|
267
|
+
FROM (
|
|
268
|
+
SELECT lease.id
|
|
269
|
+
FROM %1$I.sandbox_leases lease
|
|
270
|
+
WHERE lease.liveness <> 'cold'
|
|
271
|
+
OR EXISTS (
|
|
272
|
+
SELECT 1
|
|
273
|
+
FROM %1$I.sandbox_lease_holders holder
|
|
274
|
+
WHERE holder.lease_id = lease.id
|
|
275
|
+
)
|
|
276
|
+
ORDER BY lease.updated_at, lease.id
|
|
277
|
+
LIMIT 500
|
|
278
|
+
FOR UPDATE OF lease SKIP LOCKED
|
|
279
|
+
) candidate;
|
|
280
|
+
|
|
281
|
+
IF pg_catalog.cardinality(locked_ids) = 0 THEN
|
|
282
|
+
RETURN;
|
|
283
|
+
END IF;
|
|
284
|
+
|
|
285
|
+
DELETE FROM %1$I.sandbox_lease_holders holder
|
|
286
|
+
USING (
|
|
287
|
+
SELECT stale.id
|
|
288
|
+
FROM %1$I.sandbox_lease_holders stale
|
|
289
|
+
WHERE stale.lease_id = ANY(locked_ids)
|
|
290
|
+
AND stale.kind IN ('viewer', 'direct')
|
|
291
|
+
AND stale.last_heartbeat_at
|
|
292
|
+
< pg_catalog.now()
|
|
293
|
+
- pg_catalog.make_interval(secs => p_viewer_holder_ttl_ms / 1000.0)
|
|
294
|
+
FOR UPDATE OF stale SKIP LOCKED
|
|
295
|
+
) victim
|
|
296
|
+
WHERE holder.id = victim.id;
|
|
297
|
+
|
|
298
|
+
IF p_turn_holder_ttl_ms > 0 THEN
|
|
299
|
+
DELETE FROM %1$I.sandbox_lease_holders holder
|
|
300
|
+
USING (
|
|
301
|
+
SELECT stale.id
|
|
302
|
+
FROM %1$I.sandbox_lease_holders stale
|
|
303
|
+
WHERE stale.lease_id = ANY(locked_ids)
|
|
304
|
+
AND stale.kind = 'turn'
|
|
305
|
+
AND (
|
|
306
|
+
stale.last_heartbeat_at
|
|
307
|
+
< pg_catalog.now()
|
|
308
|
+
- pg_catalog.make_interval(secs => p_turn_holder_ttl_ms / 1000.0)
|
|
309
|
+
OR (
|
|
310
|
+
stale.holder_id ~* '^turn-attempt:[0-9a-f]{8}-[0-9a-f]{4}-[1-5][0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$'
|
|
311
|
+
AND NOT EXISTS (
|
|
312
|
+
SELECT 1
|
|
313
|
+
FROM %1$I.session_turn_attempts attempt
|
|
314
|
+
JOIN %1$I.session_turns turn
|
|
315
|
+
ON turn.account_id = attempt.account_id
|
|
316
|
+
AND turn.workspace_id = attempt.workspace_id
|
|
317
|
+
AND turn.session_id = attempt.session_id
|
|
318
|
+
AND turn.id = attempt.turn_id
|
|
319
|
+
AND turn.execution_generation = attempt.execution_generation
|
|
320
|
+
AND turn.active_attempt_id = attempt.id
|
|
321
|
+
WHERE stale.holder_id = ('turn-attempt:' || attempt.id::text)
|
|
322
|
+
AND attempt.account_id = stale.account_id
|
|
323
|
+
AND attempt.workspace_id = stale.workspace_id
|
|
324
|
+
AND attempt.session_id = stale.subject_id
|
|
325
|
+
AND attempt.state IN ('claimed', 'running')
|
|
326
|
+
)
|
|
327
|
+
)
|
|
328
|
+
)
|
|
329
|
+
FOR UPDATE OF stale SKIP LOCKED
|
|
330
|
+
) victim
|
|
331
|
+
WHERE holder.id = victim.id;
|
|
332
|
+
END IF;
|
|
333
|
+
|
|
334
|
+
IF p_interaction_holder_ttl_ms > 0 THEN
|
|
335
|
+
SELECT coalesce(pg_catalog.array_agg(candidate.id), ARRAY[]::uuid[])
|
|
336
|
+
INTO stale_interaction_ids
|
|
337
|
+
FROM (
|
|
338
|
+
SELECT stale.id
|
|
339
|
+
FROM %1$I.sandbox_lease_holders stale
|
|
340
|
+
JOIN %1$I.sandbox_leases lease ON lease.id = stale.lease_id
|
|
341
|
+
WHERE stale.lease_id = ANY(locked_ids)
|
|
342
|
+
AND stale.kind = 'interaction'
|
|
343
|
+
AND (
|
|
344
|
+
stale.last_heartbeat_at
|
|
345
|
+
< pg_catalog.now()
|
|
346
|
+
- pg_catalog.make_interval(
|
|
347
|
+
secs => p_interaction_holder_ttl_ms / 1000.0
|
|
348
|
+
)
|
|
349
|
+
OR NOT (
|
|
350
|
+
EXISTS (
|
|
351
|
+
SELECT 1
|
|
352
|
+
FROM %1$I.browser_sessions browser
|
|
353
|
+
WHERE stale.holder_id = ('browser-session:' || browser.id::text)
|
|
354
|
+
AND browser.account_id = stale.account_id
|
|
355
|
+
AND browser.workspace_id = stale.workspace_id
|
|
356
|
+
AND browser.sandbox_group_id = lease.sandbox_group_id
|
|
357
|
+
AND browser.lifecycle IN (
|
|
358
|
+
'starting', 'active', 'suspending', 'restoring', 'ending'
|
|
359
|
+
)
|
|
360
|
+
)
|
|
361
|
+
OR EXISTS (
|
|
362
|
+
SELECT 1
|
|
363
|
+
FROM %1$I.computer_sessions computer
|
|
364
|
+
WHERE stale.holder_id = ('computer-session:' || computer.id::text)
|
|
365
|
+
AND computer.account_id = stale.account_id
|
|
366
|
+
AND computer.workspace_id = stale.workspace_id
|
|
367
|
+
AND computer.sandbox_group_id = lease.sandbox_group_id
|
|
368
|
+
AND computer.lifecycle IN (
|
|
369
|
+
'starting', 'active', 'suspending', 'restoring', 'ending'
|
|
370
|
+
)
|
|
371
|
+
)
|
|
372
|
+
)
|
|
373
|
+
)
|
|
374
|
+
FOR UPDATE OF stale SKIP LOCKED
|
|
375
|
+
) candidate;
|
|
376
|
+
|
|
377
|
+
IF pg_catalog.cardinality(stale_interaction_ids) > 0 THEN
|
|
378
|
+
WITH updated_browser AS (
|
|
379
|
+
UPDATE %1$I.browser_sessions browser
|
|
380
|
+
SET lifecycle = 'lost',
|
|
381
|
+
controller_id = null,
|
|
382
|
+
controller_generation = null,
|
|
383
|
+
placement_instance_id = null,
|
|
384
|
+
controller_heartbeat_at = null,
|
|
385
|
+
failure_code = 'controller_heartbeat_expired',
|
|
386
|
+
updated_at = pg_catalog.now()
|
|
387
|
+
FROM %1$I.sandbox_lease_holders holder
|
|
388
|
+
WHERE holder.id = ANY(stale_interaction_ids)
|
|
389
|
+
AND holder.holder_id = ('browser-session:' || browser.id::text)
|
|
390
|
+
AND holder.account_id = browser.account_id
|
|
391
|
+
AND holder.workspace_id = browser.workspace_id
|
|
392
|
+
AND browser.lifecycle IN (
|
|
393
|
+
'starting', 'active', 'suspending', 'restoring', 'ending'
|
|
394
|
+
)
|
|
395
|
+
RETURNING browser.workspace_id
|
|
396
|
+
), updated_computer AS (
|
|
397
|
+
UPDATE %1$I.computer_sessions computer
|
|
398
|
+
SET lifecycle = 'lost',
|
|
399
|
+
controller_id = null,
|
|
400
|
+
controller_generation = null,
|
|
401
|
+
placement_instance_id = null,
|
|
402
|
+
controller_heartbeat_at = null,
|
|
403
|
+
failure_code = 'controller_heartbeat_expired',
|
|
404
|
+
updated_at = pg_catalog.now()
|
|
405
|
+
FROM %1$I.sandbox_lease_holders holder
|
|
406
|
+
WHERE holder.id = ANY(stale_interaction_ids)
|
|
407
|
+
AND holder.holder_id = ('computer-session:' || computer.id::text)
|
|
408
|
+
AND holder.account_id = computer.account_id
|
|
409
|
+
AND holder.workspace_id = computer.workspace_id
|
|
410
|
+
AND computer.lifecycle IN (
|
|
411
|
+
'starting', 'active', 'suspending', 'restoring', 'ending'
|
|
412
|
+
)
|
|
413
|
+
RETURNING computer.workspace_id
|
|
414
|
+
), updated AS (
|
|
415
|
+
SELECT workspace_id FROM updated_browser
|
|
416
|
+
UNION
|
|
417
|
+
SELECT workspace_id FROM updated_computer
|
|
418
|
+
)
|
|
419
|
+
SELECT coalesce(
|
|
420
|
+
pg_catalog.array_agg(DISTINCT updated.workspace_id),
|
|
421
|
+
ARRAY[]::uuid[]
|
|
422
|
+
)
|
|
423
|
+
INTO changed_interaction_workspaces
|
|
424
|
+
FROM updated;
|
|
425
|
+
|
|
426
|
+
DELETE FROM %1$I.sandbox_lease_holders holder
|
|
427
|
+
WHERE holder.id = ANY(stale_interaction_ids);
|
|
428
|
+
|
|
429
|
+
UPDATE %1$I.workspace_interaction_revisions revision
|
|
430
|
+
SET revision = revision.revision + 1,
|
|
431
|
+
updated_at = pg_catalog.now()
|
|
432
|
+
WHERE revision.workspace_id = ANY(changed_interaction_workspaces);
|
|
433
|
+
END IF;
|
|
434
|
+
END IF;
|
|
435
|
+
|
|
436
|
+
UPDATE %1$I.sandbox_leases lease SET
|
|
437
|
+
refcount = counts.total,
|
|
438
|
+
turn_holders = counts.turns,
|
|
439
|
+
viewer_holders = counts.viewers,
|
|
440
|
+
liveness = CASE
|
|
441
|
+
WHEN lease.liveness = 'warm'
|
|
442
|
+
AND counts.total = 0
|
|
443
|
+
AND counts.turns = 0
|
|
444
|
+
AND (
|
|
445
|
+
lease.reaper_hold_id IS NULL
|
|
446
|
+
OR lease.reaper_hold_until <= pg_catalog.now()
|
|
447
|
+
)
|
|
448
|
+
THEN 'draining' ELSE lease.liveness END,
|
|
449
|
+
expires_at = CASE
|
|
450
|
+
WHEN lease.liveness = 'warm'
|
|
451
|
+
AND counts.total = 0
|
|
452
|
+
AND counts.turns = 0
|
|
453
|
+
AND (
|
|
454
|
+
lease.reaper_hold_id IS NULL
|
|
455
|
+
OR lease.reaper_hold_until <= pg_catalog.now()
|
|
456
|
+
)
|
|
457
|
+
THEN CASE
|
|
458
|
+
WHEN lease.rotation_requested_at IS NOT NULL
|
|
459
|
+
OR lease.archive_capture_id IS NOT NULL
|
|
460
|
+
THEN pg_catalog.now() - interval '1 millisecond'
|
|
461
|
+
ELSE pg_catalog.now()
|
|
462
|
+
+ pg_catalog.make_interval(secs => p_idle_grace_ms / 1000.0)
|
|
463
|
+
END
|
|
464
|
+
ELSE lease.expires_at END,
|
|
465
|
+
updated_at = pg_catalog.now()
|
|
466
|
+
FROM (
|
|
467
|
+
SELECT candidate.id,
|
|
468
|
+
pg_catalog.count(holder.id)::int AS total,
|
|
469
|
+
pg_catalog.count(holder.id)
|
|
470
|
+
FILTER (WHERE holder.kind = 'turn')::int AS turns,
|
|
471
|
+
pg_catalog.count(holder.id)
|
|
472
|
+
FILTER (WHERE holder.kind = 'viewer')::int AS viewers
|
|
473
|
+
FROM pg_catalog.unnest(locked_ids) candidate(id)
|
|
474
|
+
LEFT JOIN %1$I.sandbox_lease_holders holder
|
|
475
|
+
ON holder.lease_id = candidate.id
|
|
476
|
+
GROUP BY candidate.id
|
|
477
|
+
) counts
|
|
478
|
+
WHERE lease.id = counts.id;
|
|
479
|
+
|
|
480
|
+
UPDATE %1$I.sandbox_leases lease SET
|
|
481
|
+
liveness = 'cold',
|
|
482
|
+
instance_id = null,
|
|
483
|
+
lease_epoch = lease.lease_epoch + 1,
|
|
484
|
+
reaper_hold_id = null,
|
|
485
|
+
reaper_hold_until = null,
|
|
486
|
+
reaper_hold_reason = null,
|
|
487
|
+
resume_state = opengeni_private.warming_reset_resume_state_v2(
|
|
488
|
+
lease.backend,
|
|
489
|
+
lease.resume_backend_id,
|
|
490
|
+
lease.resume_state,
|
|
491
|
+
lease.workspace_generation,
|
|
492
|
+
lease.archive_generation,
|
|
493
|
+
pg_catalog.clock_timestamp()
|
|
494
|
+
),
|
|
495
|
+
resume_backend_id = CASE
|
|
496
|
+
WHEN coalesce(
|
|
497
|
+
lease.resume_state #>> '{sessionState,workspaceArchive}', ''
|
|
498
|
+
) <> ''
|
|
499
|
+
OR coalesce(
|
|
500
|
+
lease.resume_state #>> '{sessionState,workspaceArchivePrev}', ''
|
|
501
|
+
) <> ''
|
|
502
|
+
THEN coalesce(lease.resume_backend_id, lease.backend)
|
|
503
|
+
ELSE null END,
|
|
504
|
+
data_plane_url = null,
|
|
505
|
+
terminal_data_plane_url = null,
|
|
506
|
+
provider_created_at = null,
|
|
507
|
+
provider_deadline_at = null,
|
|
508
|
+
rotation_requested_at = null,
|
|
509
|
+
rotation_reason = null,
|
|
510
|
+
updated_at = pg_catalog.now()
|
|
511
|
+
WHERE lease.id = ANY(locked_ids)
|
|
512
|
+
AND lease.liveness = 'warming'
|
|
513
|
+
AND lease.expires_at < pg_catalog.now()
|
|
514
|
+
AND lease.instance_id IS NULL
|
|
515
|
+
AND (
|
|
516
|
+
lease.reaper_hold_id IS NULL
|
|
517
|
+
OR lease.reaper_hold_until <= pg_catalog.now()
|
|
518
|
+
);
|
|
519
|
+
|
|
520
|
+
UPDATE %1$I.sandbox_leases lease SET
|
|
521
|
+
liveness = 'draining',
|
|
522
|
+
refcount = 0,
|
|
523
|
+
turn_holders = 0,
|
|
524
|
+
viewer_holders = 0,
|
|
525
|
+
data_plane_url = null,
|
|
526
|
+
terminal_data_plane_url = null,
|
|
527
|
+
lease_epoch = lease.lease_epoch + 1,
|
|
528
|
+
reaper_hold_id = null,
|
|
529
|
+
reaper_hold_until = null,
|
|
530
|
+
reaper_hold_reason = null,
|
|
531
|
+
expires_at = pg_catalog.now() - interval '1 millisecond',
|
|
532
|
+
updated_at = pg_catalog.now()
|
|
533
|
+
WHERE lease.id = ANY(locked_ids)
|
|
534
|
+
AND lease.liveness = 'warming'
|
|
535
|
+
AND lease.expires_at < pg_catalog.now()
|
|
536
|
+
AND lease.instance_id IS NOT NULL
|
|
537
|
+
AND (
|
|
538
|
+
lease.reaper_hold_id IS NULL
|
|
539
|
+
OR lease.reaper_hold_until <= pg_catalog.now()
|
|
540
|
+
);
|
|
541
|
+
|
|
542
|
+
RETURN QUERY
|
|
543
|
+
SELECT lease.workspace_id, lease.sandbox_group_id,
|
|
544
|
+
lease.instance_id, lease.lease_epoch
|
|
545
|
+
FROM %1$I.sandbox_leases lease
|
|
546
|
+
WHERE lease.id = ANY(locked_ids)
|
|
547
|
+
AND lease.liveness = 'draining'
|
|
548
|
+
AND lease.expires_at < pg_catalog.now()
|
|
549
|
+
AND lease.refcount = 0
|
|
550
|
+
AND (
|
|
551
|
+
lease.reaper_hold_id IS NULL
|
|
552
|
+
OR lease.reaper_hold_until <= pg_catalog.now()
|
|
553
|
+
);
|
|
554
|
+
END;
|
|
555
|
+
$function$;
|
|
556
|
+
$create$, data_schema);
|
|
557
|
+
END
|
|
558
|
+
$interaction_aware_reaper$;
|
|
559
|
+
|
|
560
|
+
REVOKE ALL ON FUNCTION opengeni_private.reap_sandbox_leases(
|
|
561
|
+
bigint, bigint, bigint, bigint
|
|
562
|
+
) FROM PUBLIC;
|
|
563
|
+
|
|
564
|
+
DO $reaper_grant$
|
|
565
|
+
BEGIN
|
|
566
|
+
IF EXISTS (SELECT 1 FROM pg_roles WHERE rolname = 'opengeni_app') THEN
|
|
567
|
+
GRANT EXECUTE ON FUNCTION opengeni_private.reap_sandbox_leases(
|
|
568
|
+
bigint, bigint, bigint, bigint
|
|
569
|
+
) TO opengeni_app;
|
|
570
|
+
END IF;
|
|
571
|
+
END
|
|
572
|
+
$reaper_grant$;
|
|
573
|
+
|
|
574
|
+
RESET statement_timeout;
|
|
575
|
+
RESET lock_timeout;
|