The sandbox composes a node from the input its engine took in, through one shape
mesh/delivery merged: source.main moved to novox/mesh-host@798d73eb11e9
mesh/check checking df13a83a9117 on 798d73eb11e9
mesh/delivery merged: source.main moved to novox/mesh-host@798d73eb11e9
mesh/check checking df13a83a9117 on 798d73eb11e9
The second sandbox fault of the same kind on mesh-host #200 (postgres's secret reader handed, the module not): the engine stripped the whole catalogue from the input it answers, so the sandbox composed the node's own modules from the indexer's source manifests while the bus reader composes them taken in from their builds (artifacts, templates archive texts, what is handed). Both sides now go through composer.SentInput: the node's own taken-in manifests and kept builds stay in the input, and the sandbox composes them over the cases'. An input past what one bus answer carries is refused in words. A conformance row composes one node through the bus reader and through the sandbox and requires the same declaration. Issue 1126. Claude-Session: https://claude.ai/code/session_01NcbgfJ9Gum47zkFKWRaovL
This commit is contained in:
@@ -15,6 +15,7 @@ import (
|
||||
|
||||
"github.com/novox/mesh-host/internal/agent"
|
||||
"github.com/novox/mesh-host/internal/compose/frombus"
|
||||
"github.com/novox/mesh-host/internal/composer"
|
||||
)
|
||||
|
||||
// **A check's candidate, composed in shadow on a call** (novox/hq ADR 0593 §7): the node seat's verb compose-candidate.
|
||||
@@ -37,6 +38,10 @@ var errNotReady = errors.New("this node's shadow has not read every input yet")
|
||||
// nothing at all. A node not done by then answers unready, naming what it waits on.
|
||||
var candidateWithin = delivery.ComposeAnswerBound - 10*time.Second
|
||||
|
||||
// maxSentInput is the most composition input an answer carries: the bus carries 1 MiB in one message (its max_payload),
|
||||
// and the answer's own fields and envelope come beside it.
|
||||
const maxSentInput = 900 << 10
|
||||
|
||||
// warmAtOnce is how many of the indexer's manifests the shadow reads at once before it composes a candidate.
|
||||
const warmAtOnce = 8
|
||||
|
||||
@@ -184,15 +189,18 @@ func (s *Shadow) composeCandidate(ctx context.Context, c *Composer, ask delivery
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
// The request's input carries no catalogue (composer.Request.Input): the cases give the manifests.
|
||||
in.Catalogue = nil
|
||||
for i := range in.Nodes {
|
||||
in.Nodes[i].Kept = nil
|
||||
}
|
||||
if body, err := json.Marshal(in); err == nil {
|
||||
// As the sandbox reads it (composer.SentInput, the one shape): this node's own modules as taken in from their
|
||||
// builds, every other module's manifest left to the cases.
|
||||
if body, err := json.Marshal(composer.SentInput(in, laid.env.Node)); err == nil {
|
||||
a.Input = body
|
||||
}
|
||||
})
|
||||
if len(a.Input) > maxSentInput {
|
||||
// Past what the bus carries in one answer, the checker would hear nothing: refused, saying so.
|
||||
size := len(a.Input)
|
||||
a.Input = nil
|
||||
return refuse(fmt.Sprintf("the composition input this node composed from is %d bytes, more than the %d an answer on the bus carries", size, maxSentInput))
|
||||
}
|
||||
if ctx.Err() != nil {
|
||||
_, on := run.said(c.now())
|
||||
return unready(fmt.Sprintf("the node did not compose the candidate within %s: it waits on %s", candidateWithin, on))
|
||||
|
||||
Reference in New Issue
Block a user