@byollm/protocol 0.1.0-alpha.87 → 0.1.0-alpha.89

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/README.md CHANGED
@@ -1,5 +1,5 @@
1
1
  > [!WARNING]
2
- > **Alpha (`0.1.0-alpha.87`) — under active development. Don't use this yet.**
2
+ > **Alpha (`0.1.0-alpha.89`) — under active development. Don't use this yet.**
3
3
  >
4
4
  > Install it deliberately: `npm install @byollm/protocol@alpha`.
5
5
  >
package/dist/index.d.ts CHANGED
@@ -1600,6 +1600,44 @@ declare function provenanceFor(input: {
1600
1600
  * opens them, nothing in between sees them, and the disposition check that
1601
1601
  * already compares clear-text against ciphertext extends to cover them.
1602
1602
  */
1603
+ /**
1604
+ * The closed set, as a schema — so the values exist once.
1605
+ *
1606
+ * A bare union would mean anything that has to VALIDATE a stop reason (the
1607
+ * ingress log, and the wire when step 4 lands) retyping the four strings
1608
+ * beside it. Instruction 9: one definition, both ends, and where a consumer
1609
+ * needs a runtime check the definition has to be one it can run.
1610
+ *
1611
+ * The type below is inferred from this rather than written twice, so the
1612
+ * compiler and the validator cannot disagree about what a stop reason is.
1613
+ */
1614
+ declare const StopReasonSchema: z.ZodEnum<{
1615
+ length: "length";
1616
+ unknown: "unknown";
1617
+ end: "end";
1618
+ "stop-sequence": "stop-sequence";
1619
+ }>;
1620
+ type StopReason =
1621
+ /** The model finished on its own. */
1622
+ "end"
1623
+ /** The model stopped at its own output ceiling. */
1624
+ | "length"
1625
+ /** A configured stop token ended it. */
1626
+ | "stop-sequence"
1627
+ /**
1628
+ * The adapter cannot tell, and says so.
1629
+ *
1630
+ * **The default, and never `"end"`.** An adapter nobody has updated — or
1631
+ * one somebody adds next year — must not be able to claim completion by
1632
+ * saying nothing. If absence meant "end", every un-updated adapter would go
1633
+ * on telling exactly the lie this exists to fix, and every new adapter
1634
+ * would inherit it in silence.
1635
+ *
1636
+ * It is the opposite-boolean rule this codebase keeps arriving at: when you
1637
+ * cannot tell, guess toward silence rather than toward a claim. "We do not
1638
+ * know" is a thing a site can act on; "it finished" when it did not is not.
1639
+ */
1640
+ | "unknown";
1603
1641
  declare const RunMetadata: z.ZodObject<{
1604
1642
  model: z.ZodString;
1605
1643
  backendClass: z.ZodEnum<{
@@ -1607,6 +1645,13 @@ declare const RunMetadata: z.ZodObject<{
1607
1645
  process: "process";
1608
1646
  }>;
1609
1647
  durationMs: z.ZodNumber;
1648
+ stop: z.ZodOptional<z.ZodEnum<{
1649
+ length: "length";
1650
+ unknown: "unknown";
1651
+ end: "end";
1652
+ "stop-sequence": "stop-sequence";
1653
+ }>>;
1654
+ stopReported: z.ZodOptional<z.ZodBoolean>;
1610
1655
  }, z.core.$strict>;
1611
1656
  type RunMetadata = z.infer<typeof RunMetadata>;
1612
1657
  /** Successful outcome. */
@@ -1717,6 +1762,13 @@ declare const SealedOutcome: z.ZodObject<{
1717
1762
  process: "process";
1718
1763
  }>;
1719
1764
  durationMs: z.ZodNumber;
1765
+ stop: z.ZodOptional<z.ZodEnum<{
1766
+ length: "length";
1767
+ unknown: "unknown";
1768
+ end: "end";
1769
+ "stop-sequence": "stop-sequence";
1770
+ }>>;
1771
+ stopReported: z.ZodOptional<z.ZodBoolean>;
1720
1772
  }, z.core.$strict>;
1721
1773
  }, z.core.$strict>;
1722
1774
  type SealedOutcome = z.infer<typeof SealedOutcome>;
@@ -1794,7 +1846,23 @@ declare const SizeClass: z.ZodEnum<{
1794
1846
  }>;
1795
1847
  type SizeClass = z.infer<typeof SizeClass>;
1796
1848
  /**
1797
- * The most one envelope may be, in bytes — ratified 2026-08-28.
1849
+ * The most one envelope may be, in bytes — **6 MiB, ruled 2026-09-10.**
1850
+ *
1851
+ * ## Why six, which is two sentences and neither is about capacity
1852
+ *
1853
+ * Todd, 09-10: *"6 MB solves for just text and people don't try to push
1854
+ * images. We will add R2 for multimodal later."* **The cap is a SHAPE
1855
+ * decision** — it makes the envelope the wrong tool for a photo, which is the
1856
+ * point, because the right tool for a photo is object storage and a reference
1857
+ * to it rather than a bigger pipe.
1858
+ *
1859
+ * And the half that makes it aligned rather than merely chosen: **6 MiB sits
1860
+ * under a hosted box's memory and bandwidth limits.** A box is 320 MiB of RAM;
1861
+ * a 10 MiB envelope buffered is a real fraction of it. **Six is the number at
1862
+ * which the smallest thing we sell can hold the largest thing we accept.**
1863
+ *
1864
+ * Both sentences are here because a number without them is a number the next
1865
+ * person rounds up. It was 10 MiB from 2026-08-28 until this ruling.
1798
1866
  *
1799
1867
  * A **relay-memory safety rail**, not a plan feature: every tier has the same
1800
1868
  * ceiling, and differentiating tiers on it would be selling a safety limit as
@@ -2875,4 +2943,4 @@ declare const MUST_IDS: readonly ("PAIR_ONE_USER" | "PAIR_INTERACTIVE" | "PAIR_C
2875
2943
  /** Every MUST verified a particular way. */
2876
2944
  declare function mustsVerifiedBy(kind: MustVerification): MustId[];
2877
2945
 
2878
- export { ABOUT, ABOUT_SHORT, ABOUT_SHORT_LEDE, ABOUT_SHORT_TAIL, AUDIENCES, Audience, BACKENDS, BACKEND_CLASSES, BACKEND_IDS, BackendClass, BackendCost, type BackendDescriptor, type BackendId, BackendIdSchema, CLOCK_ATTRIBUTION_MS, CLOCK_SKEW_WARN_MS, Capability, CapabilityMatrix, ChatMessage, ChatPayload, ClaimRequest, ClaimResponse, ClaimedJob, ClaimedStub, DeliveredResult, ENCRYPTION_KEY_CONTEXT, ENDPOINTS, ENVELOPE_MAX_AGE_MS, ERROR_STATUS, type Endpoint, type EnvelopeContext, EnvelopeDirection, type EnvelopeFailure, FetchRequest, FetchResponse, type FloorRefusal, GRANT_CONTEXT, GRANT_MAX_AGE_MS, GRANT_SIGNED_FIELDS, GeneratePayload, type GrantClaims, GrantRef, type GrantRefusal, HeartbeatRequest, HeartbeatResponse, JOB_KINDS, JobKind, JobOutcome, JobPayload, JobRefused, JobResultCanceled, JobResultError, JobResultOk, JobState, JobStub, KindedPayload, Lease, MAX_CLOCK_SKEW_MS, MAX_ENVELOPE_BYTES, MAX_PURPOSES, MAX_SUCCESSION_CHAIN, MIN_PROTOCOL_VERSION, MUSTS, MUST_IDS, Manifest, type MatchDaemon, type MatchJob, MatchRefusal, type MatchResult, type Must, type MustEnforcer, type MustId, type MustVerification, type MustVerifiedBy, OFFER_SCOPES, OfferScope, type OpenResult, PAYLOAD_LIMITS, PROTOCOL_PREFIX, PROTOCOL_VERSION, PairPollRequest, PairPollResponse, PairRequest, PairStartRequest, PairStartResponse, type PayloadFor, PublicIdentity, Purpose, REFUSAL_MESSAGES, RESERVED_PURPOSE, RETIREMENT_WINDOW_MS, RefusalReason, ReleaseRequest, ReleaseResponse, RequestSignature, ResultDisposition, ResultProvenance, ResultRequest, ResultResponse, RunMetadata, SIZE_CLASSES, SIZE_CLASS_LIMITS, SUCCESSION_CONTEXT, SUPPORTED_PROTOCOL_VERSIONS, SealedEnvelope, SealedOutcome, type SignatureFailure, SignedGrant, SizeClass, type SpendConsent, StoredKeys, Succession, type SuccessionFailure, type SuccessionWalk, TERMINAL_STATES, UPDATE_OFFER_SINCE, UPGRADE_COMMAND, type VersionRefusal, WireError, WireErrorCode, WithheldKind, backendDescriptor, backendName, canTransition, canonicalRequest, checkDaemonFloor, checkProtocolVersion, classifyCost, compareVersions, cryptoReady, declaredVersion, describeBytes, effectiveOfferScope, envelopeBytes, fingerprint, generateKeys, grantStatement, isBackendId, isCloudTaggedModel, isJobKind, isLocalHost, isTerminal, keyId, kindsOf, matchAudience, mayOfferUpdate, mentionsWireField, mustsVerifiedBy, open, payloadTextLength, provenanceFor, publicIdentityOf, resolveCost, seal, signGrant, signRequest, signSiteRequest, signSuccession, signWith, singlePurposeManifest, sizeClassCeiling, sizeClassOf, successionStatement, tooLargeMessage, updateOfferFor, verifyGrant, verifyLink, verifyPublicIdentity, verifyRequest, verifySiteRequest, verifyWith, walkSuccession, withoutComments };
2946
+ export { ABOUT, ABOUT_SHORT, ABOUT_SHORT_LEDE, ABOUT_SHORT_TAIL, AUDIENCES, Audience, BACKENDS, BACKEND_CLASSES, BACKEND_IDS, BackendClass, BackendCost, type BackendDescriptor, type BackendId, BackendIdSchema, CLOCK_ATTRIBUTION_MS, CLOCK_SKEW_WARN_MS, Capability, CapabilityMatrix, ChatMessage, ChatPayload, ClaimRequest, ClaimResponse, ClaimedJob, ClaimedStub, DeliveredResult, ENCRYPTION_KEY_CONTEXT, ENDPOINTS, ENVELOPE_MAX_AGE_MS, ERROR_STATUS, type Endpoint, type EnvelopeContext, EnvelopeDirection, type EnvelopeFailure, FetchRequest, FetchResponse, type FloorRefusal, GRANT_CONTEXT, GRANT_MAX_AGE_MS, GRANT_SIGNED_FIELDS, GeneratePayload, type GrantClaims, GrantRef, type GrantRefusal, HeartbeatRequest, HeartbeatResponse, JOB_KINDS, JobKind, JobOutcome, JobPayload, JobRefused, JobResultCanceled, JobResultError, JobResultOk, JobState, JobStub, KindedPayload, Lease, MAX_CLOCK_SKEW_MS, MAX_ENVELOPE_BYTES, MAX_PURPOSES, MAX_SUCCESSION_CHAIN, MIN_PROTOCOL_VERSION, MUSTS, MUST_IDS, Manifest, type MatchDaemon, type MatchJob, MatchRefusal, type MatchResult, type Must, type MustEnforcer, type MustId, type MustVerification, type MustVerifiedBy, OFFER_SCOPES, OfferScope, type OpenResult, PAYLOAD_LIMITS, PROTOCOL_PREFIX, PROTOCOL_VERSION, PairPollRequest, PairPollResponse, PairRequest, PairStartRequest, PairStartResponse, type PayloadFor, PublicIdentity, Purpose, REFUSAL_MESSAGES, RESERVED_PURPOSE, RETIREMENT_WINDOW_MS, RefusalReason, ReleaseRequest, ReleaseResponse, RequestSignature, ResultDisposition, ResultProvenance, ResultRequest, ResultResponse, RunMetadata, SIZE_CLASSES, SIZE_CLASS_LIMITS, SUCCESSION_CONTEXT, SUPPORTED_PROTOCOL_VERSIONS, SealedEnvelope, SealedOutcome, type SignatureFailure, SignedGrant, SizeClass, type SpendConsent, type StopReason, StopReasonSchema, StoredKeys, Succession, type SuccessionFailure, type SuccessionWalk, TERMINAL_STATES, UPDATE_OFFER_SINCE, UPGRADE_COMMAND, type VersionRefusal, WireError, WireErrorCode, WithheldKind, backendDescriptor, backendName, canTransition, canonicalRequest, checkDaemonFloor, checkProtocolVersion, classifyCost, compareVersions, cryptoReady, declaredVersion, describeBytes, effectiveOfferScope, envelopeBytes, fingerprint, generateKeys, grantStatement, isBackendId, isCloudTaggedModel, isJobKind, isLocalHost, isTerminal, keyId, kindsOf, matchAudience, mayOfferUpdate, mentionsWireField, mustsVerifiedBy, open, payloadTextLength, provenanceFor, publicIdentityOf, resolveCost, seal, signGrant, signRequest, signSiteRequest, signSuccession, signWith, singlePurposeManifest, sizeClassCeiling, sizeClassOf, successionStatement, tooLargeMessage, updateOfferFor, verifyGrant, verifyLink, verifyPublicIdentity, verifyRequest, verifySiteRequest, verifyWith, walkSuccession, withoutComments };
package/dist/index.js CHANGED
@@ -405,6 +405,12 @@ function backendName(id) {
405
405
  }
406
406
  function classifyCost(id, baseUrl, model) {
407
407
  const declared = BACKENDS[id].cost;
408
+ if (declared === "free" && model !== void 0 && isCloudTaggedModel(model)) {
409
+ return {
410
+ cost: "metered",
411
+ because: `its model tag ends in \`:cloud\`, so the work runs on your provider's cloud account rather than on this machine \u2014 ${backendName(id)} serves hosted models through the same local address as local ones`
412
+ };
413
+ }
408
414
  if (declared !== null) {
409
415
  const label = BACKENDS[id].label;
410
416
  return {
@@ -885,12 +891,51 @@ function provenanceFor(input) {
885
891
  untrusted: input.audience !== "private"
886
892
  };
887
893
  }
894
+ var StopReasonSchema = z7.enum([
895
+ "end",
896
+ "length",
897
+ "stop-sequence",
898
+ "unknown"
899
+ ]);
888
900
  var RunMetadata = z7.object({
889
901
  /** Which model actually served it. */
890
902
  model: z7.string().min(1),
891
903
  backendClass: BackendClass,
892
904
  /** Wall-clock milliseconds the backend call took. */
893
- durationMs: z7.number().int().nonnegative()
905
+ durationMs: z7.number().int().nonnegative(),
906
+ /**
907
+ * Why generation stopped — B064 step 4.
908
+ *
909
+ * Here rather than on {@link JobResultOk} because the outcome is the
910
+ * ANSWER and this is the daemon's signed account of how it was produced.
911
+ * Why generation ended is the same kind of fact as how long it took.
912
+ *
913
+ * **Optional because it is meaningless, not because it is new.** A
914
+ * cancelled job has no model to have stopped and an error has no
915
+ * generation to have ended, and `ran` travels on those arms too.
916
+ * Instruction 10 forbids optionality bought for compatibility — a
917
+ * version gate wearing a question mark — and this is not that: it is
918
+ * absent exactly where it would be a fact about nothing. Present on
919
+ * every `ok` result, always, because the whole value is the difference
920
+ * between `end`, `length` and `unknown` and that difference only exists
921
+ * if it is always there.
922
+ */
923
+ stop: StopReasonSchema.optional(),
924
+ /**
925
+ * Whether the adapter could read a stop signal at all — B105's lesson,
926
+ * carried to the wire.
927
+ *
928
+ * Without this the site re-commits the defect B064's third mapping kind
929
+ * was introduced to fix. `unknown` is TWO facts: an adapter that cannot
930
+ * report one, and an adapter that reported a word we do not map — and
931
+ * `openai-http` maps `stop` and `length` and nothing else, so the second
932
+ * is the common case rather than the corner.
933
+ *
934
+ * A site told only `unknown` would say "we do not know why this stopped"
935
+ * for a `claude-cli` job forever, which is true, and for a
936
+ * `content_filter` result, which is not the same thing at all.
937
+ */
938
+ stopReported: z7.boolean().optional()
894
939
  }).strict();
895
940
  var JobResultOk = z7.object({
896
941
  outcome: z7.literal("ok"),
@@ -977,7 +1022,7 @@ var DeliveredResult = z7.object({
977
1022
  }).strict();
978
1023
  var SizeClass = z7.enum(["small", "medium", "large", "unbounded"]);
979
1024
  var SIZE_CLASSES = Object.freeze(SizeClass.options);
980
- var MAX_ENVELOPE_BYTES = 10 * 1024 * 1024;
1025
+ var MAX_ENVELOPE_BYTES = 6 * 1024 * 1024;
981
1026
  function envelopeBytes(envelope) {
982
1027
  const counted = jsonLength(envelope);
983
1028
  if (counted !== void 0) return counted;
@@ -2694,6 +2739,7 @@ export {
2694
2739
  SealedOutcome,
2695
2740
  SignedGrant,
2696
2741
  SizeClass,
2742
+ StopReasonSchema,
2697
2743
  StoredKeys,
2698
2744
  Succession,
2699
2745
  TERMINAL_STATES,