dbos 1.15.0a2__py3-none-any.whl → 1.15.0a3__py3-none-any.whl
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.
Potentially problematic release.
This version of dbos might be problematic. Click here for more details.
- dbos/_app_db.py +26 -14
- dbos/_client.py +3 -0
- dbos/_dbos.py +4 -0
- dbos/_dbos_config.py +10 -1
- dbos/_migration.py +46 -35
- dbos/_schemas/system_database.py +17 -0
- dbos/_sys_db.py +2 -0
- dbos/_sys_db_postgres.py +8 -8
- dbos/_sys_db_sqlite.py +1 -6
- dbos/cli/cli.py +79 -2
- dbos/cli/migration.py +22 -18
- {dbos-1.15.0a2.dist-info → dbos-1.15.0a3.dist-info}/METADATA +1 -1
- {dbos-1.15.0a2.dist-info → dbos-1.15.0a3.dist-info}/RECORD +16 -16
- {dbos-1.15.0a2.dist-info → dbos-1.15.0a3.dist-info}/WHEEL +0 -0
- {dbos-1.15.0a2.dist-info → dbos-1.15.0a3.dist-info}/entry_points.txt +0 -0
- {dbos-1.15.0a2.dist-info → dbos-1.15.0a3.dist-info}/licenses/LICENSE +0 -0
dbos/_app_db.py
CHANGED
|
@@ -241,6 +241,7 @@ class ApplicationDatabase(ABC):
|
|
|
241
241
|
def create(
|
|
242
242
|
database_url: str,
|
|
243
243
|
engine_kwargs: Dict[str, Any],
|
|
244
|
+
schema: Optional[str],
|
|
244
245
|
debug_mode: bool = False,
|
|
245
246
|
) -> "ApplicationDatabase":
|
|
246
247
|
"""Factory method to create the appropriate ApplicationDatabase implementation based on URL."""
|
|
@@ -256,12 +257,32 @@ class ApplicationDatabase(ABC):
|
|
|
256
257
|
database_url=database_url,
|
|
257
258
|
engine_kwargs=engine_kwargs,
|
|
258
259
|
debug_mode=debug_mode,
|
|
260
|
+
schema=schema,
|
|
259
261
|
)
|
|
260
262
|
|
|
261
263
|
|
|
262
264
|
class PostgresApplicationDatabase(ApplicationDatabase):
|
|
263
265
|
"""PostgreSQL-specific implementation of ApplicationDatabase."""
|
|
264
266
|
|
|
267
|
+
def __init__(
|
|
268
|
+
self,
|
|
269
|
+
*,
|
|
270
|
+
database_url: str,
|
|
271
|
+
engine_kwargs: Dict[str, Any],
|
|
272
|
+
schema: Optional[str],
|
|
273
|
+
debug_mode: bool = False,
|
|
274
|
+
):
|
|
275
|
+
super().__init__(
|
|
276
|
+
database_url=database_url,
|
|
277
|
+
engine_kwargs=engine_kwargs,
|
|
278
|
+
debug_mode=debug_mode,
|
|
279
|
+
)
|
|
280
|
+
if schema is None:
|
|
281
|
+
self.schema = "dbos"
|
|
282
|
+
else:
|
|
283
|
+
self.schema = schema
|
|
284
|
+
ApplicationSchema.transaction_outputs.schema = schema
|
|
285
|
+
|
|
265
286
|
def _create_engine(
|
|
266
287
|
self, database_url: str, engine_kwargs: Dict[str, Any]
|
|
267
288
|
) -> sa.Engine:
|
|
@@ -271,9 +292,6 @@ class PostgresApplicationDatabase(ApplicationDatabase):
|
|
|
271
292
|
if engine_kwargs is None:
|
|
272
293
|
engine_kwargs = {}
|
|
273
294
|
|
|
274
|
-
# TODO: Make the schema dynamic so this isn't needed
|
|
275
|
-
ApplicationSchema.transaction_outputs.schema = "dbos"
|
|
276
|
-
|
|
277
295
|
return sa.create_engine(
|
|
278
296
|
app_db_url,
|
|
279
297
|
**engine_kwargs,
|
|
@@ -307,24 +325,18 @@ class PostgresApplicationDatabase(ApplicationDatabase):
|
|
|
307
325
|
sa.text(
|
|
308
326
|
"SELECT 1 FROM information_schema.schemata WHERE schema_name = :schema_name"
|
|
309
327
|
),
|
|
310
|
-
parameters={"schema_name":
|
|
328
|
+
parameters={"schema_name": self.schema},
|
|
311
329
|
).scalar()
|
|
312
330
|
|
|
313
331
|
if not schema_exists:
|
|
314
|
-
schema_creation_query = sa.text(
|
|
315
|
-
f"CREATE SCHEMA {ApplicationSchema.schema}"
|
|
316
|
-
)
|
|
332
|
+
schema_creation_query = sa.text(f'CREATE SCHEMA "{self.schema}"')
|
|
317
333
|
conn.execute(schema_creation_query)
|
|
318
334
|
|
|
319
335
|
inspector = inspect(self.engine)
|
|
320
|
-
if not inspector.has_table(
|
|
321
|
-
"transaction_outputs", schema=ApplicationSchema.schema
|
|
322
|
-
):
|
|
336
|
+
if not inspector.has_table("transaction_outputs", schema=self.schema):
|
|
323
337
|
ApplicationSchema.metadata_obj.create_all(self.engine)
|
|
324
338
|
else:
|
|
325
|
-
columns = inspector.get_columns(
|
|
326
|
-
"transaction_outputs", schema=ApplicationSchema.schema
|
|
327
|
-
)
|
|
339
|
+
columns = inspector.get_columns("transaction_outputs", schema=self.schema)
|
|
328
340
|
column_names = [col["name"] for col in columns]
|
|
329
341
|
|
|
330
342
|
if "function_name" not in column_names:
|
|
@@ -333,7 +345,7 @@ class PostgresApplicationDatabase(ApplicationDatabase):
|
|
|
333
345
|
conn.execute(
|
|
334
346
|
text(
|
|
335
347
|
f"""
|
|
336
|
-
ALTER TABLE {
|
|
348
|
+
ALTER TABLE \"{self.schema}\".transaction_outputs
|
|
337
349
|
ADD COLUMN function_name TEXT NOT NULL DEFAULT '';
|
|
338
350
|
"""
|
|
339
351
|
)
|
dbos/_client.py
CHANGED
|
@@ -123,6 +123,7 @@ class DBOSClient:
|
|
|
123
123
|
*,
|
|
124
124
|
system_database_url: Optional[str] = None,
|
|
125
125
|
application_database_url: Optional[str] = None,
|
|
126
|
+
dbos_system_schema: Optional[str] = "dbos",
|
|
126
127
|
system_database: Optional[str] = None, # DEPRECATED
|
|
127
128
|
):
|
|
128
129
|
application_database_url = (
|
|
@@ -146,6 +147,7 @@ class DBOSClient:
|
|
|
146
147
|
"max_overflow": 0,
|
|
147
148
|
"pool_size": 2,
|
|
148
149
|
},
|
|
150
|
+
schema=dbos_system_schema,
|
|
149
151
|
)
|
|
150
152
|
self._sys_db.check_connection()
|
|
151
153
|
if application_database_url:
|
|
@@ -156,6 +158,7 @@ class DBOSClient:
|
|
|
156
158
|
"max_overflow": 0,
|
|
157
159
|
"pool_size": 2,
|
|
158
160
|
},
|
|
161
|
+
schema=dbos_system_schema,
|
|
159
162
|
)
|
|
160
163
|
|
|
161
164
|
def destroy(self) -> None:
|
dbos/_dbos.py
CHANGED
|
@@ -444,10 +444,13 @@ class DBOS:
|
|
|
444
444
|
self._executor_field = ThreadPoolExecutor(max_workers=sys.maxsize)
|
|
445
445
|
self._background_event_loop.start()
|
|
446
446
|
assert self._config["database"]["sys_db_engine_kwargs"] is not None
|
|
447
|
+
# Get the schema configuration, use "dbos" as default
|
|
448
|
+
schema = self._config.get("dbos_system_schema", "dbos")
|
|
447
449
|
self._sys_db_field = SystemDatabase.create(
|
|
448
450
|
system_database_url=get_system_database_url(self._config),
|
|
449
451
|
engine_kwargs=self._config["database"]["sys_db_engine_kwargs"],
|
|
450
452
|
debug_mode=debug_mode,
|
|
453
|
+
schema=schema,
|
|
451
454
|
)
|
|
452
455
|
assert self._config["database"]["db_engine_kwargs"] is not None
|
|
453
456
|
if self._config["database_url"]:
|
|
@@ -455,6 +458,7 @@ class DBOS:
|
|
|
455
458
|
database_url=self._config["database_url"],
|
|
456
459
|
engine_kwargs=self._config["database"]["db_engine_kwargs"],
|
|
457
460
|
debug_mode=debug_mode,
|
|
461
|
+
schema=schema,
|
|
458
462
|
)
|
|
459
463
|
|
|
460
464
|
if debug_mode:
|
dbos/_dbos_config.py
CHANGED
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
import json
|
|
2
1
|
import os
|
|
3
2
|
import re
|
|
4
3
|
from importlib import resources
|
|
@@ -34,6 +33,7 @@ class DBOSConfig(TypedDict, total=False):
|
|
|
34
33
|
otlp_attributes (dict[str, str]): A set of custom attributes to apply OTLP-exported logs and traces
|
|
35
34
|
application_version (str): Application version
|
|
36
35
|
executor_id (str): Executor ID, used to identify the application instance in distributed environments
|
|
36
|
+
dbos_system_schema (str): Schema name for DBOS system tables. Defaults to "dbos".
|
|
37
37
|
enable_otlp (bool): If True, enable built-in DBOS OTLP tracing and logging.
|
|
38
38
|
"""
|
|
39
39
|
|
|
@@ -52,6 +52,7 @@ class DBOSConfig(TypedDict, total=False):
|
|
|
52
52
|
otlp_attributes: Optional[dict[str, str]]
|
|
53
53
|
application_version: Optional[str]
|
|
54
54
|
executor_id: Optional[str]
|
|
55
|
+
dbos_system_schema: Optional[str]
|
|
55
56
|
enable_otlp: Optional[bool]
|
|
56
57
|
|
|
57
58
|
|
|
@@ -70,6 +71,7 @@ class DatabaseConfig(TypedDict, total=False):
|
|
|
70
71
|
sys_db_pool_size (int): System database pool size
|
|
71
72
|
db_engine_kwargs (Dict[str, Any]): SQLAlchemy engine kwargs
|
|
72
73
|
migrate (List[str]): Migration commands to run on startup
|
|
74
|
+
dbos_system_schema (str): Schema name for DBOS system tables. Defaults to "dbos".
|
|
73
75
|
"""
|
|
74
76
|
|
|
75
77
|
sys_db_name: Optional[str]
|
|
@@ -113,6 +115,7 @@ class ConfigFile(TypedDict, total=False):
|
|
|
113
115
|
system_database_url (str): System database URL
|
|
114
116
|
telemetry (TelemetryConfig): Configuration for tracing / logging
|
|
115
117
|
env (Dict[str,str]): Environment variables
|
|
118
|
+
dbos_system_schema (str): Schema name for DBOS system tables. Defaults to "dbos".
|
|
116
119
|
|
|
117
120
|
"""
|
|
118
121
|
|
|
@@ -123,6 +126,7 @@ class ConfigFile(TypedDict, total=False):
|
|
|
123
126
|
system_database_url: Optional[str]
|
|
124
127
|
telemetry: Optional[TelemetryConfig]
|
|
125
128
|
env: Dict[str, str]
|
|
129
|
+
dbos_system_schema: Optional[str]
|
|
126
130
|
|
|
127
131
|
|
|
128
132
|
def translate_dbos_config_to_config_file(config: DBOSConfig) -> ConfigFile:
|
|
@@ -153,6 +157,9 @@ def translate_dbos_config_to_config_file(config: DBOSConfig) -> ConfigFile:
|
|
|
153
157
|
if "system_database_url" in config:
|
|
154
158
|
translated_config["system_database_url"] = config.get("system_database_url")
|
|
155
159
|
|
|
160
|
+
if "dbos_system_schema" in config:
|
|
161
|
+
translated_config["dbos_system_schema"] = config.get("dbos_system_schema")
|
|
162
|
+
|
|
156
163
|
# Runtime config
|
|
157
164
|
translated_config["runtimeConfig"] = {"run_admin_server": True}
|
|
158
165
|
if "admin_port" in config:
|
|
@@ -546,6 +553,8 @@ def overwrite_config(provided_config: ConfigFile) -> ConfigFile:
|
|
|
546
553
|
"DBOS_SYSTEM_DATABASE_URL environment variable is not set. This is required to connect to the database."
|
|
547
554
|
)
|
|
548
555
|
provided_config["system_database_url"] = system_db_url
|
|
556
|
+
# Always use the "dbos" schema when deploying to DBOS Cloud
|
|
557
|
+
provided_config["dbos_system_schema"] = "dbos"
|
|
549
558
|
|
|
550
559
|
# Telemetry config
|
|
551
560
|
if "telemetry" not in provided_config or provided_config["telemetry"] is None:
|
dbos/_migration.py
CHANGED
|
@@ -5,7 +5,7 @@ import sqlalchemy as sa
|
|
|
5
5
|
from ._logger import dbos_logger
|
|
6
6
|
|
|
7
7
|
|
|
8
|
-
def ensure_dbos_schema(engine: sa.Engine) -> None:
|
|
8
|
+
def ensure_dbos_schema(engine: sa.Engine, schema: str) -> None:
|
|
9
9
|
"""
|
|
10
10
|
True if using DBOS migrations (DBOS schema and migrations table already exist or were created)
|
|
11
11
|
False if using Alembic migrations (DBOS schema exists, but dbos_migrations table doesn't)
|
|
@@ -14,41 +14,46 @@ def ensure_dbos_schema(engine: sa.Engine) -> None:
|
|
|
14
14
|
# Check if dbos schema exists
|
|
15
15
|
schema_result = conn.execute(
|
|
16
16
|
sa.text(
|
|
17
|
-
"SELECT schema_name FROM information_schema.schemata WHERE schema_name =
|
|
18
|
-
)
|
|
17
|
+
"SELECT schema_name FROM information_schema.schemata WHERE schema_name = :schema"
|
|
18
|
+
),
|
|
19
|
+
{"schema": schema},
|
|
19
20
|
)
|
|
20
21
|
schema_exists = schema_result.fetchone() is not None
|
|
21
22
|
|
|
22
23
|
# Create schema if it doesn't exist
|
|
23
24
|
if not schema_exists:
|
|
24
|
-
conn.execute(sa.text(
|
|
25
|
+
conn.execute(sa.text(f'CREATE SCHEMA "{schema}"'))
|
|
25
26
|
|
|
26
27
|
# Check if dbos_migrations table exists
|
|
27
28
|
table_result = conn.execute(
|
|
28
29
|
sa.text(
|
|
29
|
-
"SELECT table_name FROM information_schema.tables WHERE table_schema =
|
|
30
|
-
)
|
|
30
|
+
"SELECT table_name FROM information_schema.tables WHERE table_schema = :schema AND table_name = 'dbos_migrations'"
|
|
31
|
+
),
|
|
32
|
+
{"schema": schema},
|
|
31
33
|
)
|
|
32
34
|
table_exists = table_result.fetchone() is not None
|
|
33
35
|
|
|
34
36
|
if not table_exists:
|
|
35
37
|
conn.execute(
|
|
36
38
|
sa.text(
|
|
37
|
-
|
|
39
|
+
f'CREATE TABLE "{schema}".dbos_migrations (version BIGINT NOT NULL PRIMARY KEY)'
|
|
38
40
|
)
|
|
39
41
|
)
|
|
40
42
|
|
|
41
43
|
|
|
42
|
-
def run_dbos_migrations(engine: sa.Engine) -> None:
|
|
44
|
+
def run_dbos_migrations(engine: sa.Engine, schema: str) -> None:
|
|
43
45
|
"""Run DBOS-managed migrations by executing each SQL command in dbos_migrations."""
|
|
44
46
|
with engine.begin() as conn:
|
|
45
47
|
# Get current migration version
|
|
46
|
-
result = conn.execute(
|
|
48
|
+
result = conn.execute(
|
|
49
|
+
sa.text(f'SELECT version FROM "{schema}".dbos_migrations')
|
|
50
|
+
)
|
|
47
51
|
current_version = result.fetchone()
|
|
48
52
|
last_applied = current_version[0] if current_version else 0
|
|
49
53
|
|
|
50
54
|
# Apply migrations starting from the next version
|
|
51
|
-
|
|
55
|
+
migrations = get_dbos_migrations(schema)
|
|
56
|
+
for i, migration_sql in enumerate(migrations, 1):
|
|
52
57
|
if i <= last_applied:
|
|
53
58
|
continue
|
|
54
59
|
|
|
@@ -60,23 +65,26 @@ def run_dbos_migrations(engine: sa.Engine) -> None:
|
|
|
60
65
|
if last_applied == 0:
|
|
61
66
|
conn.execute(
|
|
62
67
|
sa.text(
|
|
63
|
-
|
|
68
|
+
f'INSERT INTO "{schema}".dbos_migrations (version) VALUES (:version)'
|
|
64
69
|
),
|
|
65
70
|
{"version": i},
|
|
66
71
|
)
|
|
67
72
|
else:
|
|
68
73
|
conn.execute(
|
|
69
|
-
sa.text(
|
|
74
|
+
sa.text(
|
|
75
|
+
f'UPDATE "{schema}".dbos_migrations SET version = :version'
|
|
76
|
+
),
|
|
70
77
|
{"version": i},
|
|
71
78
|
)
|
|
72
79
|
last_applied = i
|
|
73
80
|
|
|
74
81
|
|
|
75
|
-
|
|
82
|
+
def get_dbos_migration_one(schema: str) -> str:
|
|
83
|
+
return f"""
|
|
76
84
|
-- Enable uuid extension for generating UUIDs
|
|
77
85
|
CREATE EXTENSION IF NOT EXISTS "uuid-ossp";
|
|
78
86
|
|
|
79
|
-
CREATE TABLE
|
|
87
|
+
CREATE TABLE \"{schema}\".workflow_status (
|
|
80
88
|
workflow_uuid TEXT PRIMARY KEY,
|
|
81
89
|
status TEXT,
|
|
82
90
|
name TEXT,
|
|
@@ -103,15 +111,15 @@ CREATE TABLE dbos.workflow_status (
|
|
|
103
111
|
priority INTEGER NOT NULL DEFAULT 0
|
|
104
112
|
);
|
|
105
113
|
|
|
106
|
-
CREATE INDEX workflow_status_created_at_index ON
|
|
107
|
-
CREATE INDEX workflow_status_executor_id_index ON
|
|
108
|
-
CREATE INDEX workflow_status_status_index ON
|
|
114
|
+
CREATE INDEX workflow_status_created_at_index ON \"{schema}\".workflow_status (created_at);
|
|
115
|
+
CREATE INDEX workflow_status_executor_id_index ON \"{schema}\".workflow_status (executor_id);
|
|
116
|
+
CREATE INDEX workflow_status_status_index ON \"{schema}\".workflow_status (status);
|
|
109
117
|
|
|
110
|
-
ALTER TABLE
|
|
118
|
+
ALTER TABLE \"{schema}\".workflow_status
|
|
111
119
|
ADD CONSTRAINT uq_workflow_status_queue_name_dedup_id
|
|
112
120
|
UNIQUE (queue_name, deduplication_id);
|
|
113
121
|
|
|
114
|
-
CREATE TABLE
|
|
122
|
+
CREATE TABLE \"{schema}\".operation_outputs (
|
|
115
123
|
workflow_uuid TEXT NOT NULL,
|
|
116
124
|
function_id INTEGER NOT NULL,
|
|
117
125
|
function_name TEXT NOT NULL DEFAULT '',
|
|
@@ -119,23 +127,23 @@ CREATE TABLE dbos.operation_outputs (
|
|
|
119
127
|
error TEXT,
|
|
120
128
|
child_workflow_id TEXT,
|
|
121
129
|
PRIMARY KEY (workflow_uuid, function_id),
|
|
122
|
-
FOREIGN KEY (workflow_uuid) REFERENCES
|
|
130
|
+
FOREIGN KEY (workflow_uuid) REFERENCES \"{schema}\".workflow_status(workflow_uuid)
|
|
123
131
|
ON UPDATE CASCADE ON DELETE CASCADE
|
|
124
132
|
);
|
|
125
133
|
|
|
126
|
-
CREATE TABLE
|
|
134
|
+
CREATE TABLE \"{schema}\".notifications (
|
|
127
135
|
destination_uuid TEXT NOT NULL,
|
|
128
136
|
topic TEXT,
|
|
129
137
|
message TEXT NOT NULL,
|
|
130
138
|
created_at_epoch_ms BIGINT NOT NULL DEFAULT (EXTRACT(epoch FROM now()) * 1000::numeric)::bigint,
|
|
131
139
|
message_uuid TEXT NOT NULL DEFAULT gen_random_uuid(), -- Built-in function
|
|
132
|
-
FOREIGN KEY (destination_uuid) REFERENCES
|
|
140
|
+
FOREIGN KEY (destination_uuid) REFERENCES \"{schema}\".workflow_status(workflow_uuid)
|
|
133
141
|
ON UPDATE CASCADE ON DELETE CASCADE
|
|
134
142
|
);
|
|
135
|
-
CREATE INDEX idx_workflow_topic ON
|
|
143
|
+
CREATE INDEX idx_workflow_topic ON \"{schema}\".notifications (destination_uuid, topic);
|
|
136
144
|
|
|
137
145
|
-- Create notification function
|
|
138
|
-
CREATE OR REPLACE FUNCTION
|
|
146
|
+
CREATE OR REPLACE FUNCTION \"{schema}\".notifications_function() RETURNS TRIGGER AS $$
|
|
139
147
|
DECLARE
|
|
140
148
|
payload text := NEW.destination_uuid || '::' || NEW.topic;
|
|
141
149
|
BEGIN
|
|
@@ -146,20 +154,20 @@ $$ LANGUAGE plpgsql;
|
|
|
146
154
|
|
|
147
155
|
-- Create notification trigger
|
|
148
156
|
CREATE TRIGGER dbos_notifications_trigger
|
|
149
|
-
AFTER INSERT ON
|
|
150
|
-
FOR EACH ROW EXECUTE FUNCTION
|
|
157
|
+
AFTER INSERT ON \"{schema}\".notifications
|
|
158
|
+
FOR EACH ROW EXECUTE FUNCTION \"{schema}\".notifications_function();
|
|
151
159
|
|
|
152
|
-
CREATE TABLE
|
|
160
|
+
CREATE TABLE \"{schema}\".workflow_events (
|
|
153
161
|
workflow_uuid TEXT NOT NULL,
|
|
154
162
|
key TEXT NOT NULL,
|
|
155
163
|
value TEXT NOT NULL,
|
|
156
164
|
PRIMARY KEY (workflow_uuid, key),
|
|
157
|
-
FOREIGN KEY (workflow_uuid) REFERENCES
|
|
165
|
+
FOREIGN KEY (workflow_uuid) REFERENCES \"{schema}\".workflow_status(workflow_uuid)
|
|
158
166
|
ON UPDATE CASCADE ON DELETE CASCADE
|
|
159
167
|
);
|
|
160
168
|
|
|
161
169
|
-- Create events function
|
|
162
|
-
CREATE OR REPLACE FUNCTION
|
|
170
|
+
CREATE OR REPLACE FUNCTION \"{schema}\".workflow_events_function() RETURNS TRIGGER AS $$
|
|
163
171
|
DECLARE
|
|
164
172
|
payload text := NEW.workflow_uuid || '::' || NEW.key;
|
|
165
173
|
BEGIN
|
|
@@ -170,20 +178,20 @@ $$ LANGUAGE plpgsql;
|
|
|
170
178
|
|
|
171
179
|
-- Create events trigger
|
|
172
180
|
CREATE TRIGGER dbos_workflow_events_trigger
|
|
173
|
-
AFTER INSERT ON
|
|
174
|
-
FOR EACH ROW EXECUTE FUNCTION
|
|
181
|
+
AFTER INSERT ON \"{schema}\".workflow_events
|
|
182
|
+
FOR EACH ROW EXECUTE FUNCTION \"{schema}\".workflow_events_function();
|
|
175
183
|
|
|
176
|
-
CREATE TABLE
|
|
184
|
+
CREATE TABLE \"{schema}\".streams (
|
|
177
185
|
workflow_uuid TEXT NOT NULL,
|
|
178
186
|
key TEXT NOT NULL,
|
|
179
187
|
value TEXT NOT NULL,
|
|
180
188
|
"offset" INTEGER NOT NULL,
|
|
181
189
|
PRIMARY KEY (workflow_uuid, key, "offset"),
|
|
182
|
-
FOREIGN KEY (workflow_uuid) REFERENCES
|
|
190
|
+
FOREIGN KEY (workflow_uuid) REFERENCES \"{schema}\".workflow_status(workflow_uuid)
|
|
183
191
|
ON UPDATE CASCADE ON DELETE CASCADE
|
|
184
192
|
);
|
|
185
193
|
|
|
186
|
-
CREATE TABLE
|
|
194
|
+
CREATE TABLE \"{schema}\".event_dispatch_kv (
|
|
187
195
|
service_name TEXT NOT NULL,
|
|
188
196
|
workflow_fn_name TEXT NOT NULL,
|
|
189
197
|
key TEXT NOT NULL,
|
|
@@ -195,6 +203,10 @@ CREATE TABLE dbos.event_dispatch_kv (
|
|
|
195
203
|
"""
|
|
196
204
|
|
|
197
205
|
|
|
206
|
+
def get_dbos_migrations(schema: str) -> list[str]:
|
|
207
|
+
return [get_dbos_migration_one(schema)]
|
|
208
|
+
|
|
209
|
+
|
|
198
210
|
def get_sqlite_timestamp_expr() -> str:
|
|
199
211
|
"""Get SQLite timestamp expression with millisecond precision for Python >= 3.12."""
|
|
200
212
|
if sys.version_info >= (3, 12):
|
|
@@ -281,5 +293,4 @@ CREATE TABLE streams (
|
|
|
281
293
|
);
|
|
282
294
|
"""
|
|
283
295
|
|
|
284
|
-
dbos_migrations = [dbos_migration_one]
|
|
285
296
|
sqlite_migrations = [sqlite_migration_one]
|
dbos/_schemas/system_database.py
CHANGED
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
from typing import Optional
|
|
2
|
+
|
|
1
3
|
from sqlalchemy import (
|
|
2
4
|
BigInteger,
|
|
3
5
|
Column,
|
|
@@ -19,6 +21,21 @@ class SystemSchema:
|
|
|
19
21
|
metadata_obj = MetaData(schema="dbos")
|
|
20
22
|
sysdb_suffix = "_dbos_sys"
|
|
21
23
|
|
|
24
|
+
@classmethod
|
|
25
|
+
def set_schema(cls, schema_name: Optional[str]) -> None:
|
|
26
|
+
"""
|
|
27
|
+
Set the schema for all DBOS system tables.
|
|
28
|
+
|
|
29
|
+
Args:
|
|
30
|
+
schema_name: The name of the schema to use for system tables
|
|
31
|
+
"""
|
|
32
|
+
cls.metadata_obj.schema = schema_name
|
|
33
|
+
cls.workflow_status.schema = schema_name
|
|
34
|
+
cls.operation_outputs.schema = schema_name
|
|
35
|
+
cls.notifications.schema = schema_name
|
|
36
|
+
cls.workflow_events.schema = schema_name
|
|
37
|
+
cls.streams.schema = schema_name
|
|
38
|
+
|
|
22
39
|
workflow_status = Table(
|
|
23
40
|
"workflow_status",
|
|
24
41
|
metadata_obj,
|
dbos/_sys_db.py
CHANGED
|
@@ -1443,6 +1443,7 @@ class SystemDatabase(ABC):
|
|
|
1443
1443
|
def create(
|
|
1444
1444
|
system_database_url: str,
|
|
1445
1445
|
engine_kwargs: Dict[str, Any],
|
|
1446
|
+
schema: Optional[str],
|
|
1446
1447
|
debug_mode: bool = False,
|
|
1447
1448
|
) -> "SystemDatabase":
|
|
1448
1449
|
"""Factory method to create the appropriate SystemDatabase implementation based on URL."""
|
|
@@ -1461,6 +1462,7 @@ class SystemDatabase(ABC):
|
|
|
1461
1462
|
system_database_url=system_database_url,
|
|
1462
1463
|
engine_kwargs=engine_kwargs,
|
|
1463
1464
|
debug_mode=debug_mode,
|
|
1465
|
+
schema=schema,
|
|
1464
1466
|
)
|
|
1465
1467
|
|
|
1466
1468
|
@db_retry()
|
dbos/_sys_db_postgres.py
CHANGED
|
@@ -20,6 +20,7 @@ class PostgresSystemDatabase(SystemDatabase):
|
|
|
20
20
|
*,
|
|
21
21
|
system_database_url: str,
|
|
22
22
|
engine_kwargs: Dict[str, Any],
|
|
23
|
+
schema: Optional[str],
|
|
23
24
|
debug_mode: bool = False,
|
|
24
25
|
):
|
|
25
26
|
super().__init__(
|
|
@@ -27,17 +28,16 @@ class PostgresSystemDatabase(SystemDatabase):
|
|
|
27
28
|
engine_kwargs=engine_kwargs,
|
|
28
29
|
debug_mode=debug_mode,
|
|
29
30
|
)
|
|
31
|
+
if schema is None:
|
|
32
|
+
self.schema = "dbos"
|
|
33
|
+
else:
|
|
34
|
+
self.schema = schema
|
|
35
|
+
SystemSchema.set_schema(self.schema)
|
|
30
36
|
self.notification_conn: Optional[psycopg.connection.Connection] = None
|
|
31
37
|
|
|
32
38
|
def _create_engine(
|
|
33
39
|
self, system_database_url: str, engine_kwargs: Dict[str, Any]
|
|
34
40
|
) -> sa.Engine:
|
|
35
|
-
# TODO: Make the schema dynamic so this isn't needed
|
|
36
|
-
SystemSchema.workflow_status.schema = "dbos"
|
|
37
|
-
SystemSchema.operation_outputs.schema = "dbos"
|
|
38
|
-
SystemSchema.notifications.schema = "dbos"
|
|
39
|
-
SystemSchema.workflow_events.schema = "dbos"
|
|
40
|
-
SystemSchema.streams.schema = "dbos"
|
|
41
41
|
url = sa.make_url(system_database_url).set(drivername="postgresql+psycopg")
|
|
42
42
|
return sa.create_engine(url, **engine_kwargs)
|
|
43
43
|
|
|
@@ -62,8 +62,8 @@ class PostgresSystemDatabase(SystemDatabase):
|
|
|
62
62
|
conn.execute(sa.text(f"CREATE DATABASE {sysdb_name}"))
|
|
63
63
|
engine.dispose()
|
|
64
64
|
|
|
65
|
-
ensure_dbos_schema(self.engine)
|
|
66
|
-
run_dbos_migrations(self.engine)
|
|
65
|
+
ensure_dbos_schema(self.engine, self.schema)
|
|
66
|
+
run_dbos_migrations(self.engine, self.schema)
|
|
67
67
|
|
|
68
68
|
def _cleanup_connections(self) -> None:
|
|
69
69
|
"""Clean up PostgreSQL-specific connections."""
|
dbos/_sys_db_sqlite.py
CHANGED
|
@@ -19,12 +19,7 @@ class SQLiteSystemDatabase(SystemDatabase):
|
|
|
19
19
|
self, system_database_url: str, engine_kwargs: Dict[str, Any]
|
|
20
20
|
) -> sa.Engine:
|
|
21
21
|
"""Create a SQLite engine."""
|
|
22
|
-
|
|
23
|
-
SystemSchema.workflow_status.schema = None
|
|
24
|
-
SystemSchema.operation_outputs.schema = None
|
|
25
|
-
SystemSchema.notifications.schema = None
|
|
26
|
-
SystemSchema.workflow_events.schema = None
|
|
27
|
-
SystemSchema.streams.schema = None
|
|
22
|
+
SystemSchema.set_schema(None)
|
|
28
23
|
return sa.create_engine(system_database_url)
|
|
29
24
|
|
|
30
25
|
def run_migrations(self) -> None:
|
dbos/cli/cli.py
CHANGED
|
@@ -287,6 +287,13 @@ def migrate(
|
|
|
287
287
|
help="The role with which you will run your DBOS application",
|
|
288
288
|
),
|
|
289
289
|
] = None,
|
|
290
|
+
schema: Annotated[
|
|
291
|
+
typing.Optional[str],
|
|
292
|
+
typer.Option(
|
|
293
|
+
"--schema",
|
|
294
|
+
help='Schema name for DBOS system tables. Defaults to "dbos".',
|
|
295
|
+
),
|
|
296
|
+
] = "dbos",
|
|
290
297
|
) -> None:
|
|
291
298
|
system_database_url, application_database_url = _get_db_url(
|
|
292
299
|
system_database_url=system_database_url,
|
|
@@ -297,21 +304,27 @@ def migrate(
|
|
|
297
304
|
if application_database_url:
|
|
298
305
|
typer.echo(f"Application database: {sa.make_url(application_database_url)}")
|
|
299
306
|
typer.echo(f"System database: {sa.make_url(system_database_url)}")
|
|
307
|
+
if schema is None:
|
|
308
|
+
schema = "dbos"
|
|
309
|
+
typer.echo(f"DBOS system schema: {schema}")
|
|
300
310
|
|
|
301
311
|
# First, run DBOS migrations on the system database and the application database
|
|
302
312
|
migrate_dbos_databases(
|
|
303
313
|
app_database_url=application_database_url,
|
|
304
314
|
system_database_url=system_database_url,
|
|
315
|
+
schema=schema,
|
|
305
316
|
)
|
|
306
317
|
|
|
307
318
|
# Next, assign permissions on the DBOS schema to the application role, if any
|
|
308
319
|
if application_role:
|
|
309
320
|
if application_database_url:
|
|
310
321
|
grant_dbos_schema_permissions(
|
|
311
|
-
database_url=application_database_url,
|
|
322
|
+
database_url=application_database_url,
|
|
323
|
+
role_name=application_role,
|
|
324
|
+
schema=schema,
|
|
312
325
|
)
|
|
313
326
|
grant_dbos_schema_permissions(
|
|
314
|
-
database_url=system_database_url, role_name=application_role
|
|
327
|
+
database_url=system_database_url, role_name=application_role, schema=schema
|
|
315
328
|
)
|
|
316
329
|
|
|
317
330
|
# Next, run any custom migration commands specified in the configuration
|
|
@@ -477,6 +490,13 @@ def list(
|
|
|
477
490
|
help="Offset for pagination",
|
|
478
491
|
),
|
|
479
492
|
] = None,
|
|
493
|
+
schema: Annotated[
|
|
494
|
+
typing.Optional[str],
|
|
495
|
+
typer.Option(
|
|
496
|
+
"--schema",
|
|
497
|
+
help='Schema name for DBOS system tables. Defaults to "dbos".',
|
|
498
|
+
),
|
|
499
|
+
] = "dbos",
|
|
480
500
|
) -> None:
|
|
481
501
|
system_database_url, application_database_url = _get_db_url(
|
|
482
502
|
system_database_url=system_database_url,
|
|
@@ -485,6 +505,7 @@ def list(
|
|
|
485
505
|
client = DBOSClient(
|
|
486
506
|
application_database_url=application_database_url,
|
|
487
507
|
system_database_url=system_database_url,
|
|
508
|
+
dbos_system_schema=schema,
|
|
488
509
|
)
|
|
489
510
|
workflows = client.list_workflows(
|
|
490
511
|
limit=limit,
|
|
@@ -519,6 +540,13 @@ def get(
|
|
|
519
540
|
help="Your DBOS system database URL",
|
|
520
541
|
),
|
|
521
542
|
] = None,
|
|
543
|
+
schema: Annotated[
|
|
544
|
+
typing.Optional[str],
|
|
545
|
+
typer.Option(
|
|
546
|
+
"--schema",
|
|
547
|
+
help='Schema name for DBOS system tables. Defaults to "dbos".',
|
|
548
|
+
),
|
|
549
|
+
] = "dbos",
|
|
522
550
|
) -> None:
|
|
523
551
|
system_database_url, application_database_url = _get_db_url(
|
|
524
552
|
system_database_url=system_database_url,
|
|
@@ -527,6 +555,7 @@ def get(
|
|
|
527
555
|
client = DBOSClient(
|
|
528
556
|
application_database_url=application_database_url,
|
|
529
557
|
system_database_url=system_database_url,
|
|
558
|
+
dbos_system_schema=schema,
|
|
530
559
|
)
|
|
531
560
|
status = client.retrieve_workflow(workflow_id=workflow_id).get_status()
|
|
532
561
|
print(json.dumps(status.__dict__, cls=DefaultEncoder))
|
|
@@ -551,6 +580,13 @@ def steps(
|
|
|
551
580
|
help="Your DBOS system database URL",
|
|
552
581
|
),
|
|
553
582
|
] = None,
|
|
583
|
+
schema: Annotated[
|
|
584
|
+
typing.Optional[str],
|
|
585
|
+
typer.Option(
|
|
586
|
+
"--schema",
|
|
587
|
+
help='Schema name for DBOS system tables. Defaults to "dbos".',
|
|
588
|
+
),
|
|
589
|
+
] = "dbos",
|
|
554
590
|
) -> None:
|
|
555
591
|
system_database_url, application_database_url = _get_db_url(
|
|
556
592
|
system_database_url=system_database_url,
|
|
@@ -559,6 +595,7 @@ def steps(
|
|
|
559
595
|
client = DBOSClient(
|
|
560
596
|
application_database_url=application_database_url,
|
|
561
597
|
system_database_url=system_database_url,
|
|
598
|
+
dbos_system_schema=schema,
|
|
562
599
|
)
|
|
563
600
|
steps = client.list_workflow_steps(workflow_id=workflow_id)
|
|
564
601
|
print(json.dumps(steps, cls=DefaultEncoder))
|
|
@@ -585,6 +622,13 @@ def cancel(
|
|
|
585
622
|
help="Your DBOS system database URL",
|
|
586
623
|
),
|
|
587
624
|
] = None,
|
|
625
|
+
schema: Annotated[
|
|
626
|
+
typing.Optional[str],
|
|
627
|
+
typer.Option(
|
|
628
|
+
"--schema",
|
|
629
|
+
help='Schema name for DBOS system tables. Defaults to "dbos".',
|
|
630
|
+
),
|
|
631
|
+
] = "dbos",
|
|
588
632
|
) -> None:
|
|
589
633
|
system_database_url, application_database_url = _get_db_url(
|
|
590
634
|
system_database_url=system_database_url,
|
|
@@ -593,6 +637,7 @@ def cancel(
|
|
|
593
637
|
client = DBOSClient(
|
|
594
638
|
application_database_url=application_database_url,
|
|
595
639
|
system_database_url=system_database_url,
|
|
640
|
+
dbos_system_schema=schema,
|
|
596
641
|
)
|
|
597
642
|
client.cancel_workflow(workflow_id=workflow_id)
|
|
598
643
|
|
|
@@ -616,6 +661,13 @@ def resume(
|
|
|
616
661
|
help="Your DBOS system database URL",
|
|
617
662
|
),
|
|
618
663
|
] = None,
|
|
664
|
+
schema: Annotated[
|
|
665
|
+
typing.Optional[str],
|
|
666
|
+
typer.Option(
|
|
667
|
+
"--schema",
|
|
668
|
+
help='Schema name for DBOS system tables. Defaults to "dbos".',
|
|
669
|
+
),
|
|
670
|
+
] = "dbos",
|
|
619
671
|
) -> None:
|
|
620
672
|
system_database_url, application_database_url = _get_db_url(
|
|
621
673
|
system_database_url=system_database_url,
|
|
@@ -624,6 +676,7 @@ def resume(
|
|
|
624
676
|
client = DBOSClient(
|
|
625
677
|
application_database_url=application_database_url,
|
|
626
678
|
system_database_url=system_database_url,
|
|
679
|
+
dbos_system_schema=schema,
|
|
627
680
|
)
|
|
628
681
|
client.resume_workflow(workflow_id=workflow_id)
|
|
629
682
|
|
|
@@ -649,6 +702,13 @@ def restart(
|
|
|
649
702
|
help="Your DBOS system database URL",
|
|
650
703
|
),
|
|
651
704
|
] = None,
|
|
705
|
+
schema: Annotated[
|
|
706
|
+
typing.Optional[str],
|
|
707
|
+
typer.Option(
|
|
708
|
+
"--schema",
|
|
709
|
+
help='Schema name for DBOS system tables. Defaults to "dbos".',
|
|
710
|
+
),
|
|
711
|
+
] = "dbos",
|
|
652
712
|
) -> None:
|
|
653
713
|
system_database_url, application_database_url = _get_db_url(
|
|
654
714
|
system_database_url=system_database_url,
|
|
@@ -657,6 +717,7 @@ def restart(
|
|
|
657
717
|
client = DBOSClient(
|
|
658
718
|
application_database_url=application_database_url,
|
|
659
719
|
system_database_url=system_database_url,
|
|
720
|
+
dbos_system_schema=schema,
|
|
660
721
|
)
|
|
661
722
|
status = client.fork_workflow(workflow_id=workflow_id, start_step=1).get_status()
|
|
662
723
|
print(json.dumps(status.__dict__, cls=DefaultEncoder))
|
|
@@ -707,6 +768,13 @@ def fork(
|
|
|
707
768
|
help="Your DBOS system database URL",
|
|
708
769
|
),
|
|
709
770
|
] = None,
|
|
771
|
+
schema: Annotated[
|
|
772
|
+
typing.Optional[str],
|
|
773
|
+
typer.Option(
|
|
774
|
+
"--schema",
|
|
775
|
+
help='Schema name for DBOS system tables. Defaults to "dbos".',
|
|
776
|
+
),
|
|
777
|
+
] = "dbos",
|
|
710
778
|
) -> None:
|
|
711
779
|
system_database_url, application_database_url = _get_db_url(
|
|
712
780
|
system_database_url=system_database_url,
|
|
@@ -715,6 +783,7 @@ def fork(
|
|
|
715
783
|
client = DBOSClient(
|
|
716
784
|
application_database_url=application_database_url,
|
|
717
785
|
system_database_url=system_database_url,
|
|
786
|
+
dbos_system_schema=schema,
|
|
718
787
|
)
|
|
719
788
|
|
|
720
789
|
if forked_workflow_id is not None:
|
|
@@ -811,6 +880,13 @@ def list_queue(
|
|
|
811
880
|
help="Offset for pagination",
|
|
812
881
|
),
|
|
813
882
|
] = None,
|
|
883
|
+
schema: Annotated[
|
|
884
|
+
typing.Optional[str],
|
|
885
|
+
typer.Option(
|
|
886
|
+
"--schema",
|
|
887
|
+
help='Schema name for DBOS system tables. Defaults to "dbos".',
|
|
888
|
+
),
|
|
889
|
+
] = "dbos",
|
|
814
890
|
) -> None:
|
|
815
891
|
system_database_url, application_database_url = _get_db_url(
|
|
816
892
|
system_database_url=system_database_url,
|
|
@@ -819,6 +895,7 @@ def list_queue(
|
|
|
819
895
|
client = DBOSClient(
|
|
820
896
|
application_database_url=application_database_url,
|
|
821
897
|
system_database_url=system_database_url,
|
|
898
|
+
dbos_system_schema=schema,
|
|
822
899
|
)
|
|
823
900
|
workflows = client.list_queued_workflows(
|
|
824
901
|
limit=limit,
|
dbos/cli/migration.py
CHANGED
|
@@ -8,7 +8,7 @@ from dbos._sys_db import SystemDatabase
|
|
|
8
8
|
|
|
9
9
|
|
|
10
10
|
def migrate_dbos_databases(
|
|
11
|
-
app_database_url: Optional[str], system_database_url: str
|
|
11
|
+
app_database_url: Optional[str], system_database_url: str, schema: str
|
|
12
12
|
) -> None:
|
|
13
13
|
app_db = None
|
|
14
14
|
sys_db = None
|
|
@@ -20,6 +20,7 @@ def migrate_dbos_databases(
|
|
|
20
20
|
"max_overflow": 0,
|
|
21
21
|
"pool_size": 2,
|
|
22
22
|
},
|
|
23
|
+
schema=schema,
|
|
23
24
|
)
|
|
24
25
|
sys_db.run_migrations()
|
|
25
26
|
if app_database_url:
|
|
@@ -30,6 +31,7 @@ def migrate_dbos_databases(
|
|
|
30
31
|
"max_overflow": 0,
|
|
31
32
|
"pool_size": 2,
|
|
32
33
|
},
|
|
34
|
+
schema=schema,
|
|
33
35
|
)
|
|
34
36
|
app_db.run_migrations()
|
|
35
37
|
except Exception as e:
|
|
@@ -42,12 +44,14 @@ def migrate_dbos_databases(
|
|
|
42
44
|
app_db.destroy()
|
|
43
45
|
|
|
44
46
|
|
|
45
|
-
def grant_dbos_schema_permissions(
|
|
47
|
+
def grant_dbos_schema_permissions(
|
|
48
|
+
database_url: str, role_name: str, schema: str
|
|
49
|
+
) -> None:
|
|
46
50
|
"""
|
|
47
|
-
Grant all permissions on all entities in the
|
|
51
|
+
Grant all permissions on all entities in the system schema to the specified role.
|
|
48
52
|
"""
|
|
49
53
|
typer.echo(
|
|
50
|
-
f"Granting permissions for
|
|
54
|
+
f"Granting permissions for the {schema} schema to {role_name} in database {sa.make_url(database_url)}"
|
|
51
55
|
)
|
|
52
56
|
engine = None
|
|
53
57
|
try:
|
|
@@ -57,38 +61,38 @@ def grant_dbos_schema_permissions(database_url: str, role_name: str) -> None:
|
|
|
57
61
|
with engine.connect() as connection:
|
|
58
62
|
connection.execution_options(isolation_level="AUTOCOMMIT")
|
|
59
63
|
|
|
60
|
-
# Grant usage on the
|
|
61
|
-
sql = f'GRANT USAGE ON SCHEMA
|
|
64
|
+
# Grant usage on the system schema
|
|
65
|
+
sql = f'GRANT USAGE ON SCHEMA "{schema}" TO "{role_name}"'
|
|
62
66
|
typer.echo(sql)
|
|
63
67
|
connection.execute(sa.text(sql))
|
|
64
68
|
|
|
65
|
-
# Grant all privileges on all existing tables in
|
|
66
|
-
sql = f'GRANT ALL PRIVILEGES ON ALL TABLES IN SCHEMA
|
|
69
|
+
# Grant all privileges on all existing tables in the system schema (includes views)
|
|
70
|
+
sql = f'GRANT ALL PRIVILEGES ON ALL TABLES IN SCHEMA "{schema}" TO "{role_name}"'
|
|
67
71
|
typer.echo(sql)
|
|
68
72
|
connection.execute(sa.text(sql))
|
|
69
73
|
|
|
70
|
-
# Grant all privileges on all sequences in
|
|
71
|
-
sql =
|
|
72
|
-
f'GRANT ALL PRIVILEGES ON ALL SEQUENCES IN SCHEMA dbos TO "{role_name}"'
|
|
73
|
-
)
|
|
74
|
+
# Grant all privileges on all sequences in the system schema
|
|
75
|
+
sql = f'GRANT ALL PRIVILEGES ON ALL SEQUENCES IN SCHEMA "{schema}" TO "{role_name}"'
|
|
74
76
|
typer.echo(sql)
|
|
75
77
|
connection.execute(sa.text(sql))
|
|
76
78
|
|
|
77
|
-
# Grant execute on all functions and procedures in
|
|
78
|
-
sql =
|
|
79
|
+
# Grant execute on all functions and procedures in the system schema
|
|
80
|
+
sql = (
|
|
81
|
+
f'GRANT EXECUTE ON ALL FUNCTIONS IN SCHEMA "{schema}" TO "{role_name}"'
|
|
82
|
+
)
|
|
79
83
|
typer.echo(sql)
|
|
80
84
|
connection.execute(sa.text(sql))
|
|
81
85
|
|
|
82
|
-
# Grant default privileges for future objects in
|
|
83
|
-
sql = f'ALTER DEFAULT PRIVILEGES IN SCHEMA
|
|
86
|
+
# Grant default privileges for future objects in the system schema
|
|
87
|
+
sql = f'ALTER DEFAULT PRIVILEGES IN SCHEMA "{schema}" GRANT ALL ON TABLES TO "{role_name}"'
|
|
84
88
|
typer.echo(sql)
|
|
85
89
|
connection.execute(sa.text(sql))
|
|
86
90
|
|
|
87
|
-
sql = f'ALTER DEFAULT PRIVILEGES IN SCHEMA
|
|
91
|
+
sql = f'ALTER DEFAULT PRIVILEGES IN SCHEMA "{schema}" GRANT ALL ON SEQUENCES TO "{role_name}"'
|
|
88
92
|
typer.echo(sql)
|
|
89
93
|
connection.execute(sa.text(sql))
|
|
90
94
|
|
|
91
|
-
sql = f'ALTER DEFAULT PRIVILEGES IN SCHEMA
|
|
95
|
+
sql = f'ALTER DEFAULT PRIVILEGES IN SCHEMA "{schema}" GRANT EXECUTE ON FUNCTIONS TO "{role_name}"'
|
|
92
96
|
typer.echo(sql)
|
|
93
97
|
connection.execute(sa.text(sql))
|
|
94
98
|
|
|
@@ -1,20 +1,20 @@
|
|
|
1
|
-
dbos-1.15.
|
|
2
|
-
dbos-1.15.
|
|
3
|
-
dbos-1.15.
|
|
4
|
-
dbos-1.15.
|
|
1
|
+
dbos-1.15.0a3.dist-info/METADATA,sha256=Ft-tggTIl0dxVo3Byd4BKytIRVdvegchZIKPnrcnq0w,13021
|
|
2
|
+
dbos-1.15.0a3.dist-info/WHEEL,sha256=9P2ygRxDrTJz3gsagc0Z96ukrxjr-LFBGOgv3AuKlCA,90
|
|
3
|
+
dbos-1.15.0a3.dist-info/entry_points.txt,sha256=_QOQ3tVfEjtjBlr1jS4sHqHya9lI2aIEIWkz8dqYp14,58
|
|
4
|
+
dbos-1.15.0a3.dist-info/licenses/LICENSE,sha256=VGZit_a5-kdw9WT6fY5jxAWVwGQzgLFyPWrcVVUhVNU,1067
|
|
5
5
|
dbos/__init__.py,sha256=pT4BuNLDCrIQX27vQG8NlfxX6PZRU7r9miq4thJTszU,982
|
|
6
6
|
dbos/__main__.py,sha256=G7Exn-MhGrVJVDbgNlpzhfh8WMX_72t3_oJaFT9Lmt8,653
|
|
7
7
|
dbos/_admin_server.py,sha256=e8ELhcDWqR3_PNobnNgUvLGh5lzZq0yFSF6dvtzoQRI,16267
|
|
8
|
-
dbos/_app_db.py,sha256=
|
|
8
|
+
dbos/_app_db.py,sha256=WJwUdKsTpSZPCIWVeSF5FQNf5y1PF_lJ96tiaCjvck8,16385
|
|
9
9
|
dbos/_classproperty.py,sha256=f0X-_BySzn3yFDRKB2JpCbLYQ9tLwt1XftfshvY7CBs,626
|
|
10
|
-
dbos/_client.py,sha256=
|
|
10
|
+
dbos/_client.py,sha256=Rp1OiT5523QosHB8Qy0xe9eWNx9osZGhfQknO122hj8,18928
|
|
11
11
|
dbos/_conductor/conductor.py,sha256=3E_hL3c9g9yWqKZkvI6KA0-ZzPMPRo06TOzT1esMiek,24114
|
|
12
12
|
dbos/_conductor/protocol.py,sha256=q3rgLxINFtWFigdOONc-4gX4vn66UmMlJQD6Kj8LnL4,7420
|
|
13
13
|
dbos/_context.py,sha256=cJDxVbswTLXKE5MV4Hmg6gpIX3Dd5mBTG-4lmofWP9E,27668
|
|
14
14
|
dbos/_core.py,sha256=13DNN_fpSIs42NquV80XsHV7yKwY_adKP03h_xhXok4,50493
|
|
15
15
|
dbos/_croniter.py,sha256=XHAyUyibs_59sJQfSNWkP7rqQY6_XrlfuuCxk4jYqek,47559
|
|
16
|
-
dbos/_dbos.py,sha256=
|
|
17
|
-
dbos/_dbos_config.py,sha256=
|
|
16
|
+
dbos/_dbos.py,sha256=ReujpyRseUNL_9FQN-uIhSFh6HJnAA2IAcVy6qDdEco,58036
|
|
17
|
+
dbos/_dbos_config.py,sha256=pnFeWZFDsk_94DWDCqm3e-ppTrqBFKQQdD5TvQGZ8-Y,25963
|
|
18
18
|
dbos/_debouncer.py,sha256=VmGq1_ZIQ79fnH14LEhdoqxKWp6rlEwzsUwumwAMgTQ,15095
|
|
19
19
|
dbos/_debug.py,sha256=0MfgNqutCUhI4PEmmra9x7f3DiFE_0nscfUCHdLimEY,1415
|
|
20
20
|
dbos/_docker_pg_helper.py,sha256=xySum4hTA8TVMBODoG19u4cXQAB1vCock-jwM2pnmSI,7791
|
|
@@ -25,7 +25,7 @@ dbos/_flask.py,sha256=Npnakt-a3W5OykONFRkDRnumaDhTQmA0NPdUCGRYKXE,1652
|
|
|
25
25
|
dbos/_kafka.py,sha256=Gm4fHWl7gYb-i5BMvwNwm5Km3z8zQpseqdMgqgFjlGI,4252
|
|
26
26
|
dbos/_kafka_message.py,sha256=NYvOXNG3Qn7bghn1pv3fg4Pbs86ILZGcK4IB-MLUNu0,409
|
|
27
27
|
dbos/_logger.py,sha256=djnCp147QoQ1iG9Bt3Uz8RyGaXGmi6gebccXsrA6Cps,4660
|
|
28
|
-
dbos/_migration.py,sha256=
|
|
28
|
+
dbos/_migration.py,sha256=VAQxZXWQISifW0JpIG78lowV1MTBJ5ZC4P0YIwqxQhM,10013
|
|
29
29
|
dbos/_outcome.py,sha256=7HvosMfEHTh1U5P6xok7kFTGLwa2lPaul0YApb3UnN4,8191
|
|
30
30
|
dbos/_queue.py,sha256=0kJTPwXy3nZ4Epzt-lHky9M9S4L31645drPGFR8fIJY,4854
|
|
31
31
|
dbos/_recovery.py,sha256=K-wlFhdf4yGRm6cUzyhcTjQUS0xp2T5rdNMLiiBErYg,2882
|
|
@@ -34,11 +34,11 @@ dbos/_roles.py,sha256=kCuhhg8XLtrHCgKgm44I0abIRTGHltf88OwjEKAUggk,2317
|
|
|
34
34
|
dbos/_scheduler.py,sha256=CWeGVfl9h51VXfxt80y5Da_5pE8SPty_AYkfpJkkMxQ,2117
|
|
35
35
|
dbos/_schemas/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
36
36
|
dbos/_schemas/application_database.py,sha256=SypAS9l9EsaBHFn9FR8jmnqt01M74d9AF1AMa4m2hhI,1040
|
|
37
|
-
dbos/_schemas/system_database.py,sha256
|
|
37
|
+
dbos/_schemas/system_database.py,sha256=aEkjRQDh9xjdke0d9uFx_20-c9UjQtvuLtHZ24aOypA,5497
|
|
38
38
|
dbos/_serialization.py,sha256=GLgWLtHpvk7nSHyXukVQLE1ASNA3CJBtfF8w6iflBDw,3590
|
|
39
|
-
dbos/_sys_db.py,sha256=
|
|
40
|
-
dbos/_sys_db_postgres.py,sha256=
|
|
41
|
-
dbos/_sys_db_sqlite.py,sha256=
|
|
39
|
+
dbos/_sys_db.py,sha256=Trlbf99KvH8YRthQ3diJQMSi0eDmky7X8dPG1wuv5VI,83098
|
|
40
|
+
dbos/_sys_db_postgres.py,sha256=V3RGj2cXdCZ8xNxiMO-ECfKuHXtGZLVVNtOXtFSVHBw,7215
|
|
41
|
+
dbos/_sys_db_sqlite.py,sha256=lEmJjyUHXo09q1sMpNpasurh4JyrH6DsmYzLjDC5k6Y,7091
|
|
42
42
|
dbos/_templates/dbos-db-starter/README.md,sha256=GhxhBj42wjTt1fWEtwNriHbJuKb66Vzu89G4pxNHw2g,930
|
|
43
43
|
dbos/_templates/dbos-db-starter/__package/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
44
44
|
dbos/_templates/dbos-db-starter/__package/main.py.dbos,sha256=aQnBPSSQpkB8ERfhf7gB7P9tsU6OPKhZscfeh0yiaD8,2702
|
|
@@ -51,9 +51,9 @@ dbos/_utils.py,sha256=ZdoM1MDbHnlJrh31zfhp3iX62bAxK1kyvMwXnltC_84,1779
|
|
|
51
51
|
dbos/_workflow_commands.py,sha256=k-i1bCfNrux43BHLT8wQ-l-MVZX3D6LGZLH7-uuiDRo,4951
|
|
52
52
|
dbos/cli/_github_init.py,sha256=R_94Fnn40CAmPy-zM00lwHi0ndyfv57TmIooADjmag4,3378
|
|
53
53
|
dbos/cli/_template_init.py,sha256=AltKk256VocgvxLpuTxpjJyACrdHFjbGoqYhHzeLae4,2649
|
|
54
|
-
dbos/cli/cli.py,sha256=
|
|
55
|
-
dbos/cli/migration.py,sha256=
|
|
54
|
+
dbos/cli/cli.py,sha256=K8Fz05qach61EMuv5reUMRgT-UltysGZ4XerOTR4KEg,29003
|
|
55
|
+
dbos/cli/migration.py,sha256=1Y52EMc2rX7PJgJa3_KXV7oiQEO569k7aHXRofwYipo,3608
|
|
56
56
|
dbos/dbos-config.schema.json,sha256=LyUT1DOTaAwOP6suxQGS5KemVIqXGPyu_q7Hbo0neA8,6192
|
|
57
57
|
dbos/py.typed,sha256=QfzXT1Ktfk3Rj84akygc7_42z0lRpCq0Ilh8OXI6Zas,44
|
|
58
58
|
version/__init__.py,sha256=L4sNxecRuqdtSFdpUGX3TtBi9KL3k7YsZVIvv-fv9-A,1678
|
|
59
|
-
dbos-1.15.
|
|
59
|
+
dbos-1.15.0a3.dist-info/RECORD,,
|
|
File without changes
|
|
File without changes
|
|
File without changes
|