@synapsor/runner 0.1.14 → 0.1.16
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/CHANGELOG.md +33 -1
- package/README.md +9 -1
- package/dist/cli.d.ts.map +1 -1
- package/dist/runner.mjs +514 -405
- package/docs/README.md +4 -0
- package/docs/capability-authoring.md +11 -2
- package/docs/conformance.md +8 -0
- package/docs/doctor.md +3 -3
- package/docs/dsl-reference.md +197 -0
- package/docs/migrating-to-synapsor-spec.md +5 -2
- package/docs/production.md +7 -8
- package/docs/release-notes.md +35 -6
- package/docs/runner-config-reference.md +194 -0
- package/docs/security-boundary.md +5 -5
- package/docs/store-lifecycle.md +38 -0
- package/docs/writeback-executors.md +3 -3
- package/examples/mcp-postgres-billing-app-handler/schema.sql +11 -1
- package/examples/reference-support-billing-app/schema.sql +11 -1
- package/examples/support-billing-agent/db/schema.sql +11 -1
- package/examples/support-plan-credit/README.md +2 -2
- package/examples/support-plan-credit/seed/001_seed.sql +11 -1
- package/package.json +1 -1
- package/schemas/synapsor.runner.schema.json +116 -3
- /package/examples/support-plan-credit/{contract.synapsor → contract.synapsor.sql} +0 -0
|
@@ -40,6 +40,16 @@ CREATE TABLE IF NOT EXISTS public.account_credits (
|
|
|
40
40
|
created_at timestamptz NOT NULL DEFAULT now()
|
|
41
41
|
);
|
|
42
42
|
|
|
43
|
+
CREATE TABLE IF NOT EXISTS public.synapsor_writeback_receipts (
|
|
44
|
+
idempotency_key text PRIMARY KEY,
|
|
45
|
+
job_id text UNIQUE NOT NULL,
|
|
46
|
+
proposal_id text NOT NULL,
|
|
47
|
+
status text NOT NULL,
|
|
48
|
+
result_hash text,
|
|
49
|
+
created_at timestamptz NOT NULL DEFAULT now(),
|
|
50
|
+
completed_at timestamptz
|
|
51
|
+
);
|
|
52
|
+
|
|
43
53
|
DO $$
|
|
44
54
|
BEGIN
|
|
45
55
|
IF NOT EXISTS (SELECT 1 FROM pg_roles WHERE rolname = 'synapsor_reader') THEN
|
|
@@ -53,7 +63,7 @@ $$;
|
|
|
53
63
|
|
|
54
64
|
GRANT CONNECT ON DATABASE synapsor_billing_app_handler TO synapsor_reader, synapsor_writer;
|
|
55
65
|
GRANT USAGE ON SCHEMA public TO synapsor_reader, synapsor_writer;
|
|
56
|
-
GRANT CREATE ON SCHEMA public TO synapsor_writer;
|
|
57
66
|
GRANT SELECT ON public.tenants, public.customers, public.invoices, public.account_credits TO synapsor_reader, synapsor_writer;
|
|
67
|
+
GRANT SELECT, INSERT, UPDATE ON public.synapsor_writeback_receipts TO synapsor_writer;
|
|
58
68
|
GRANT UPDATE (late_fee_cents, waiver_reason, credit_requested_cents, credit_reason, credited_cents, updated_at) ON public.invoices TO synapsor_writer;
|
|
59
69
|
GRANT INSERT ON public.account_credits TO synapsor_writer;
|
|
@@ -47,6 +47,16 @@ CREATE TABLE IF NOT EXISTS public.orders (
|
|
|
47
47
|
updated_at timestamptz NOT NULL DEFAULT now()
|
|
48
48
|
);
|
|
49
49
|
|
|
50
|
+
CREATE TABLE IF NOT EXISTS public.synapsor_writeback_receipts (
|
|
51
|
+
idempotency_key text PRIMARY KEY,
|
|
52
|
+
job_id text UNIQUE NOT NULL,
|
|
53
|
+
proposal_id text NOT NULL,
|
|
54
|
+
status text NOT NULL,
|
|
55
|
+
result_hash text,
|
|
56
|
+
created_at timestamptz NOT NULL DEFAULT now(),
|
|
57
|
+
completed_at timestamptz
|
|
58
|
+
);
|
|
59
|
+
|
|
50
60
|
DO $$
|
|
51
61
|
BEGIN
|
|
52
62
|
IF NOT EXISTS (SELECT 1 FROM pg_roles WHERE rolname = 'synapsor_reader') THEN
|
|
@@ -60,8 +70,8 @@ $$;
|
|
|
60
70
|
|
|
61
71
|
GRANT CONNECT ON DATABASE synapsor_reference_support_billing TO synapsor_reader, synapsor_writer;
|
|
62
72
|
GRANT USAGE ON SCHEMA public TO synapsor_reader, synapsor_writer;
|
|
63
|
-
GRANT CREATE ON SCHEMA public TO synapsor_writer;
|
|
64
73
|
GRANT SELECT ON public.tenants, public.customers, public.support_tickets, public.invoices, public.orders TO synapsor_reader, synapsor_writer;
|
|
74
|
+
GRANT SELECT, INSERT, UPDATE ON public.synapsor_writeback_receipts TO synapsor_writer;
|
|
65
75
|
GRANT UPDATE (plan_credit_cents, credit_reason, updated_at) ON public.customers TO synapsor_writer;
|
|
66
76
|
GRANT UPDATE (status, resolution_note, updated_at) ON public.support_tickets TO synapsor_writer;
|
|
67
77
|
GRANT UPDATE (late_fee_cents, waiver_reason, updated_at) ON public.invoices TO synapsor_writer;
|
|
@@ -70,6 +70,16 @@ CREATE TABLE IF NOT EXISTS public.orders (
|
|
|
70
70
|
updated_at timestamptz NOT NULL DEFAULT now()
|
|
71
71
|
);
|
|
72
72
|
|
|
73
|
+
CREATE TABLE IF NOT EXISTS public.synapsor_writeback_receipts (
|
|
74
|
+
idempotency_key text PRIMARY KEY,
|
|
75
|
+
job_id text UNIQUE NOT NULL,
|
|
76
|
+
proposal_id text NOT NULL,
|
|
77
|
+
status text NOT NULL,
|
|
78
|
+
result_hash text,
|
|
79
|
+
created_at timestamptz NOT NULL DEFAULT now(),
|
|
80
|
+
completed_at timestamptz
|
|
81
|
+
);
|
|
82
|
+
|
|
73
83
|
DO $$
|
|
74
84
|
BEGIN
|
|
75
85
|
IF NOT EXISTS (SELECT 1 FROM pg_roles WHERE rolname = 'synapsor_reader') THEN
|
|
@@ -83,8 +93,8 @@ $$;
|
|
|
83
93
|
|
|
84
94
|
GRANT CONNECT ON DATABASE synapsor_support_billing_agent TO synapsor_reader, synapsor_writer;
|
|
85
95
|
GRANT USAGE ON SCHEMA public TO synapsor_reader, synapsor_writer;
|
|
86
|
-
GRANT CREATE ON SCHEMA public TO synapsor_writer;
|
|
87
96
|
GRANT SELECT ON public.tenants, public.customers, public.support_tickets, public.invoices, public.credits, public.agent_actions, public.orders TO synapsor_reader, synapsor_writer;
|
|
97
|
+
GRANT SELECT, INSERT, UPDATE ON public.synapsor_writeback_receipts TO synapsor_writer;
|
|
88
98
|
GRANT UPDATE (plan_credit_cents, credit_reason, updated_at) ON public.customers TO synapsor_writer;
|
|
89
99
|
GRANT UPDATE (status, resolution_note, updated_at) ON public.support_tickets TO synapsor_writer;
|
|
90
100
|
GRANT UPDATE (late_fee_cents, waiver_reason, updated_at) ON public.invoices TO synapsor_writer;
|
|
@@ -27,7 +27,7 @@ When working from this source checkout, use `corepack pnpm runner` in place of
|
|
|
27
27
|
Validate the authored boundary before starting Docker:
|
|
28
28
|
|
|
29
29
|
```bash
|
|
30
|
-
synapsor-runner dsl compile examples/support-plan-credit/contract.synapsor \
|
|
30
|
+
synapsor-runner dsl compile examples/support-plan-credit/contract.synapsor.sql \
|
|
31
31
|
--out /tmp/support-plan-credit.contract.json \
|
|
32
32
|
--strict
|
|
33
33
|
synapsor-runner contract validate /tmp/support-plan-credit.contract.json
|
|
@@ -192,7 +192,7 @@ tool metadata and results. For Claude, Cursor, or generic MCP clients, omit
|
|
|
192
192
|
|
|
193
193
|
## How The Policy Is Governed
|
|
194
194
|
|
|
195
|
-
The auto-approval policy lives in `contract.synapsor`:
|
|
195
|
+
The auto-approval policy lives in `contract.synapsor.sql`:
|
|
196
196
|
|
|
197
197
|
```sql
|
|
198
198
|
AUTO APPROVE WHEN plan_credit_cents <= 2500
|
|
@@ -14,6 +14,16 @@ CREATE TABLE IF NOT EXISTS public.customers (
|
|
|
14
14
|
private_notes text
|
|
15
15
|
);
|
|
16
16
|
|
|
17
|
+
CREATE TABLE IF NOT EXISTS public.synapsor_writeback_receipts (
|
|
18
|
+
idempotency_key text PRIMARY KEY,
|
|
19
|
+
job_id text UNIQUE NOT NULL,
|
|
20
|
+
proposal_id text NOT NULL,
|
|
21
|
+
status text NOT NULL,
|
|
22
|
+
result_hash text,
|
|
23
|
+
created_at timestamptz NOT NULL DEFAULT now(),
|
|
24
|
+
completed_at timestamptz
|
|
25
|
+
);
|
|
26
|
+
|
|
17
27
|
INSERT INTO public.customers (
|
|
18
28
|
id,
|
|
19
29
|
tenant_id,
|
|
@@ -87,6 +97,6 @@ $$;
|
|
|
87
97
|
|
|
88
98
|
GRANT CONNECT ON DATABASE synapsor_runner_plan_credit TO synapsor_reader, synapsor_writer;
|
|
89
99
|
GRANT USAGE ON SCHEMA public TO synapsor_reader, synapsor_writer;
|
|
90
|
-
GRANT CREATE ON SCHEMA public TO synapsor_writer;
|
|
91
100
|
GRANT SELECT ON public.customers TO synapsor_reader, synapsor_writer;
|
|
92
101
|
GRANT UPDATE (plan_credit_cents, credit_reason, updated_at) ON public.customers TO synapsor_writer;
|
|
102
|
+
GRANT SELECT, INSERT, UPDATE ON public.synapsor_writeback_receipts TO synapsor_writer;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@synapsor/runner",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.16",
|
|
4
4
|
"description": "Stop giving AI agents execute_sql; expose reviewed Postgres/MySQL MCP actions with proposals, approval, writeback, and replay.",
|
|
5
5
|
"license": "Apache-2.0",
|
|
6
6
|
"type": "module",
|
|
@@ -5,12 +5,36 @@
|
|
|
5
5
|
"description": "Configuration for local Synapsor Runner MCP capabilities over Postgres/MySQL.",
|
|
6
6
|
"type": "object",
|
|
7
7
|
"additionalProperties": false,
|
|
8
|
-
"required": ["version", "mode"
|
|
8
|
+
"required": ["version", "mode"],
|
|
9
|
+
"allOf": [
|
|
10
|
+
{
|
|
11
|
+
"if": { "properties": { "mode": { "const": "cloud" } }, "required": ["mode"] },
|
|
12
|
+
"then": { "required": ["cloud"] },
|
|
13
|
+
"else": { "required": ["sources"] }
|
|
14
|
+
},
|
|
15
|
+
{
|
|
16
|
+
"if": { "required": ["contracts"] },
|
|
17
|
+
"then": {},
|
|
18
|
+
"else": {
|
|
19
|
+
"if": { "properties": { "mode": { "not": { "const": "cloud" } } }, "required": ["mode"] },
|
|
20
|
+
"then": {
|
|
21
|
+
"required": ["capabilities"],
|
|
22
|
+
"properties": { "capabilities": { "minItems": 1 } },
|
|
23
|
+
"anyOf": [
|
|
24
|
+
{ "required": ["trusted_context"] },
|
|
25
|
+
{ "required": ["contexts"] }
|
|
26
|
+
]
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
],
|
|
9
31
|
"properties": {
|
|
10
32
|
"version": {
|
|
33
|
+
"description": "Runner configuration contract version. Version 1 is the current public format.",
|
|
11
34
|
"const": 1
|
|
12
35
|
},
|
|
13
36
|
"mode": {
|
|
37
|
+
"description": "Local execution mode. review permits proposals and trusted writeback; cloud delegates reviewed tools to Synapsor Cloud.",
|
|
14
38
|
"type": "string",
|
|
15
39
|
"enum": ["read_only", "shadow", "review", "cloud"]
|
|
16
40
|
},
|
|
@@ -21,20 +45,24 @@
|
|
|
21
45
|
"default": 1
|
|
22
46
|
},
|
|
23
47
|
"strict": {
|
|
48
|
+
"description": "Reject unknown configuration keys when true.",
|
|
24
49
|
"type": "boolean",
|
|
25
50
|
"default": true
|
|
26
51
|
},
|
|
27
52
|
"storage": {
|
|
53
|
+
"description": "Local proposal, evidence, receipt, and replay ledger. Relative sqlite_path values resolve from the Runner process working directory.",
|
|
28
54
|
"type": "object",
|
|
29
55
|
"additionalProperties": false,
|
|
30
56
|
"properties": {
|
|
31
57
|
"sqlite_path": {
|
|
58
|
+
"description": "SQLite ledger path. The file can contain visible business-data evidence and is created with owner-only permissions on POSIX.",
|
|
32
59
|
"type": "string",
|
|
33
60
|
"minLength": 1
|
|
34
61
|
}
|
|
35
62
|
}
|
|
36
63
|
},
|
|
37
64
|
"sources": {
|
|
65
|
+
"description": "Named Postgres/MySQL sources. Contract SOURCE names must match these keys.",
|
|
38
66
|
"type": "object",
|
|
39
67
|
"minProperties": 1,
|
|
40
68
|
"additionalProperties": {
|
|
@@ -42,30 +70,69 @@
|
|
|
42
70
|
}
|
|
43
71
|
},
|
|
44
72
|
"trusted_context": {
|
|
73
|
+
"description": "Default operator-controlled tenant/principal binding. These values are never model arguments.",
|
|
45
74
|
"$ref": "#/$defs/trusted_context"
|
|
46
75
|
},
|
|
47
76
|
"contexts": {
|
|
77
|
+
"description": "Named trusted contexts referenced by capabilities or portable contracts.",
|
|
48
78
|
"type": "object",
|
|
49
79
|
"additionalProperties": {
|
|
50
80
|
"$ref": "#/$defs/trusted_context"
|
|
51
81
|
}
|
|
52
82
|
},
|
|
53
83
|
"executors": {
|
|
84
|
+
"description": "Trusted app-owned writeback executors. URLs, tokens, and commands are referenced through environment-variable names.",
|
|
54
85
|
"type": "object",
|
|
55
86
|
"additionalProperties": {
|
|
56
87
|
"$ref": "#/$defs/executor"
|
|
57
88
|
}
|
|
58
89
|
},
|
|
59
|
-
"
|
|
90
|
+
"contracts": {
|
|
91
|
+
"description": "Portable @synapsor/spec contract files. Relative paths resolve from this config file's directory.",
|
|
60
92
|
"type": "array",
|
|
61
93
|
"minItems": 1,
|
|
94
|
+
"items": {
|
|
95
|
+
"type": "string",
|
|
96
|
+
"minLength": 1
|
|
97
|
+
}
|
|
98
|
+
},
|
|
99
|
+
"capabilities": {
|
|
100
|
+
"description": "Embedded compatibility capabilities. May be empty when contracts supplies the capability catalog.",
|
|
101
|
+
"type": "array",
|
|
102
|
+
"minItems": 0,
|
|
62
103
|
"items": {
|
|
63
104
|
"$ref": "#/$defs/capability"
|
|
64
105
|
}
|
|
65
106
|
},
|
|
107
|
+
"policies": {
|
|
108
|
+
"description": "Embedded reviewed policies. Contract-authored policies are merged into the same runtime catalog.",
|
|
109
|
+
"type": "array",
|
|
110
|
+
"items": { "$ref": "#/$defs/policy" }
|
|
111
|
+
},
|
|
112
|
+
"approvals": {
|
|
113
|
+
"description": "Local approval behavior overrides.",
|
|
114
|
+
"type": "object",
|
|
115
|
+
"additionalProperties": false,
|
|
116
|
+
"properties": {
|
|
117
|
+
"disable_auto_approval": { "type": "boolean" }
|
|
118
|
+
}
|
|
119
|
+
},
|
|
66
120
|
"cloud": {
|
|
67
121
|
"type": "object",
|
|
68
|
-
"additionalProperties":
|
|
122
|
+
"additionalProperties": false,
|
|
123
|
+
"required": ["base_url_env", "runner_token_env", "adapter_id"],
|
|
124
|
+
"properties": {
|
|
125
|
+
"base_url_env": { "$ref": "#/$defs/env_name" },
|
|
126
|
+
"runner_token_env": { "$ref": "#/$defs/env_name" },
|
|
127
|
+
"runner_id": { "type": "string", "minLength": 1 },
|
|
128
|
+
"runner_version": { "type": "string", "minLength": 1 },
|
|
129
|
+
"project_id": { "type": "string", "minLength": 1 },
|
|
130
|
+
"adapter_id": { "type": "string", "minLength": 1 },
|
|
131
|
+
"source_id": { "type": "string", "minLength": 1 },
|
|
132
|
+
"engines": { "type": "array", "minItems": 1, "items": { "enum": ["postgres", "mysql"] } },
|
|
133
|
+
"capabilities": { "type": "array", "minItems": 1, "items": { "type": "string", "minLength": 1 } },
|
|
134
|
+
"session": { "type": "object" }
|
|
135
|
+
}
|
|
69
136
|
}
|
|
70
137
|
},
|
|
71
138
|
"$defs": {
|
|
@@ -94,15 +161,18 @@
|
|
|
94
161
|
"enum": ["postgres", "mysql"]
|
|
95
162
|
},
|
|
96
163
|
"read_url_env": {
|
|
164
|
+
"description": "Environment variable containing the least-privilege read connection URL.",
|
|
97
165
|
"$ref": "#/$defs/env_name"
|
|
98
166
|
},
|
|
99
167
|
"write_url_env": {
|
|
168
|
+
"description": "Environment variable containing the separate trusted writer URL. It is never exposed over MCP.",
|
|
100
169
|
"$ref": "#/$defs/env_name"
|
|
101
170
|
},
|
|
102
171
|
"read_only": {
|
|
103
172
|
"type": "boolean"
|
|
104
173
|
},
|
|
105
174
|
"statement_timeout_ms": {
|
|
175
|
+
"description": "Per-read database statement timeout in milliseconds.",
|
|
106
176
|
"type": "integer",
|
|
107
177
|
"minimum": 1
|
|
108
178
|
},
|
|
@@ -295,9 +365,16 @@
|
|
|
295
365
|
},
|
|
296
366
|
"required_role": {
|
|
297
367
|
"type": "string"
|
|
368
|
+
},
|
|
369
|
+
"policy": {
|
|
370
|
+
"type": "string",
|
|
371
|
+
"minLength": 1
|
|
298
372
|
}
|
|
299
373
|
}
|
|
300
374
|
},
|
|
375
|
+
"writeback": {
|
|
376
|
+
"$ref": "#/$defs/writeback"
|
|
377
|
+
},
|
|
301
378
|
"single_tenant_dev_ack": {
|
|
302
379
|
"type": "boolean"
|
|
303
380
|
}
|
|
@@ -410,6 +487,42 @@
|
|
|
410
487
|
}
|
|
411
488
|
}
|
|
412
489
|
}
|
|
490
|
+
},
|
|
491
|
+
"writeback": {
|
|
492
|
+
"type": "object",
|
|
493
|
+
"additionalProperties": false,
|
|
494
|
+
"required": ["mode"],
|
|
495
|
+
"properties": {
|
|
496
|
+
"mode": {
|
|
497
|
+
"enum": ["direct_sql", "app_handler", "cloud_worker", "none"]
|
|
498
|
+
},
|
|
499
|
+
"executor": {
|
|
500
|
+
"type": "string",
|
|
501
|
+
"minLength": 1
|
|
502
|
+
}
|
|
503
|
+
}
|
|
504
|
+
},
|
|
505
|
+
"policy": {
|
|
506
|
+
"type": "object",
|
|
507
|
+
"additionalProperties": false,
|
|
508
|
+
"required": ["name", "kind"],
|
|
509
|
+
"properties": {
|
|
510
|
+
"name": { "type": "string", "minLength": 1 },
|
|
511
|
+
"kind": { "enum": ["approval", "settlement", "scope", "custom"] },
|
|
512
|
+
"mode": { "type": "string" },
|
|
513
|
+
"rules": {
|
|
514
|
+
"type": "array",
|
|
515
|
+
"items": {
|
|
516
|
+
"type": "object",
|
|
517
|
+
"additionalProperties": false,
|
|
518
|
+
"required": ["field", "max"],
|
|
519
|
+
"properties": {
|
|
520
|
+
"field": { "$ref": "#/$defs/identifier" },
|
|
521
|
+
"max": { "type": "integer", "minimum": 0 }
|
|
522
|
+
}
|
|
523
|
+
}
|
|
524
|
+
}
|
|
525
|
+
}
|
|
413
526
|
}
|
|
414
527
|
}
|
|
415
528
|
}
|
|
File without changes
|