@plurnk/plurnk-contracts 1.29.0 → 3.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.env.defaults +1 -1
- package/SPEC.md +101 -77
- package/dist/schema/ApplicationOperationEvent.json +1 -1
- package/dist/schema/ClientInteractionProjection.json +2 -1
- package/dist/schema/PlurnkStatement.json +0 -16
- package/dist/schema/ProblemDetails.json +1 -1
- package/dist/schema/ProposalDisposition.json +4 -5
- package/dist/schema/ProposalPolicy.json +7 -0
- package/dist/schema/ProposalProjection.json +2 -2
- package/dist/schema/WorkerOwner.json +17 -0
- package/dist/src/ApplicationPort.d.ts +34 -9
- package/dist/src/ApplicationPort.d.ts.map +1 -1
- package/dist/src/Validator.d.ts +5 -6
- package/dist/src/Validator.d.ts.map +1 -1
- package/dist/src/Validator.js +11 -26
- package/dist/src/Validator.js.map +1 -1
- package/dist/src/index.d.ts +1 -1
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/index.js +1 -1
- package/dist/src/index.js.map +1 -1
- package/dist/src/types.d.ts +2 -2
- package/dist/src/types.d.ts.map +1 -1
- package/dist/src/types.generated.d.ts +25 -55
- package/dist/src/types.generated.d.ts.map +1 -1
- package/dist/src/types.js +4 -3
- package/dist/src/types.js.map +1 -1
- package/package.json +3 -2
- package/plurnk.md +14 -14
- package/dist/schema/LoopPolicy.json +0 -41
- package/dist/schema/LoopPolicyRequest.json +0 -16
package/.env.defaults
CHANGED
|
@@ -7,5 +7,5 @@ PLURNK_HOST=127.0.0.1
|
|
|
7
7
|
# The daemon's TCP port, shared by all client interfaces.
|
|
8
8
|
PLURNK_PORT=1066
|
|
9
9
|
# The whole URL a client dials instead: a remote portal, or a daemon bound to an address no
|
|
10
|
-
# client can dial (0.0.0.0). Unset = http://$PLURNK_HOST:$PLURNK_PORT.
|
|
10
|
+
# client can dial (0.0.0.0). Unset = http://$PLURNK_HOST:$PLURNK_PORT/agui.
|
|
11
11
|
# PLURNK_AGUI_URL=
|
package/SPEC.md
CHANGED
|
@@ -10,7 +10,7 @@ runtime-neutral wire envelopes; `@plurnk/plurnk-parser` implements the language
|
|
|
10
10
|
| Surface | Canonical export or artifact |
|
|
11
11
|
| ------------------------------------------------------------------------------- | --------------------------------------------------- |
|
|
12
12
|
| AST, validators, Problems, results, Notices, text regions and extents | `@plurnk/plurnk-contracts` |
|
|
13
|
-
| Capability and
|
|
13
|
+
| Capability admission and approval ownership | `CapabilityPolicy`, `WorkerOwner`, `ProposalPolicy`, `PROPOSAL_POLICIES` |
|
|
14
14
|
| Durable effort | `Effort`, `EFFORTS` |
|
|
15
15
|
| Model route and catalog discovery | `ModelRoute`, `ModelCatalogQuery`, `ModelCatalogPage`, `ModelReadiness` |
|
|
16
16
|
| Stopped-world client contract | `ProposalDisposition`, `ProposalProjection` |
|
|
@@ -137,9 +137,10 @@ The schemas own the runtime-neutral shapes; core owns their stateful values.
|
|
|
137
137
|
| `CapabilityDescriptor` | One routed operation demand with its operation, access class, resource/runtime/tool coordinates, and declared traits | Derive every demand before dispatch |
|
|
138
138
|
| `CapabilityPolicy` | Exact `only`/`deny` selectors; omitted `only` is unrestricted and present empty `only` denies all | Intersect service and workspace layers |
|
|
139
139
|
| `CapabilityProjection` | Exact service, workspace, and normalized effective policies | Expose the resolver's workspace cascade without claiming one layer is effective authority |
|
|
140
|
-
| `
|
|
141
|
-
| `
|
|
142
|
-
| `
|
|
140
|
+
| `WorkerOwner` | Nonempty address and unique client-tool names | Persist by workspace; inherit through worker creation |
|
|
141
|
+
| `ProposalPolicy` | `review`, `accept`, or `reject` | Read the server's disposition knob at the proposal boundary |
|
|
142
|
+
| `ProposalDisposition` | Review, or automatic accept/reject with optional outcome | Select once for the pending gate |
|
|
143
|
+
| `ProposalProjection` | Identity, review target, body/attrs, owner, stale signal, disposition | One validated projection for live delivery and reconnect |
|
|
143
144
|
| `ProviderUsage` | Conventional input/output totals with cache and reasoning details | Preserve observed quantities without replacing absence with zero |
|
|
144
145
|
| `ProviderCost` | Exact charged, estimated, or unknown monetary evidence | Normalize one monetary disposition for each physical provider request |
|
|
145
146
|
| `ProviderRequestAccounting` | Usage and cost evidence for one physical provider request | Preserve request order across retries, failover, success, and failure |
|
|
@@ -167,15 +168,11 @@ workspace layer and their normalized intersection: `service`, `workspace`, and
|
|
|
167
168
|
capability policy or inherited bound; every actor uses the same live workspace
|
|
168
169
|
policy. A client never derives effective authority from the mutable layer alone.
|
|
169
170
|
|
|
170
|
-
§
|
|
171
|
-
`
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
Contracts hold no default for the rest: the daemon's panel supplies it
|
|
176
|
-
({§loop-policy-composition}). `PROPOSAL_POLICIES` is the schema-owned
|
|
177
|
-
vocabulary of `proposals`. Capability admission precedes effect
|
|
178
|
-
classification and proposal settlement.
|
|
171
|
+
§proposal-policy `ProposalPolicy` names one server disposition; `PROPOSAL_POLICIES`
|
|
172
|
+
is its schema-owned vocabulary. `WorkerOwner` carries an address and the client-tool
|
|
173
|
+
names that recipient implements. Neither contains resource permissions or
|
|
174
|
+
message-carried authority. Core owns persistence, inheritance and settlement
|
|
175
|
+
({§worker-ownership}, {§proposal-disposition}); capability admission precedes approval.
|
|
179
176
|
|
|
180
177
|
§effort-wire `Effort` is exactly `off | adaptive | low |
|
|
181
178
|
medium | high | xhigh | max`. The schema owns this shared wire vocabulary. Providers own the
|
|
@@ -314,7 +311,8 @@ column-zero line outside any block containing a native operation's name and at m
|
|
|
314
311
|
`<!-- aside -->`, with only horizontal whitespace otherwise, opens that operation as if it were
|
|
315
312
|
fenced with the taught three backticks. The aside retains its ordinary meaning: no target or
|
|
316
313
|
modifiers are inferred. Its body runs to a line that is exactly the name
|
|
317
|
-
again, to the next heading ({§fence-heading-in-body}), or to the end of the turn
|
|
314
|
+
again, to the next heading ({§fence-heading-in-body}), or to the end of the turn, except
|
|
315
|
+
parameterless KILL always takes the remaining answer region ({§terminal-kill}). A fence inside
|
|
318
316
|
naming nothing known is body; the block expects no closer, so its body is never cut
|
|
319
317
|
back ({§closer-fallback}). A naked `KILL` alone holds every fence inside it as text ({§naked-kill}). It runs, and one warning-severity receipt follows its statement —
|
|
320
318
|
`` `KILL` opened with no fence; the taught form is three backticks. `` One rule for every native
|
|
@@ -330,8 +328,8 @@ read this way.
|
|
|
330
328
|
§fence-heading-in-body Outside a complete nested block ({§balanced-fences}), a fence
|
|
331
329
|
line of three or more backticks and a name that is a native operation or a known executor
|
|
332
330
|
is a heading. Inside an open block it either ends that block without closing it and opens the
|
|
333
|
-
next statement, or it is a literal example held by the block
|
|
334
|
-
the
|
|
331
|
+
next statement, or it is a literal example held by the block. {§fence-pairing} chooses between
|
|
332
|
+
the two; parameterless KILL always holds the remaining input ({§terminal-kill}). Fence lines of
|
|
335
333
|
fewer than three backticks are never headings ({§operation-fences}). Known executors are `sh`
|
|
336
334
|
plus what the host names in `ParseOptions.executors`. Inside a parameterless `KILL` a
|
|
337
335
|
heading never ends the block ({§terminal-kill}).
|
|
@@ -364,7 +362,9 @@ input at once by {§fence-pairing}:
|
|
|
364
362
|
|
|
365
363
|
A whole-input pass, `FencePairing`, decides where every block ends before the lexer reads a
|
|
366
364
|
token; the lexer's semantic predicates consult its decision, and ANTLR keeps framing, slots and
|
|
367
|
-
statement composition ({§parser-architecture}).
|
|
365
|
+
statement composition ({§parser-architecture}). Heading shape comes from the same grammar and
|
|
366
|
+
AST interpretation as normal admission, including recovered operand order and target notation;
|
|
367
|
+
fence pairing does not infer slot ownership from raw text. The pass is a least-cost parse of the fence
|
|
368
368
|
lines as a bracket language, in the manner of Aho and Peterson's least-errors parser
|
|
369
369
|
(SIAM J. Comput. 1(4), 1972): every reading of the fences is a derivation, and the pass returns
|
|
370
370
|
the cheapest.
|
|
@@ -409,7 +409,7 @@ repaired reading: a complete nested interpretation takes precedence. Each class
|
|
|
409
409
|
| Counted | Complete readings | Repaired readings | Why |
|
|
410
410
|
|---|---|---|---|
|
|
411
411
|
| Hidden operations: a heading that will not run, written at its block's width or wider | 1, together with the next row | 1 | Every operation the author wrote should run |
|
|
412
|
-
| Repairs: a supplied closer (except a message's run to the end of the input, {§message-run-on}), a fence read as a stray, a narrower closer accepted, a body under an operation that takes none (FIND, READ, COPY, MOVE, targeted KILL), a body not well-formed in the media type its runtime declares ({§executor-invocation}) | none by definition | 2 | The least-errors distance |
|
|
412
|
+
| Repairs: a supplied closer (except a message's run to the end of the input, {§message-run-on}), a fence read as a stray, a narrower closer accepted, a body under an operation that takes none (FIND, READ, COPY, MOVE, non-log targeted KILL), a body not well-formed in the media type its runtime declares ({§executor-invocation}) | none by definition | 2 | The least-errors distance |
|
|
413
413
|
| Literal by declaration: a heading narrower than its block, or no wider than the labeled block or example holding it, or inside a quotation or a KILL, or an executor heading inside a SEND, WORK, FORK or BARE body ({§prose-code-blocks}); a labeled fence in a body read as text | 1, together with the row above | 3 | Every code block the author declared should stand |
|
|
414
414
|
| Supplied closers | 2 | 4 | A block the author opened should end at a fence the author wrote |
|
|
415
415
|
| Other fences read as text | 3 | 5 | The least departure from the fences as written |
|
|
@@ -443,11 +443,13 @@ heading. An operation example quoted in a body of its own width therefore reads
|
|
|
443
443
|
closing and the example running; the wider outer fence or the tab offset quotes it
|
|
444
444
|
({§operation-fences}).
|
|
445
445
|
|
|
446
|
-
§terminal-kill **A KILL
|
|
447
|
-
|
|
448
|
-
|
|
449
|
-
|
|
450
|
-
and
|
|
446
|
+
§terminal-kill **A parameterless KILL starts the final answer region.** Once its heading is
|
|
447
|
+
recognized as an operation, the rest of the input is its literal body. A fence cannot return
|
|
448
|
+
that region to executable operations or outside text. Apparent operations, receipts and malformed
|
|
449
|
+
fences within it are answer text. An actual enclosing closer at the end is framing, not body;
|
|
450
|
+
an earlier fence remains body. Compact and recovered naked spellings obey the same boundary.
|
|
451
|
+
Quoted KILL examples do not open this region; targeted KILL retains ordinary statement framing.
|
|
452
|
+
Earlier operations still execute and completion remains subject to {§kill-conclusion}.
|
|
451
453
|
|
|
452
454
|
§prose-code-blocks **A message or a prompt shows code.** Inside a `SEND`, `WORK`, `FORK` or `BARE`
|
|
453
455
|
body, at any depth, a heading that names an executor (` ```sh `, ` ```python3 `) is a code block the
|
|
@@ -458,8 +460,8 @@ operation. In the distinct recorded benchmark emissions an executor heading ende
|
|
|
458
460
|
run218, run114 and run118, deepdumb run44) was the child's task, the prompt's code or code quoted in
|
|
459
461
|
a report, and reading it as an operation truncated the task and ran the example in the parent.
|
|
460
462
|
|
|
461
|
-
§message-run-on **A message runs to the end of the turn.** A
|
|
462
|
-
|
|
463
|
+
§message-run-on **A message runs to the end of the turn.** A `SEND`, `WORK`, `FORK` or `BARE`
|
|
464
|
+
whose block reaches the end of the input without its closer takes it
|
|
463
465
|
there with no repair: the text after its last inner block is still the deliverable, the message
|
|
464
466
|
or the task, never outside text. The run counts as a supplied closer, so a reading that closes at
|
|
465
467
|
a real fence still wins, and it never costs an operation: when the reading that runs on hides more
|
|
@@ -468,11 +470,9 @@ operations the author wrote than the best repaired reading, the repaired reading
|
|
|
468
470
|
inner fence keep what followed it (the qflash run192, run90 and run210 deliverables regain their last
|
|
469
471
|
sections), one echoed transcript (glm run155) runs one more operation, and none loses one.
|
|
470
472
|
|
|
471
|
-
§naked-kill **A naked KILL
|
|
472
|
-
a fence ({§naked-operation}), with or without an aside,
|
|
473
|
-
|
|
474
|
-
inside a fenced KILL ({§terminal-kill}), and the block ends only at its name alone on a line or at
|
|
475
|
-
the end of the input. No operation the deliverable shows runs.
|
|
473
|
+
§naked-kill **A naked KILL obeys the same answer boundary.** A parameterless `KILL` opened without
|
|
474
|
+
a fence ({§naked-operation}), with or without an aside, takes the remaining input under
|
|
475
|
+
{§terminal-kill}. A repeated name can close it only at the end; it never exposes later operations.
|
|
476
476
|
|
|
477
477
|
§pairing-witness **Witnesses.**
|
|
478
478
|
|
|
@@ -654,9 +654,9 @@ normalize optional bodies to null. Closing fences are conventional, never requir
|
|
|
654
654
|
({§closer-fallback}).
|
|
655
655
|
|
|
656
656
|
§statement-rendering `PlurnkParser.stringify` renders native OP names and named
|
|
657
|
-
runtime fences from the shared AST, with one blank line between operations
|
|
658
|
-
target group
|
|
659
|
-
|
|
657
|
+
runtime fences from the shared AST, with one blank line between operations. A
|
|
658
|
+
target group compiles to ordinary statements, each rendered with its resolved
|
|
659
|
+
selection ({§target-group}).
|
|
660
660
|
Every closing fence occupies its own line, including bodyless operations;
|
|
661
661
|
inline fences remain accepted input, not generated examples.
|
|
662
662
|
It chooses at least three backticks and more than any run within the body
|
|
@@ -692,16 +692,24 @@ below the header.
|
|
|
692
692
|
|
|
693
693
|
§target-group **READ and KILL take a target group.** A READ or KILL heading may carry several
|
|
694
694
|
`(path)` slots, each binding the scope and metadata that follow it under {§slot-order}; a naked
|
|
695
|
-
pattern on the heading ({§naked-pattern})
|
|
696
|
-
|
|
697
|
-
|
|
698
|
-
|
|
699
|
-
|
|
695
|
+
pattern on the heading ({§naked-pattern}) supplies the default for each member without its own
|
|
696
|
+
metadata `pattern`. The parser compiles the complete heading into one ordinary statement per
|
|
697
|
+
member, in authored order, each with its own target, scope, metadata and resolved matcher. No
|
|
698
|
+
duplicated first-member or group representation crosses the parser boundary. Every resulting
|
|
699
|
+
statement retains the heading's source position and aside; a heading-level parse error refuses
|
|
700
|
+
all its members, not valid sibling headings. A distilling body ({§log-kill-distillation}) lands
|
|
700
701
|
once, with the first member. COPY and MOVE keep their two operands with their own meaning
|
|
701
702
|
({§transfer-resource-selections}); every other operation takes one slot, and a second slot on its
|
|
702
703
|
heading is the slot-opener diagnostic. The form is accepted, not taught: it rescues a bulk attempt
|
|
703
704
|
written one path per slot.
|
|
704
705
|
|
|
706
|
+
§safe-uri-target-groups **An explicit URI list is a target group.** In READ and KILL only,
|
|
707
|
+
one path slot may contain several explicit `scheme://` URIs separated by top-level commas or
|
|
708
|
+
whitespace; braces protect their contents. Every member must independently parse as a URI,
|
|
709
|
+
otherwise the target stays singular and exact. Local filenames containing spaces or commas
|
|
710
|
+
are never split. Each URI inherits its slot's scope and metadata and compiles through
|
|
711
|
+
{§target-group}; COPY/MOVE and other operations do not admit this tolerance.
|
|
712
|
+
|
|
705
713
|
§scope-on-scopeless **A scope on an operation that takes none is dropped, and named.** WORK, FORK,
|
|
706
714
|
BARE and NOTE take no scope, and neither does a SEND without a recipient; a `<…>` slot on such a
|
|
707
715
|
heading, in any position, is skipped and the operation runs, with one warning-severity advisory
|
|
@@ -715,21 +723,33 @@ dead; in the distinct recorded emissions one heading carried the form (zai run42
|
|
|
715
723
|
```` ```WORK (worker://deprecation-implementer) <1,-1> ````), beside two recipient SENDs whose scope
|
|
716
724
|
the recipient refuses at runtime.
|
|
717
725
|
|
|
718
|
-
§heading-inline-body Nonempty body text belongs below the fence header.
|
|
719
|
-
|
|
720
|
-
|
|
721
|
-
|
|
726
|
+
§heading-inline-body Nonempty body text belongs below the fence header. Text after the slots
|
|
727
|
+
on the heading line is read by the operation's shape, by the builder that reads that operation,
|
|
728
|
+
and that reading is named: no text on the line is dropped silently, and none loses the operation.
|
|
729
|
+
Taken as the body, it is the first body line, with one warning: "`EDIT` body text was on the OP
|
|
730
|
+
line and was taken as the body; body content goes immediately beneath the opening fence line." A
|
|
731
|
+
sigil claims a matcher only on an operation that has one. This does not change the meaning of a
|
|
732
|
+
compact empty block or permit unmatched fences.
|
|
733
|
+
|
|
734
|
+
| Operation | Text after the slots on the heading line |
|
|
735
|
+
|---|---|
|
|
736
|
+
| FIND, READ, KILL with a non-log target | The matcher ({§naked-pattern}). Beside an option block's `pattern`, ignored ({§matcher-body-redirect}). |
|
|
737
|
+
| KILL on a log target | The matcher. Beside an option block's `pattern`, the first line of the distillation ({§log-kill-distillation}). |
|
|
738
|
+
| EDIT | A sigil-led matcher ({§edit-pattern}), unless an option block carries the `pattern`; otherwise the body. |
|
|
739
|
+
| COPY, MOVE | Ignored ({§transfer-resource-selections}). |
|
|
740
|
+
| SEND, WORK, FORK, BARE, executors | One JSON object is the option block where the heading admits one ({§bare-option-object}); otherwise the body. |
|
|
741
|
+
| NOTE, WAIT, KILL without a target | The body. |
|
|
722
742
|
|
|
723
743
|
§bare-option-object A bare option object is the option block, where the house option array owns the
|
|
724
744
|
block. On an operation that takes an option block and no bare matcher — SEND, BARE, WORK, FORK and
|
|
725
|
-
every executor fence — heading text after the slots that is exactly one JSON object `{…}
|
|
745
|
+
every executor fence — heading text after the slots that is exactly one JSON object `{…}`, where the
|
|
746
|
+
heading admits a block (BARE, WORK and FORK only after their target), is read
|
|
726
747
|
as `[{…}]`: the AST carries the array form, the written heading renders it, and one
|
|
727
748
|
warning-severity receipt names the indulgence in place of the {§heading-inline-body} advisory:
|
|
728
749
|
"`SEND` took a bare option object; the taught form is `[{…}]`." The option array is a house
|
|
729
750
|
convention, not a language rule ({§scheme-metadata-modifier}): an executor whose declared body is
|
|
730
751
|
JSON ({§executor-invocation}), an MCP tool, reads the object as its body instead — its arguments,
|
|
731
|
-
written on the heading line —
|
|
732
|
-
body belongs on the lines below it." The host names those executors to the parse
|
|
752
|
+
written on the heading line — under {§heading-inline-body}. The host names those executors to the parse
|
|
733
753
|
(`ParseOptions.jsonBodyExecutors`). A heading that already carries a block keeps the object as
|
|
734
754
|
inline body. On FIND, READ and KILL the same text is the matcher
|
|
735
755
|
({§naked-pattern}), because a search for JSON text is legitimate; a bare matcher
|
|
@@ -788,7 +808,7 @@ still the aside under {§misplaced-aside-advisory}. EDIT keeps its literal body:
|
|
|
788
808
|
with a matcher it is the replacement for every selected span ({§edit-pattern}),
|
|
789
809
|
and an absent body deletes them. `PlurnkParser.stringify` writes a lifted matcher
|
|
790
810
|
whose block left no metadata back bare when the bare form reads back identically
|
|
791
|
-
({§naked-pattern}), otherwise as `[{"pattern": "…"}]`.
|
|
811
|
+
and draws no advisory ({§naked-pattern}), otherwise as `[{"pattern": "…"}]`.
|
|
792
812
|
|
|
793
813
|
## 3. Lexical elements
|
|
794
814
|
|
|
@@ -892,8 +912,8 @@ disposition.
|
|
|
892
912
|
anchored (```` ```KILL (log:///**/READ) <17,-1>``` ```` or
|
|
893
913
|
```` ```KILL (worker:///notes.md) <@aB3dE,@0Aa9Z>``` ````), and an optional matcher option that
|
|
894
914
|
selects rows or lines (```` ```KILL (log:///**) [{"pattern": "~stale"}]``` ````, {§matcher-option}).
|
|
895
|
-
|
|
896
|
-
|
|
915
|
+
Each operand becomes an ordinary KILL statement with its own `target`, `lineMarker` and
|
|
916
|
+
`matcher`; no grouped AST reaches execution ({§target-group}).
|
|
897
917
|
The body is retained on parameterless KILL ({§kill-conclusion}) and on a `log:///` target, where
|
|
898
918
|
it is the model's distillation of what the KILL retires and lands as its own NOTE row
|
|
899
919
|
({§log-kill-distillation}); every other targeted KILL has `body: null`, and a body beneath one
|
|
@@ -985,8 +1005,10 @@ Mutation semantics:
|
|
|
985
1005
|
- `<SL,SC,EL,EC>` deletes the exact exclusive-end region and inserts the body at its start.
|
|
986
1006
|
- §transfer-resource-selections COPY and MOVE require two singular
|
|
987
1007
|
`ResourceSelection` operands, source first and destination second, and admit
|
|
988
|
-
no body
|
|
989
|
-
|
|
1008
|
+
no body: text after the slots on the heading line, or beneath it, is ignored and the
|
|
1009
|
+
operation still runs, with one warning-severity advisory (`MOVE takes no body; the body
|
|
1010
|
+
was ignored.`). Each selection binds its own target, scope, matcher, and metadata under
|
|
1011
|
+
{§slot-order}, {§matcher-option}, and {§scheme-metadata-modifier}.
|
|
990
1012
|
|
|
991
1013
|
### Per-operation observations
|
|
992
1014
|
|
|
@@ -1112,7 +1134,8 @@ refusal ({§matcher-refusal}), not a parse error.
|
|
|
1112
1134
|
operation, two for COPY and MOVE, any number on READ and KILL ({§target-group}) — is a parser
|
|
1113
1135
|
error at its opening paren. Report the unexpected slot and the grammar's expected
|
|
1114
1136
|
alternatives when available, without inferring pattern intent or imposing another
|
|
1115
|
-
operation's operand count.
|
|
1137
|
+
operation's operand count. Recovery-only body text is not advertised as a valid body
|
|
1138
|
+
for an operation that takes none. The statement is dropped and its siblings run.
|
|
1116
1139
|
|
|
1117
1140
|
| Prefix | Dialect | Canonical form | Typed admission | Runtime owner |
|
|
1118
1141
|
|-----------|----------|--------------------------------------|-----------------------------------|---------------------|
|
|
@@ -1274,7 +1297,7 @@ operation receives empty-turn recovery, not successful completion ({§empty-turn
|
|
|
1274
1297
|
|
|
1275
1298
|
The model may supply WAIT or request completion with parameterless KILL. The host, not the grammar, owns
|
|
1276
1299
|
turn boundaries and adjudicates the loop's actual obligations. Asking
|
|
1277
|
-
the human
|
|
1300
|
+
the human uses the native `question` executor tool when enabled ({§question-tool}), not a
|
|
1278
1301
|
disposition. The shape rules ARE structural:
|
|
1279
1302
|
|
|
1280
1303
|
- §send-mid-reservation WAIT is reserved ({§turn-disposition}).
|
|
@@ -1286,6 +1309,8 @@ disposition. The shape rules ARE structural:
|
|
|
1286
1309
|
dispositions until the other admitted operations settle
|
|
1287
1310
|
({§op-execution-order}). Nothing is dropped and no diagnostic is raised for
|
|
1288
1311
|
position. Omission does not synthesize a disposition ({§turn-shape}).
|
|
1312
|
+
This applies to WAIT, not to the literal answer region opened by parameterless KILL
|
|
1313
|
+
({§terminal-kill}).
|
|
1289
1314
|
- SEND is communication: an optional recipient path and an optional body.
|
|
1290
1315
|
- §park-202-only WAIT joins live work: an open stream or a live
|
|
1291
1316
|
child. With none, it continues. Its optional duration bounds parking ({§send-wait-scope});
|
|
@@ -1356,18 +1381,15 @@ tiers ignore outside text. Core alone owns storing it as the turn's outside sour
|
|
|
1356
1381
|
and no-operation strikes ({§empty-turn}); parsing never infers delivery or completion
|
|
1357
1382
|
intent.
|
|
1358
1383
|
|
|
1359
|
-
§unfenced-operation **
|
|
1360
|
-
|
|
1361
|
-
|
|
1362
|
-
|
|
1363
|
-
|
|
1364
|
-
|
|
1365
|
-
|
|
1366
|
-
|
|
1367
|
-
|
|
1368
|
-
outside text ({§outside-text}), an unfenced KILL would sit in the record as an answer never given,
|
|
1369
|
-
and only the warning tells the model otherwise. The warning and the exclusion together keep the
|
|
1370
|
-
line out of the record.
|
|
1384
|
+
§unfenced-operation **The parser identifies ignored unfenced fragments.** An outside-text line
|
|
1385
|
+
that opens at column zero with an operation's name and anything else — `KILL The answer…`,
|
|
1386
|
+
`READ (a.md)`, `KILL (notes.md)` — draws one warning: `` Unfenced `KILL` ignored. ``
|
|
1387
|
+
This describes only that fragment, never a fenced operation elsewhere in the turn or its reasoning.
|
|
1388
|
+
The line is not response text ({§response-text}): it is neither stored as outside text nor echoed
|
|
1389
|
+
into the next packet, and the exact emission remains at `ops://`. A name with only an optional
|
|
1390
|
+
complete aside opens the operation instead ({§naked-operation}). A registered executor's name
|
|
1391
|
+
followed by an operand slot — `gitea (list_issues)`, `sh(build.sh)` — draws the same warning under
|
|
1392
|
+
the executor's own spelling. Quoted blocks, offset lines and names inside a sentence draw nothing.
|
|
1371
1393
|
|
|
1372
1394
|
§recorded-emissions **The parser is regressed against emissions models actually produced,
|
|
1373
1395
|
not fixtures we wrote.** `test/fixtures/recorded-emissions.jsonl` holds one real exemplar
|
|
@@ -1437,7 +1459,7 @@ among them: the parser is `@plurnk/plurnk-parser`'s ({§parser-consumers}).
|
|
|
1437
1459
|
| `TurnDisposition` | The one turn disposition and its recognition | {§turn-disposition} |
|
|
1438
1460
|
| `CapabilityAdmission` | Admission of a capability descriptor against policy layers | {§capability-admission} |
|
|
1439
1461
|
| `PLURNK_OPS`, `INTERNAL_ROW_OPS`, `PLURNK_FENCE` | The closed operation alphabet and the language's fence | {§canonical-statement} |
|
|
1440
|
-
| `PROPOSAL_POLICIES`
|
|
1462
|
+
| `PROPOSAL_POLICIES` | Server proposal disposition vocabulary | {§proposal-policy} |
|
|
1441
1463
|
| `WORKER_NAME` | Authority minting predicate | {§worker-name} |
|
|
1442
1464
|
| `UNKNOWN_POSITION` | Frozen sentinel for an AST statement without retained parsed source | {§parser-position} |
|
|
1443
1465
|
|
|
@@ -1620,8 +1642,8 @@ discriminated values:
|
|
|
1620
1642
|
| `mimetype` | Non-empty `mimetype` media type | `CapabilityDisplay` |
|
|
1621
1643
|
|
|
1622
1644
|
`CapabilityDisplay` is a closed object whose optional `glyph` is a non-empty,
|
|
1623
|
-
opaque string.
|
|
1624
|
-
declarations; Core owns composition of the installed
|
|
1645
|
+
opaque string. Frameworks own and validate their intrinsic
|
|
1646
|
+
declarations; Core owns composition of the installed extensions; interface
|
|
1625
1647
|
modules expose this exact shape; clients own rendering, font support, theme,
|
|
1626
1648
|
and identity fallback when `glyph` is absent. Empty framework sentinels are
|
|
1627
1649
|
normalized to absence at composition. Display metadata is client state, never
|
|
@@ -1865,7 +1887,9 @@ diagnostics are:
|
|
|
1865
1887
|
until what remains is the matcher. `READ (a.rs) /fn resolve_/ <1,-1> <!-- entities -->`
|
|
1866
1888
|
is the same operation as `READ (a.rs) <1,-1> /fn resolve_/ <!-- entities -->`, with
|
|
1867
1889
|
one warning-severity advisory naming the canonical order for the scope or block:
|
|
1868
|
-
|
|
1890
|
+
recovery requires a single possible path-slot owner. With multiple slots, a trailing scope
|
|
1891
|
+
or metadata block refuses the heading rather than relocating or discarding the slot.
|
|
1892
|
+
A matcher that
|
|
1869
1893
|
itself ends in one of those shapes takes the option escape.
|
|
1870
1894
|
`plurnk.md` teaches one order — `OP (path)? <scope|range>? [metadata]? pattern?
|
|
1871
1895
|
<!-- aside -->?` — and free ordering is not taught. Small departure, small
|
|
@@ -1902,15 +1926,15 @@ diagnostics are:
|
|
|
1902
1926
|
body instead, the anchor would be written into the file, or the EDIT refused for want of a line
|
|
1903
1927
|
marker (14 distinct recorded headings). On READ and KILL the same text stays a literal matcher,
|
|
1904
1928
|
since `@patch` is a search a model means.
|
|
1905
|
-
- §matcher-body-redirect **
|
|
1906
|
-
|
|
1907
|
-
|
|
1908
|
-
|
|
1909
|
-
|
|
1910
|
-
|
|
1911
|
-
|
|
1912
|
-
|
|
1913
|
-
|
|
1929
|
+
- §matcher-body-redirect **Unread body text on bodyless operations.** FIND, READ and bodyless
|
|
1930
|
+
KILL keep the statement but discard text the matcher did not consume, with one warning:
|
|
1931
|
+
`READ takes no body; the body was ignored. A pattern belongs on the opening fence line
|
|
1932
|
+
after the path.` KILL's advisory says `This KILL`, limiting the claim to that invocation:
|
|
1933
|
+
parameterless completion and log distillation bodies remain valid. Delivered like
|
|
1934
|
+
{§misplaced-aside-advisory} as a `parse_advisory` notice (a warning, never an error).
|
|
1935
|
+
One sigil line beneath a bodyless heading is the bare form written a line low and still lifts;
|
|
1936
|
+
nothing else is promoted into a matcher from below the heading. An option block's `pattern`
|
|
1937
|
+
prevents that lift, and the advisory never echoes the discarded text.
|
|
1914
1938
|
- §combined-anchor-tolerance **Combined line number and anchor in a scope.** A
|
|
1915
1939
|
text-coordinate scope written `L<@hash>` — digits immediately before the opener — is the
|
|
1916
1940
|
displayed `42<@abcde>` row prefix copied whole: the scope is the anchor, the number is dropped, and one
|
|
@@ -11,7 +11,7 @@
|
|
|
11
11
|
"loopId": { "type": "integer", "minimum": 1 },
|
|
12
12
|
"turnId": { "type": "integer", "minimum": 1 },
|
|
13
13
|
"sequence": { "type": "integer", "minimum": 1 },
|
|
14
|
-
"origin": { "enum": ["model", "client", "_plurnk"
|
|
14
|
+
"origin": { "enum": ["model", "client", "_plurnk"] },
|
|
15
15
|
"projectRoot": { "type": ["string", "null"] },
|
|
16
16
|
"statement": { "$ref": "https://schemas.plurnk.xyz/v0/PlurnkStatement.json" },
|
|
17
17
|
"phase": { "enum": ["started", "settled"] },
|
|
@@ -4,13 +4,14 @@
|
|
|
4
4
|
"title": "ClientInteractionProjection",
|
|
5
5
|
"description": "The runtime-neutral client-interface projection of one pending client interaction. Live delivery and reconnect discovery expose this same shape.",
|
|
6
6
|
"type": "object",
|
|
7
|
-
"required": ["interactionId", "workerId", "loopId", "turnId", "request"],
|
|
7
|
+
"required": ["interactionId", "workerId", "loopId", "turnId", "recipient", "request"],
|
|
8
8
|
"additionalProperties": false,
|
|
9
9
|
"properties": {
|
|
10
10
|
"interactionId": { "type": "integer", "minimum": 1 },
|
|
11
11
|
"workerId": { "type": "integer", "minimum": 1 },
|
|
12
12
|
"loopId": { "type": "integer", "minimum": 1 },
|
|
13
13
|
"turnId": { "type": "integer", "minimum": 1 },
|
|
14
|
+
"recipient": { "type": "string", "minLength": 1 },
|
|
14
15
|
"request": { "$ref": "https://schemas.plurnk.xyz/v0/ClientInteractionRequest.json" }
|
|
15
16
|
}
|
|
16
17
|
}
|
|
@@ -186,14 +186,6 @@
|
|
|
186
186
|
"target": {
|
|
187
187
|
"$ref": "#/$defs/PathOrNull"
|
|
188
188
|
},
|
|
189
|
-
"group": {
|
|
190
|
-
"type": "array",
|
|
191
|
-
"minItems": 2,
|
|
192
|
-
"items": {
|
|
193
|
-
"$ref": "https://schemas.plurnk.xyz/v0/ResourceSelection.json"
|
|
194
|
-
},
|
|
195
|
-
"description": "The heading's target group ({§target-group}): every `(path)` slot with the scope and metadata that follow it, in authored order, the first repeating `target`, `lineMarker` and `metadata`. Present only when the heading carries more than one slot; absent, as in every statement stored before groups existed, the operation has its one target."
|
|
196
|
-
},
|
|
197
189
|
"lineMarker": {
|
|
198
190
|
"$ref": "#/$defs/TextLineMarkerOrNull"
|
|
199
191
|
},
|
|
@@ -454,14 +446,6 @@
|
|
|
454
446
|
"target": {
|
|
455
447
|
"$ref": "#/$defs/PathOrNull"
|
|
456
448
|
},
|
|
457
|
-
"group": {
|
|
458
|
-
"type": "array",
|
|
459
|
-
"minItems": 2,
|
|
460
|
-
"items": {
|
|
461
|
-
"$ref": "https://schemas.plurnk.xyz/v0/ResourceSelection.json"
|
|
462
|
-
},
|
|
463
|
-
"description": "The heading's target group ({§target-group}): every `(path)` slot with the scope and metadata that follow it, in authored order, the first repeating `target`, `lineMarker` and `metadata`. Present only when the heading carries more than one slot; absent, as in every statement stored before groups existed, the operation has its one target."
|
|
464
|
-
},
|
|
465
449
|
"lineMarker": {
|
|
466
450
|
"$ref": "#/$defs/TextLineMarkerOrNull",
|
|
467
451
|
"description": "Scope of the kill: lines of a log body or of an entry ({§kill-scope}); null kills the whole target."
|
|
@@ -31,7 +31,7 @@
|
|
|
31
31
|
"instance": {
|
|
32
32
|
"type": "string",
|
|
33
33
|
"pattern": "^[a-zA-Z][a-zA-Z0-9+.-]*:",
|
|
34
|
-
"description": "Absolute URI identifying the failed durable operation, normally its log URI. Core adds it at persistence when
|
|
34
|
+
"description": "Absolute URI identifying the failed durable operation, normally its log URI. Core adds it at persistence when an extension cannot know the durable coordinate."
|
|
35
35
|
},
|
|
36
36
|
"stage": {
|
|
37
37
|
"type": "string",
|
|
@@ -2,22 +2,21 @@
|
|
|
2
2
|
"$schema": "https://json-schema.org/draft/2020-12/schema",
|
|
3
3
|
"$id": "https://schemas.plurnk.xyz/v0/ProposalDisposition.json",
|
|
4
4
|
"title": "ProposalDisposition",
|
|
5
|
-
"description": "The one core-owned settlement decision
|
|
5
|
+
"description": "The one core-owned settlement decision. Review waits for the worker's owner; accept and reject carry the automatic resolution core applies.",
|
|
6
6
|
"oneOf": [
|
|
7
7
|
{
|
|
8
8
|
"type": "object",
|
|
9
|
-
"required": ["
|
|
9
|
+
"required": ["decision"],
|
|
10
10
|
"additionalProperties": false,
|
|
11
11
|
"properties": {
|
|
12
|
-
"
|
|
12
|
+
"decision": { "const": "review" }
|
|
13
13
|
}
|
|
14
14
|
},
|
|
15
15
|
{
|
|
16
16
|
"type": "object",
|
|
17
|
-
"required": ["
|
|
17
|
+
"required": ["decision"],
|
|
18
18
|
"additionalProperties": false,
|
|
19
19
|
"properties": {
|
|
20
|
-
"owner": { "const": "loop" },
|
|
21
20
|
"decision": { "enum": ["accept", "reject"] },
|
|
22
21
|
"outcome": { "type": "string", "minLength": 1 }
|
|
23
22
|
}
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"$schema": "https://json-schema.org/draft/2020-12/schema",
|
|
3
|
+
"$id": "https://schemas.plurnk.xyz/v0/ProposalPolicy.json",
|
|
4
|
+
"title": "ProposalPolicy",
|
|
5
|
+
"description": "Server disposition for proposals. Review requires the worker's owner; accept and reject settle within core.",
|
|
6
|
+
"enum": ["review", "accept", "reject"]
|
|
7
|
+
}
|
|
@@ -13,7 +13,7 @@
|
|
|
13
13
|
"target",
|
|
14
14
|
"body",
|
|
15
15
|
"attrs",
|
|
16
|
-
"
|
|
16
|
+
"owner",
|
|
17
17
|
"disposition"
|
|
18
18
|
],
|
|
19
19
|
"additionalProperties": false,
|
|
@@ -42,7 +42,7 @@
|
|
|
42
42
|
},
|
|
43
43
|
"body": { "type": "string" },
|
|
44
44
|
"attrs": { "type": "object", "additionalProperties": true },
|
|
45
|
-
"
|
|
45
|
+
"owner": { "type": "string", "minLength": 1 },
|
|
46
46
|
"disposition": { "$ref": "https://schemas.plurnk.xyz/v0/ProposalDisposition.json" }
|
|
47
47
|
}
|
|
48
48
|
}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
{
|
|
2
|
+
"$schema": "https://json-schema.org/draft/2020-12/schema",
|
|
3
|
+
"$id": "https://schemas.plurnk.xyz/v0/WorkerOwner.json",
|
|
4
|
+
"title": "WorkerOwner",
|
|
5
|
+
"description": "A workspace-scoped approval owner and the client tools it implements. Capabilities persist while disconnected; a message never changes ownership.",
|
|
6
|
+
"type": "object",
|
|
7
|
+
"required": ["address", "tools"],
|
|
8
|
+
"additionalProperties": false,
|
|
9
|
+
"properties": {
|
|
10
|
+
"address": { "type": "string", "minLength": 1 },
|
|
11
|
+
"tools": {
|
|
12
|
+
"type": "array",
|
|
13
|
+
"uniqueItems": true,
|
|
14
|
+
"items": { "type": "string", "minLength": 1 }
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
}
|