Why: A goal-sensitive project provider can return different authorized sources for a prompt step and its judge, causing a valid workflow to fail when the judge re-resolves with an empty goal. Evidence: RED goal-sensitive step test; full compiled workflow positive and withdrawal negative tests; go test ./... -count=1 and targeted race passed locally before commit. Impact: Persist each trusted model attempt selector outside the public manifest, enforce receipt state continuity, and reauthorize every contributing model turn with its original selector before judging. Refs: RDM two-trees stage5 W6; W6 independent review P2.
32 lines
1.2 KiB
Go
32 lines
1.2 KiB
Go
package projectcontext
|
|
|
|
import "context"
|
|
|
|
type workflowStepAttemptKey struct{}
|
|
type resolveScopeKey struct{}
|
|
|
|
type resolveScope struct{ goal, targetID string }
|
|
|
|
// WithWorkflowStepAttempt is used by the trusted squad executor adapter. The
|
|
// value comes from the engine's persisted step attempt, never from model text.
|
|
func WithWorkflowStepAttempt(ctx context.Context, attemptID string) context.Context {
|
|
return context.WithValue(ctx, workflowStepAttemptKey{}, attemptID)
|
|
}
|
|
|
|
func WorkflowStepAttempt(ctx context.Context) string {
|
|
value, _ := ctx.Value(workflowStepAttemptKey{}).(string)
|
|
return value
|
|
}
|
|
|
|
// WithResolveScope carries the exact selector used for this model request to
|
|
// Backend's trusted receipt writer. It is saved separately from the public
|
|
// final-input manifest and survives a resumed workflow judge.
|
|
func WithResolveScope(ctx context.Context, goal, targetID string) context.Context {
|
|
return context.WithValue(ctx, resolveScopeKey{}, resolveScope{goal: goal, targetID: targetID})
|
|
}
|
|
|
|
func ResolveScope(ctx context.Context) (goal, targetID string, ok bool) {
|
|
scope, ok := ctx.Value(resolveScopeKey{}).(resolveScope)
|
|
return scope.goal, scope.targetID, ok
|
|
}
|