fix(graph): make structural action contract authoritative
This commit is contained in:
+16
-12
@@ -900,24 +900,28 @@ export function validateGraphUpdate(graph, update) {
|
||||
errors.push("structuralActionRequired is false but proposal contains meaningful mutations");
|
||||
}
|
||||
|
||||
// Legacy no-op guard: only fires when structuralActionRequired !== false.
|
||||
// When false → zero-mutation is a valid intentional no-op (contract PASS).
|
||||
if (!hasMeaningfulChange && update.structuralActionRequired !== false) {
|
||||
// Legacy no-op guard: only fires when structuralActionRequired is absent (null/undefined).
|
||||
// When true or false → the new contract owns no-op/mutation consistency.
|
||||
// The contract checks above already produced authoritative errors for those cases.
|
||||
|
||||
const fieldAbsent =
|
||||
update.structuralActionRequired === null ||
|
||||
update.structuralActionRequired === undefined;
|
||||
|
||||
if (!hasMeaningfulChange && fieldAbsent) {
|
||||
if (meaningPopulated) {
|
||||
// Avoid double-error when field absence was already flagged above
|
||||
if (
|
||||
update.structuralActionRequired !== null &&
|
||||
update.structuralActionRequired !== undefined
|
||||
) {
|
||||
errors.push(
|
||||
"answerMeaning.userSupportedMeaning is populated, but the proposal contains no graph mutation. answerMeaning alone does not constitute graph progress.",
|
||||
);
|
||||
}
|
||||
// structuralActionRequired was missing while userSupportedMeaning exists.
|
||||
// Missing-field rejection already added above; skip semantic-only guard to avoid duplicate errors on the same proposal.
|
||||
} else if (!meaningPopulated) {
|
||||
errors.push("Update contains no meaningful change");
|
||||
}
|
||||
}
|
||||
|
||||
// Legacy guard when structuralActionRequired=false: false declares no action needed,
|
||||
// but userSupportedMeaning populated implies semantic intent for change. However the
|
||||
// new-contract checks above already produced an error if there IS mutation. If there's
|
||||
// zero mutation with false + meaning, treat as intentional no-op (contract PASS).
|
||||
|
||||
// Reject oversized input
|
||||
const totalSize = JSON.stringify(update).length;
|
||||
if (totalSize > 100000) {
|
||||
|
||||
Reference in New Issue
Block a user