Skip to main content

Work Order State Machine Specification

Document Type: Technical Specification
Version: 1.0 | Date: 2026-02-13
Compliance: FDA 21 CFR Part 11, HIPAA, SOC 2


1. State Definitions

1.1 Work Order States

StateDescriptionTerminalEditable Fields
DRAFTInitial creation; metadata being populatedNoAll fields
PLANNEDRequirements defined; job plan attachedNoDetail, priority, job plan, schedule
SCHEDULEDResources allocated; timeline confirmedNoSchedule, assignee
IN_PROGRESSActive execution underwayNoExecution notes, time entries
PENDING_REVIEWExecution complete; awaiting approvalNoNone (locked)
APPROVEDSystem Owner + QA (if regulatory) approvedNoNone (locked)
REJECTEDReviewer rejected; requires reworkNoCreates new DRAFT revision
COMPLETEDAll post-approval tasks confirmed doneYesNone (immutable)
CANCELLEDTerminated with justificationYesNone (immutable)

1.2 State Categories

MUTABLE STATES:    { DRAFT, PLANNED, SCHEDULED, IN_PROGRESS }
FROZEN STATES: { PENDING_REVIEW, APPROVED, REJECTED }
TERMINAL STATES: { COMPLETED, CANCELLED }

2. Transition Map

2.1 Valid Transitions

DRAFT ──────────→ PLANNED ──────────→ SCHEDULED ──────────→ IN_PROGRESS
│ │ │ │
│ │ │ ▼
│ │ │ PENDING_REVIEW
│ │ │ │ │
│ │ │ ▼ ▼
│ │ │ APPROVED REJECTED
│ │ │ │ │
│ │ │ ▼ │
│ │ │ COMPLETED │
│ │ │ │
▼ ▼ ▼ ▼
CANCELLED ←──────────────────────────────────────────── (any non-terminal)

REJECTED ────→ DRAFT (new revision, version++)

2.2 Transition Table

FromToGuard ConditionsActionsRequired Role
DRAFTPLANNEDoriginator set, item set, summary+detail presentAudit: PLAN_CREATEDORIGINATOR, ASSIGNER
PLANNEDSCHEDULEDjob_plan_id set, schedule_id set, min requirements definedAudit: SCHEDULEDASSIGNER
SCHEDULEDIN_PROGRESSassignee acknowledged (e-sig or login-bound action)Create TimeEntry.actual_start_atASSIGNEE
IN_PROGRESSPENDING_REVIEWall child WOs ≥ PENDING_REVIEW or COMPLETED; all TimeEntries closedLock mutable fieldsASSIGNEE, ASSIGNER
PENDING_REVIEWAPPROVEDSystem Owner approval + QA approval (if regulatory_flag=true)Lock fields, log Part 11 signatureSYSTEM_OWNER, QA
PENDING_REVIEWREJECTEDReviewer records rejection with commentCreate rejection recordSYSTEM_OWNER, QA
APPROVEDCOMPLETEDall post-approval tasks confirmed (asset updated, golden image, docs)Archive, finalize audit trailSYSTEM_OWNER
REJECTEDDRAFTCreates new revision (version++)Copy fields, reset state, link to prior versionORIGINATOR, ASSIGNER
Any non-terminalCANCELLEDauthorized role + justification text capturedLog cancellation reasonSYSTEM_OWNER, QA, ADMIN

3. Guard Specifications

3.1 DRAFT → PLANNED

interface DraftToPlannedGuard {
conditions: {
originator_set: boolean; // originator_id NOT NULL
item_set: boolean; // item_id NOT NULL, ChangeItem exists
summary_present: boolean; // summary.length > 0
detail_present: boolean; // detail.length > 0
source_type_set: boolean; // source_type IN ('AUTOMATION','EXTERNAL_VENDOR','MANUAL')
};
audit_action: 'PLAN_CREATED';
signature_required: false;
}

3.2 PLANNED → SCHEDULED

interface PlannedToScheduledGuard {
conditions: {
job_plan_attached: boolean; // job_plan_id NOT NULL, JobPlan exists
schedule_attached: boolean; // schedule_id NOT NULL, Schedule exists
min_requirements_defined: boolean; // ≥1 WorkOrderMinimumRequirement exists
assignee_set: boolean; // assignee_id NOT NULL
assigner_set: boolean; // assigner_id NOT NULL
dependency_check: boolean; // if dependencies exist, all predecessor WOs ≥ SCHEDULED
};
audit_action: 'SCHEDULED';
signature_required: false;
}

3.3 SCHEDULED → IN_PROGRESS

interface ScheduledToInProgressGuard {
conditions: {
assignee_acknowledged: boolean; // e-signature or login-bound action recorded
schedule_window_open: boolean; // current_time ≥ schedule.expected_start_at (soft)
dependencies_met: boolean; // all predecessor WOs ≥ IN_PROGRESS
resources_available: boolean; // tools, materials confirmed available (soft)
};
audit_action: 'EXECUTION_STARTED';
signature_required: true; // assignee e-signature for acknowledgment
}

3.4 IN_PROGRESS → PENDING_REVIEW

interface InProgressToPendingReviewGuard {
conditions: {
// For Master WOs:
all_children_ready: boolean; // all child WOs in {PENDING_REVIEW, APPROVED, COMPLETED, CANCELLED}
no_children_in_early_state: boolean; // no child in {DRAFT, PLANNED, SCHEDULED, IN_PROGRESS}
// For all WOs:
all_time_entries_closed: boolean; // no open TimeEntry (actual_end_at NOT NULL)
execution_notes_present: boolean; // execution detail recorded
};
audit_action: 'REVIEW_REQUESTED';
signature_required: false;
}

3.5 PENDING_REVIEW → APPROVED (Part 11 Critical)

interface PendingReviewToApprovedGuard {
conditions: {
system_owner_approval: {
recorded: boolean; // Approval with role=SYSTEM_OWNER, decision=APPROVED
signature_valid: boolean; // ElectronicSignature linked, signer matches approver
signature_recent: boolean; // signed_at within configurable window (default 1 hour)
};
qa_approval: {
required: boolean; // true if regulatory_flag = true
recorded: boolean; // Approval with role=QA, decision=APPROVED
signature_valid: boolean;
signature_recent: boolean;
artifacts_verified: boolean; // IQ/OQ, WI updates, golden image evidence attached
};
no_open_deviations: boolean; // no unresolved deviation records
version_conflict_check: boolean; // optimistic concurrency: current version matches
};
audit_action: 'APPROVED';
signature_required: true; // Part 11 §11.50: Electronic signatures must be linked
field_lock: 'ALL'; // Part 11 §11.10(e): Closed records cannot be altered
}

3.6 APPROVED → COMPLETED

interface ApprovedToCompletedGuard {
conditions: {
// For Master WOs:
all_children_terminal: boolean; // all child WOs in {COMPLETED, CANCELLED}
// Post-approval tasks:
asset_state_updated: boolean; // Asset status reflects change (if applicable)
golden_image_captured: boolean; // if system change, golden image archived
documents_updated: boolean; // WIs, SOPs version-updated and approved
training_records_updated: boolean; // if new procedures, training logged
};
audit_action: 'COMPLETED';
signature_required: false;
terminal: true; // No further transitions possible
}

3.7 Cancellation Guard

interface CancellationGuard {
conditions: {
authorized_role: boolean; // performer is SYSTEM_OWNER, QA, or ADMIN
justification_present: boolean; // cancellation reason text.length > 10
// For Master WOs:
child_handling_defined: boolean; // all children either CANCELLED or explicitly excluded
no_in_progress_children: boolean; // cannot cancel if children are mid-execution
};
audit_action: 'CANCELLED';
signature_required: true; // cancellation is a controlled action
terminal: true;
}

4. Master / Linked WO Coordination

4.1 Hierarchy Rules

RuleDescription
Single masterA linked WO has exactly one master_id (or NULL for standalone)
DAG onlyDependencies form a Directed Acyclic Graph — cycles are rejected at creation
Master ceilingMaster WO cannot advance past the minimum state of its children
Child floorChild WOs cannot reach COMPLETED if master is CANCELLED (unless explicit override)
Cascade cancelCancelling a master offers to cascade-cancel all non-terminal children

4.2 Master State Derived Rules

Master.effective_state = min(Master.own_state, min(children.states))

Example:
Master: IN_PROGRESS
Child A: APPROVED
Child B: IN_PROGRESS
Child C: PENDING_REVIEW
→ Master cannot advance to PENDING_REVIEW until Child B reaches PENDING_REVIEW

4.3 Dependency Graph Validation

function validateDependencyDAG(workOrderId: string, dependencies: string[]): ValidationResult {
// Build adjacency list
// Run topological sort (Kahn's algorithm)
// If cycle detected → reject with cycle path
// If valid → return topological order for scheduling

// Critical: This runs on every dependency addition, not just at transition time
// Prevents cycles from being introduced at any point
}

5. Audit Trail Requirements (Part 11 §11.10)

5.1 Every Transition Generates

interface AuditEntry {
id: string; // Immutable, system-generated
entity_type: 'WORK_ORDER';
entity_id: string; // work_order.id
action: TransitionAction; // Enum of all transition types
performed_by: string; // person.id (authenticated user)
performed_at: DateTime; // Server-side timestamp, not client
previous_value: {
status: WOStatus;
version: number;
fields_changed: Record<string, any>;
};
new_value: {
status: WOStatus;
version: number;
fields_changed: Record<string, any>;
};
signature_id?: string; // If e-signature was required
ip_address: string; // Request origin
session_id: string; // Authenticated session
tenant_id: string; // Multi-tenant isolation
}

5.2 Immutability Enforcement

-- Database trigger: prevent UPDATE or DELETE on audit_trail
CREATE OR REPLACE FUNCTION prevent_audit_modification()
RETURNS TRIGGER AS $$
BEGIN
RAISE EXCEPTION 'Audit trail records are immutable. Operation % denied.', TG_OP;
RETURN NULL;
END;
$$ LANGUAGE plpgsql;

CREATE TRIGGER audit_trail_immutable
BEFORE UPDATE OR DELETE ON audit_trail
FOR EACH ROW
EXECUTE FUNCTION prevent_audit_modification();

6. Electronic Signature Integration (Part 11 §11.50, §11.70)

6.1 Signature-Required Transitions

TransitionSignature RequiredMeaning of Signature
SCHEDULED → IN_PROGRESSYes (assignee)"I acknowledge responsibility for this task"
PENDING_REVIEW → APPROVEDYes (System Owner + QA)"I approve this change to the validated system"
PENDING_REVIEW → REJECTEDYes (reviewer)"I reject this change with stated reasons"
Any → CANCELLEDYes (authorized role)"I authorize cancellation with stated justification"

6.2 Signature Validation Rules

interface SignatureValidation {
signer_matches_actor: boolean; // signature.signer_id === action.performed_by
signature_is_recent: boolean; // signature.signed_at within 1 hour of action
auth_method_acceptable: boolean; // password re-entry, smartcard, or SSO re-auth
meaning_matches_action: boolean; // signature.meaning matches transition type
no_signature_reuse: boolean; // signature not linked to any other approval
signer_has_role: boolean; // signer has required role for this transition
}

This specification defines the complete behavioral contract for the WO lifecycle engine. All implementations must satisfy these guards and audit requirements to maintain regulatory compliance.