mesh-catalog seat: a config declaration's minimum and maximum are nullable, so a declared 0 survives the typed state; a fixture row with 0 (third of a kind: a zero or empty optional value dropped; ADR 0634 §2; issue 1966)

This commit is contained in:
2026-11-05 16:36:06 +01:00
parent 9ffdaca898
commit 4cd6934842
5 changed files with 55 additions and 17 deletions
+13 -11
View File
@@ -590,17 +590,19 @@ type ConfigCandidatesByPullValueDeclaresValueValue struct {
Default any `json:"default"`
Description string `json:"description,omitempty"`
// the allowed values
Enum any `json:"enum,omitempty"`
Kind string `json:"kind"`
Maximum float64 `json:"maximum,omitempty"`
Minimum float64 `json:"minimum,omitempty"`
Pattern string `json:"pattern,omitempty"`
Predefined string `json:"predefined,omitempty"`
Required bool `json:"required,omitempty"`
Runtime bool `json:"runtime,omitempty"`
Trusted bool `json:"trusted,omitempty"`
Type string `json:"type,omitempty"`
Why string `json:"why"`
Enum any `json:"enum,omitempty"`
Kind string `json:"kind"`
// a declared bound; 0 is a bound, absent is none
Maximum any `json:"maximum,omitempty"`
// a declared bound; 0 is a bound, absent is none
Minimum any `json:"minimum,omitempty"`
Pattern string `json:"pattern,omitempty"`
Predefined string `json:"predefined,omitempty"`
Required bool `json:"required,omitempty"`
Runtime bool `json:"runtime,omitempty"`
Trusted bool `json:"trusted,omitempty"`
Type string `json:"type,omitempty"`
Why string `json:"why"`
}
// ConfigCandidatesByPullValue is one value of the state config-candidates under the key <pull>.
@@ -33,6 +33,12 @@ func TestFixtures(t *testing.T) {
err := json.Unmarshal(b, &v)
return v, err
}, subjectIs: nil},
{name: "a pull request's configuration state whose bounds are declared 0 (a zero is a bound, not none)", subject: "", given: "{\"declares\":{\"nats\":{\"limit\":{\"default\":0,\"kind\":\"setting\",\"maximum\":0,\"minimum\":0,\"why\":\"a bound\"}}},\"head\":\"cccccccccccccccccccccccccccccccccccccccc\",\"pull\":\"novox/mesh-catalog#1\",\"v\":1}", wire: "{\"declares\":{\"nats\":{\"limit\":{\"default\":0,\"kind\":\"setting\",\"maximum\":0,\"minimum\":0,\"why\":\"a bound\"}}},\"head\":\"cccccccccccccccccccccccccccccccccccccccc\",\"pull\":\"novox/mesh-catalog#1\",\"v\":1}",
decode: func(b []byte) (any, error) {
var v ConfigCandidatesByPullValue
err := json.Unmarshal(b, &v)
return v, err
}, subjectIs: nil},
{name: "a published Go module", subject: "", given: "{\"commit\":\"cccccccccccccccccccccccccccccccccccccccc\",\"module\":\"git.novox.be/novox/mesh-sdk/go\",\"packages\":[{\"digest\":\"ab\",\"package\":\"git.novox.be/novox/mesh-sdk/go/keys\"}],\"repository\":\"novox/mesh-sdk\",\"v\":1}", wire: "{\"commit\":\"cccccccccccccccccccccccccccccccccccccccc\",\"module\":\"git.novox.be/novox/mesh-sdk/go\",\"packages\":[{\"digest\":\"ab\",\"package\":\"git.novox.be/novox/mesh-sdk/go/keys\"}],\"repository\":\"novox/mesh-sdk\",\"v\":1}",
decode: func(b []byte) (any, error) { var v PackagesByModuleValue; err := json.Unmarshal(b, &v); return v, err }, subjectIs: nil},
{name: "a package series", subject: "", given: "{\"name\":\"go-keys\",\"series\":\"0.1\",\"v\":1}", wire: "{\"name\":\"go-keys\",\"series\":\"0.1\",\"v\":1}",
@@ -81,6 +81,26 @@
}
}
},
{
"name": "a pull request's configuration state whose bounds are declared 0 (a zero is a bound, not none)",
"of": "state:config-candidates/<pull>",
"given": {
"v": 1,
"pull": "novox/mesh-catalog#1",
"head": "cccccccccccccccccccccccccccccccccccccccc",
"declares": {
"nats": {
"limit": {
"kind": "setting",
"default": 0,
"why": "a bound",
"minimum": 0,
"maximum": 0
}
}
}
}
},
{
"name": "a published Go module",
"of": "state:packages/<module>",
+12 -4
View File
@@ -165,7 +165,7 @@
},
{
"name": "seat-definitions",
"description": "The seat list (ADR 0636 \u00a74): with no seat, every trunk seat with its digest and the revision of the list; with a seat, that trunk definition resolved with the parts it includes. Reads only.",
"description": "The seat list (ADR 0636 §4): with no seat, every trunk seat with its digest and the revision of the list; with a seat, that trunk definition resolved with the parts it includes. Reads only.",
"optional": true,
"input": {
"properties": {
@@ -244,7 +244,7 @@
}
}
],
"description": "The catalog of the mesh: every module the trunk holds with its manifest, fingerprint and verdict, the packages published, and the seat list (ADR 0636 \u00a71, \u00a74).",
"description": "The catalog of the mesh: every module the trunk holds with its manifest, fingerprint and verdict, the packages published, and the seat list (ADR 0636 §1, §4).",
"family": {
"name": "mesh-catalog.events",
"max-age-days": 7
@@ -823,10 +823,18 @@
"description": "the allowed values"
},
"minimum": {
"type": "number"
"type": [
"number",
"null"
],
"description": "a declared bound; 0 is a bound, absent is none"
},
"maximum": {
"type": "number"
"type": [
"number",
"null"
],
"description": "a declared bound; 0 is a bound, absent is none"
},
"pattern": {
"type": "string"
+4 -2
View File
@@ -426,8 +426,10 @@ export interface ConfigCandidatesByPullValueDeclaresValueValue {
/** the allowed values */
"enum"?: unknown;
"kind": string;
"maximum"?: number;
"minimum"?: number;
/** a declared bound; 0 is a bound, absent is none */
"maximum"?: unknown;
/** a declared bound; 0 is a bound, absent is none */
"minimum"?: unknown;
"pattern"?: string;
"predefined"?: string;
"required"?: boolean;