JuliusBrussee/caveman · error

cache-replay: could not encode verifier input

Error message

cache-replay: could not encode verifier input

What it means

Returned by the cache-replay verifier wrapper when the goroutine that JSON-encodes the verifier input fails. The wrapper encodes the input into an io.Pipe feeding the child's stdin; if json.Marshal/Encoder returns an error (for example a channel, function, or cycle in the input value), encodeErr becomes non-nil and is surfaced as this message. Note runErr is checked first, so a child failure masks an encode failure.

Source

Thrown at cacheengine/cmd/cache-replay/main.go:125

	go func() {
		err := json.NewEncoder(inputWriter).Encode(verificationInput)
		_ = inputWriter.CloseWithError(err)
		encodeDone <- err
	}()
	command.Stdin = inputReader
	command.Env = append([]string(nil), verifier.environment...)
	stdout := &boundedBuffer{max: verifier.maxOutputBytes}
	stderr := &boundedBuffer{max: 64 << 10}
	command.Stdout = stdout
	command.Stderr = stderr
	runErr := command.Run()
	_ = inputReader.Close()
	encodeErr := <-encodeDone
	if runErr != nil {
		return cachebench.TaskVerification{}, errors.New("cache-replay: verifier process failed")
	}
	if encodeErr != nil {
		return cachebench.TaskVerification{}, errors.New("cache-replay: could not encode verifier input")
	}
	return cachebench.ParseVerificationCommandOutput(stdout.Bytes(), input.Trace.RequestID)
}

type boundedBuffer struct {
	buffer bytes.Buffer
	max    int64
}

func (buffer *boundedBuffer) Write(value []byte) (int, error) {
	if int64(buffer.buffer.Len())+int64(len(value)) > buffer.max {
		remaining := buffer.max - int64(buffer.buffer.Len())
		if remaining > 0 {
			written, _ := buffer.buffer.Write(value[:remaining])
			return written, errors.New("output limit exceeded")
		}
		return 0, errors.New("output limit exceeded")
	}

View on GitHub (pinned to 27d5a3981a)

Solutions

  1. First resolve error 723 if present — the child failing early closes the pipe and causes the encode error
  2. Re-run with preflight only (omit -execute) to validate the trace before verification is attempted
  3. If you modified the input types, ensure every field is json-encodable (no chans, funcs, cycles)
  4. Confirm the trace passes cachebench.ReadTraceJSONL cleanly, including Body digest checks
Defensive patterns

Strategy: try-catch

Try / catch

if err != nil {
	if err.Error() == "cache-replay: could not encode verifier input" {
		// runErr is checked first; if you see this alone, suspect input serialization
		return fmt.Errorf("verifier input not encodable; validate the trace with a preflight run")
	}
}

Prevention

When it happens

Trigger: The TaskVerificationInput (or nested TraceRecord.Body raw JSON) contains a value json.Encoder cannot serialize, or the inputReader pipe is closed before encoding finishes (which usually coincides with the child exiting early, in which case 723 fires instead).

Common situations: Almost always secondary to a verifier that exits immediately and closes stdin (then error 723 wins); a corrupted trace Body that fails raw-message validation; custom code extending the input struct with unmarshalable fields.

Related errors


AI-assisted analysis of JuliusBrussee/caveman@27d5a3981a (2026-08-15). Data as JSON: /api/errors/4008a9590240b9a6. Report an issue: GitHub.