import { readFile } from 'node:fs/promises' import { resolve } from 'node:path' const root = resolve(new URL('..', import.meta.url).pathname) const [report, plan] = await Promise.all([ readFile(resolve(root, 'config/freecad-gui-workflow-oracle.json'), 'utf8').then(JSON.parse), readFile(resolve(root, 'config/freecad-gui-workflow-plan.json'), 'utf8').then(JSON.parse), ]) const fail = (message) => { throw new Error(`FreeCAD GUI workflow oracle: ${message}`) } const lockedCommit = '0108fd4b4850cc46e625b60e53cea7a7bbe69f8d' if (report.schemaVersion !== 1 || report.baseline?.freecadVersion !== '1.1.1' || report.baseline?.commit !== lockedCommit || report.baseline.profile !== 'desktop-xvfb-isolated-config') fail('baseline mismatch.') if (report.family?.id !== plan.family?.id || report.family.primaryCommand !== plan.family.primaryCommand || report.family.exactTask !== plan.family.primaryExactTask) fail('selected family mapping is stale.') if (report.generatedBy !== './npmw run probe:freecad-gui-workflow' || report.checkedBy !== './npmw run check:freecad-gui-workflow') fail('probe/check provenance is incomplete.') const success = report.workflows?.success if (success?.workflowId !== report.family.id || success.commandId !== report.family.primaryCommand || success.state !== 'success' || success.success !== true) fail('success workflow identity is invalid.') if (success.before?.activeWorkbench !== 'PartDesignWorkbench' || success.before.commandRegistered !== true || success.before.commandActive !== true || success.before.actionCount < 1 || success.before.selection?.join(',') !== 'Sketch') fail('native command preconditions are incomplete.') if (success.taskPanel?.opened?.activeDialog !== true || success.taskPanel.opened.inEdit !== 'Pad' || success.taskPanel.opened.fieldCount < 1 || success.taskPanel.preview?.name !== 'Pad' || success.taskPanel.preview.length !== 10 || success.taskPanel.preview.volume !== 120) fail('native Pad Task preview evidence is incomplete.') if (success.after?.acceptClicked !== true || success.taskPanel?.closed?.activeDialog !== false || success.taskPanel.closed.inEdit !== '') fail('native Pad Task accept/close evidence is incomplete.') const pad = success.after?.pad if (success.after?.bodyTip !== 'Pad' || success.after.bodyGroup?.join(',') !== 'Sketch,Pad' || pad?.typeId !== 'PartDesign::Pad' || pad.length !== 10 || pad.shapeValid !== true || pad.solidCount !== 1 || pad.faceCount !== 6 || pad.edgeCount !== 12 || pad.vertexCount !== 8 || pad.volume !== 120 || pad.profile !== 'Sketch' || pad.state?.join(',') !== 'Up-to-date') fail('native Pad result semantics are incomplete.') if ((!Number.isInteger(success.after.undoCount) || success.after.undoCount < 1) && (!Array.isArray(success.after.undoNames) || success.after.undoNames.length < 1)) fail('native Pad transaction evidence is missing.') const disabled = report.workflows?.disabled if (disabled?.workflowId !== report.family.id || disabled.commandId !== report.family.primaryCommand || disabled.state !== 'disabled' || disabled.success !== true) fail('disabled workflow identity is invalid.') if (disabled.before?.activeWorkbench !== 'PartDesignWorkbench' || disabled.before.commandRegistered !== true || disabled.before.commandActive !== false || disabled.before.actionCount < 1 || disabled.before.actionEnabled !== false) fail('native disabled command state is incomplete.') const checkpoints = [ disabled.before?.sideEffects, disabled.activationAttempts?.actionTrigger?.after, disabled.activationAttempts?.runCommand?.after, disabled.after?.sideEffects, ] for (const checkpoint of checkpoints) { if (!checkpoint || checkpoint.documentCount !== 0 || checkpoint.documents?.length !== 0 || checkpoint.activeDocument !== '' || checkpoint.activeGuiDocument !== false || checkpoint.selection?.length !== 0) fail('disabled Pad created or activated document state.') if (checkpoint.taskPanel?.activeDialog !== false || checkpoint.taskPanel.inEdit !== '') fail('disabled Pad created a Task or edit state.') if (checkpoint.transaction?.active !== false || checkpoint.transaction.name !== '' || checkpoint.transaction.id !== null || checkpoint.transaction.documents?.length !== 0) fail('disabled Pad created a transaction scope.') } if (disabled.activationAttempts.actionTrigger.requested !== true || disabled.activationAttempts.actionTrigger.triggeredSignalCount !== 0 || disabled.activationAttempts.actionTrigger.sideEffectsUnchanged !== true) fail('disabled QAction activation was not blocked cleanly.') if (disabled.activationAttempts.runCommand.requested !== true || disabled.activationAttempts.runCommand.sideEffectsUnchanged !== true || disabled.after.commandActive !== false || disabled.after.actionEnabled !== false) fail('disabled command-manager activation was not blocked cleanly.') const failure = report.workflows?.failure if (failure?.workflowId !== report.family.id || failure.commandId !== report.family.primaryCommand || failure.state !== 'failure' || failure.success !== true) fail('failure workflow identity is invalid.') if (failure.before?.activeWorkbench !== 'PartDesignWorkbench' || failure.before.commandRegistered !== true || failure.before.commandActive !== true || failure.before.actionCount < 1 || typeof failure.before.actionEnabled !== 'boolean' || failure.before.baseline?.selection?.join(',') !== 'Sketch' || failure.before.baseline.sketchGeometryCount !== 2 || failure.before.baseline.bodyTip !== '') fail('native failure preconditions are incomplete.') if (failure.taskPanel?.opened?.activeDialog !== true || failure.taskPanel.opened.inEdit !== 'Pad' || failure.taskPanel.preview?.exists !== true || failure.taskPanel.preview.typeId !== 'PartDesign::Pad' || failure.taskPanel.preview.profile !== 'Sketch' || failure.taskPanel.preview.shapeNull !== true || !failure.taskPanel.preview.state?.includes('Invalid') || !failure.taskPanel.preview.statusString) fail('invalid Pad preview evidence is incomplete.') const warning = failure.diagnostic?.warnings?.[0] if (failure.diagnostic?.requested !== true || failure.diagnostic.warnings.length !== 1 || warning.title !== 'Input error' || warning.text !== failure.taskPanel.preview.statusString) fail('native Pad failure diagnostic is incomplete.') if (failure.taskPanel.afterAttempt?.taskPanel?.activeDialog !== true || failure.taskPanel.afterAttempt.taskPanel.inEdit !== 'Pad' || failure.taskPanel.afterAttempt.padExists !== true || failure.taskPanel.afterAttempt.padShapeNull !== true || failure.taskPanel.afterAttempt.transaction?.active !== true) fail('failed Pad Task was not retained for correction.') if (failure.after?.rejectRequested !== true || failure.after.taskPanel?.activeDialog !== false || failure.after.taskPanel.inEdit !== '' || failure.after.padExists !== false || JSON.stringify(failure.after.objectNames) !== JSON.stringify(failure.before.baseline.objectNames) || failure.after.bodyTip !== failure.before.baseline.bodyTip || failure.after.sketchGeometryCount !== failure.before.baseline.sketchGeometryCount || failure.after.sketchShapeValid !== failure.before.baseline.sketchShapeValid || failure.after.transaction?.active !== false) fail('failed Pad cleanup did not restore the last valid document state.') const cancel = report.workflows?.cancel if (cancel?.workflowId !== report.family.id || cancel.commandId !== report.family.primaryCommand || cancel.state !== 'cancel' || cancel.success !== true || cancel.nativeSelectionOutcome !== 'selected-profile-consumed' || cancel.nativeFocusOutcome !== 'task-view-after-cancel') fail('cancel workflow identity is invalid.') if (cancel.before?.activeWorkbench !== 'PartDesignWorkbench' || cancel.before.commandRegistered !== true || cancel.before.commandActive !== true || cancel.before.actionCount < 1 || typeof cancel.before.actionEnabled !== 'boolean' || cancel.before.baseline?.selection?.join(',') !== 'Sketch' || cancel.before.baseline.activeBody !== 'Body' || cancel.before.baseline.focus?.className !== 'Gui::View3DInventorViewer' || cancel.before.baseline.focus.objectName !== '') fail('native cancel preconditions are incomplete.') if (cancel.taskPanel?.opened?.activeDialog !== true || cancel.taskPanel.opened.inEdit !== 'Pad' || cancel.taskPanel.preview?.exists !== true || cancel.taskPanel.preview.typeId !== 'PartDesign::Pad' || cancel.taskPanel.preview.length !== 17.5 || cancel.taskPanel.preview.shapeValid !== true || cancel.taskPanel.preview.solidCount !== 1 || cancel.taskPanel.preview.volume !== 210 || cancel.taskPanel.preview.bodyTip !== 'Pad' || cancel.taskPanel.preview.activeBody !== 'Body' || cancel.taskPanel.preview.selection?.length !== 0 || cancel.taskPanel.preview.transaction?.active !== true) fail('native Pad cancel preview evidence is incomplete.') if (cancel.after?.rejectRequested !== true || cancel.after.taskPanel?.activeDialog !== false || cancel.after.taskPanel.inEdit !== '' || cancel.after.padExists !== false || JSON.stringify(cancel.after.objectNames) !== JSON.stringify(cancel.before.baseline.objectNames) || cancel.after.bodyTip !== cancel.before.baseline.bodyTip || cancel.after.activeBody !== cancel.before.baseline.activeBody || cancel.after.selection?.length !== 0 || cancel.after.focus?.className !== 'Gui::TaskView::TaskView' || cancel.after.focus.objectName !== 'Tasks' || cancel.after.sketchGeometryCount !== cancel.before.baseline.sketchGeometryCount || cancel.after.sketchShapeValid !== cancel.before.baseline.sketchShapeValid || cancel.after.sketchVisible !== true || cancel.after.transaction?.active !== false) fail('cancelled Pad did not restore the native document and active Body or expose the native TaskView focus outcome.') const recovery = report.workflows?.recovery if (recovery?.workflowId !== report.family.id || recovery.commandId !== report.family.primaryCommand || recovery.state !== 'recovery' || recovery.success !== true) fail('recovery workflow identity is invalid.') if (recovery.before?.sketchGeometryCount !== 2 || recovery.before.padExists !== false || recovery.before.bodyTip !== '' || recovery.before.transaction?.active !== false) fail('native recovery open-wire baseline is incomplete.') const recoveryWarning = recovery.initialFailure?.diagnostic?.warnings?.[0] if (recovery.initialFailure?.taskPanel?.activeDialog !== true || recovery.initialFailure.taskPanel.inEdit !== 'Pad' || recovery.initialFailure.padShapeNull !== true || !recovery.initialFailure.padState?.includes('Invalid') || recoveryWarning?.title !== 'Input error' || recoveryWarning.text !== 'Wire is not closed.' || recovery.initialFailure.afterAttempt?.activeDialog !== true || recovery.initialFailure.afterAttempt.inEdit !== 'Pad') fail('native recovery failure phase is incomplete.') if (recovery.repairedPreview?.taskPanel?.activeDialog !== true || recovery.repairedPreview.taskPanel.inEdit !== 'Pad' || recovery.repairedPreview.lengthInputUpdated !== true || recovery.repairedPreview.sketchGeometryCount !== 4 || recovery.repairedPreview.padLength !== 12 || recovery.repairedPreview.padShapeValid !== true || recovery.repairedPreview.padSolidCount !== 1 || recovery.repairedPreview.padVolume !== 144 || recovery.repairedPreview.transaction?.active !== true) fail('native repaired Pad preview is incomplete.') const assertRecoveredPad = (value, phase) => { if (!value || value.padExists !== true || value.bodyTip !== 'Pad' || value.bodyGroup?.join(',') !== 'Sketch,Pad' || value.sketchGeometryCount !== 4 || value.padTypeId !== 'PartDesign::Pad' || value.padLength !== 12 || value.padProfile !== 'Sketch' || value.padShapeValid !== true || value.padSolidCount !== 1 || value.padFaceCount !== 6 || value.padEdgeCount !== 12 || value.padVertexCount !== 8 || value.padVolume !== 144 || value.padState?.join(',') !== 'Up-to-date' || value.transaction?.active !== false) fail(`native recovered Pad ${phase} state is incomplete.`) } if (recovery.committed?.acceptRequested !== true || recovery.committed.taskPanel?.activeDialog !== false || recovery.committed.taskPanel.inEdit !== '') fail('repaired Pad Task did not commit cleanly.') assertRecoveredPad(recovery.committed, 'commit') if (recovery.undo?.padExists !== false || recovery.undo.sketchGeometryCount !== 2 || recovery.undo.bodyTip !== '' || recovery.undo.redoCount < 1 || recovery.undo.transaction?.active !== false) fail('native recovery Undo did not restore the failed-workflow baseline.') assertRecoveredPad(recovery.redo, 'redo') if (recovery.redo.undoCount < 1) fail('native recovery Redo did not restore an undoable Pad.') const persistencePhases = { saved: 'saved', reopened: 'reopened', resavedReopened: 'resaved-reopened', } if (Object.keys(recovery.persistence ?? {}).sort().join(',') !== Object.keys(persistencePhases).sort().join(',')) fail('native recovery persistence phases are incomplete.') for (const [phase, value] of Object.entries(recovery.persistence)) { assertRecoveredPad(value, phase) if (value.phase !== persistencePhases[phase]) fail(`native recovery ${phase} phase identity is incomplete.`) if (!value.fileName?.endsWith('/partdesign-pad-recovery.FCStd')) fail(`native recovery ${phase} file provenance is incomplete.`) } if (JSON.stringify(report.remainingStates) !== JSON.stringify([]) || report.exactPromotionReady !== false) fail('remaining workflow boundary is incorrect.') console.log(JSON.stringify({ status: 'freecad-gui-workflow-pass', family: report.family.id, command: report.family.primaryCommand, capturedStates: Object.keys(report.workflows), remainingStates: report.remainingStates, disabledNoSideEffects: true, failureDiagnostic: warning.text, failureRolledBack: true, cancelPreviewVolume: cancel.taskPanel.preview.volume, cancelRolledBack: true, recoveryVolume: recovery.persistence.resavedReopened.padVolume, recoveryResaved: true, bodyTip: success.after.bodyTip, volume: pad.volume, undoNames: success.after.undoNames, }, null, 2))