Deep-clone source metadata during chunk materialization
This commit is contained in:
@@ -16,6 +16,24 @@ type extractCaptureRecorder struct {
|
||||
checkpoint ExtractCheckpoint
|
||||
}
|
||||
|
||||
type pipelineTypedMetadata map[string]any
|
||||
|
||||
type mutatingMetadataValidator struct {
|
||||
seen string
|
||||
}
|
||||
|
||||
func (*mutatingMetadataValidator) Name() string { return "test/mutating-metadata" }
|
||||
func (*mutatingMetadataValidator) ExecutionClass() contracts.ExecutionClass {
|
||||
return contracts.ExecutionClassDeterministic
|
||||
}
|
||||
func (v *mutatingMetadataValidator) Validate(_ context.Context, request contracts.ChunkValidationRequest) (contracts.ValidationResult, error) {
|
||||
nested := request.Chunks[0].Units[0].Metadata["typed"].(pipelineTypedMetadata)
|
||||
v.seen = string(nested["raw"].(json.RawMessage))
|
||||
nested["raw"].(json.RawMessage)[0] = '['
|
||||
nested["changed"] = true
|
||||
return contracts.ValidationResult{Approved: true}, nil
|
||||
}
|
||||
|
||||
func (r *extractCaptureRecorder) ExtractSucceeded(_ string, _ string, _ []CheckpointFingerprint, outputs []CheckpointArtifact, rejected []contracts.RejectedOutput, warnings []contracts.Warning) error {
|
||||
r.checkpoint = ExtractCheckpoint{
|
||||
Outputs: cloneCheckpointArtifacts(outputs),
|
||||
@@ -77,6 +95,46 @@ func TestRunnerPassesIndependentAnnotationScopesToExtractors(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
func TestRunnerPassesIndependentConcreteMetadataToValidatorsAndExtractors(t *testing.T) {
|
||||
prepared := preparedAttemptDebugPipeline(t)
|
||||
input := prepared.input.(*typedTestInput)
|
||||
input.doc.Units[0].Metadata = map[string]any{
|
||||
"typed": pipelineTypedMetadata{"raw": json.RawMessage(`{"value":true}`)},
|
||||
}
|
||||
var err error
|
||||
input.doc.Digest, err = source.DigestDocument(input.doc)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
chunker := prepared.chunker.(*typedTestChunker)
|
||||
chunker.plan = typedTestPlan(input.doc)
|
||||
|
||||
validator := &mutatingMetadataValidator{}
|
||||
prepared.chunkValidators.validators = []preparedValidator{{
|
||||
resolved: ResolvedValidator{Binding: Binding(validator.Name()), Target: ValidatorTargetChunk},
|
||||
chunk: validator,
|
||||
}}
|
||||
var extractorSeen string
|
||||
installExtractOperation(prepared, 0, func(_ context.Context, request contracts.TypedExtractionRequest) (erasedTypedResult, error) {
|
||||
nested := request.Chunk.Units[0].Metadata["typed"].(pipelineTypedMetadata)
|
||||
extractorSeen = string(nested["raw"].(json.RawMessage))
|
||||
nested["raw"].(json.RawMessage)[0] = '['
|
||||
nested["changed"] = true
|
||||
return erasedTypedResult{Value: typedValueForLane(0, request.Chunk.Index)}, nil
|
||||
})
|
||||
|
||||
if _, err := New().Run(context.Background(), RunInput{Prepared: prepared, RawInput: []byte("input")}); err != nil {
|
||||
t.Fatalf("Run() error = %v", err)
|
||||
}
|
||||
if validator.seen != `{"value":true}` || extractorSeen != `{"value":true}` {
|
||||
t.Fatalf("validator/extractor metadata = %q / %q", validator.seen, extractorSeen)
|
||||
}
|
||||
original := input.doc.Units[0].Metadata["typed"].(pipelineTypedMetadata)
|
||||
if _, changed := original["changed"]; changed || string(original["raw"].(json.RawMessage)) != `{"value":true}` {
|
||||
t.Fatalf("source metadata changed through runner handoff: %#v", original)
|
||||
}
|
||||
}
|
||||
|
||||
func TestRunnerContinuesFromFreshAndReusedExtractResults(t *testing.T) {
|
||||
prepared := preparedAttemptDebugPipeline(t)
|
||||
extractCalls := 0
|
||||
|
||||
Reference in New Issue
Block a user