use super::*;
use crate::reducer::state::PromptPermissionsState;
#[test]
fn test_orchestration_derives_lock_permissions_before_planning() {
let state = PipelineState {
phase: PipelinePhase::Planning,
prompt_permissions: PromptPermissionsState {
locked: false,
restore_needed: false,
restored: false,
last_warning: None,
},
..PipelineState::initial(1, 0)
};
let effect = determine_next_effect(&state);
assert!(
matches!(effect, Effect::LockPromptPermissions),
"Expected LockPromptPermissions, got {effect:?}"
);
}
#[test]
fn test_orchestration_skips_lock_when_already_locked() {
use crate::agents::AgentRole;
use crate::reducer::state::AgentChainState;
let state = PipelineState {
phase: PipelinePhase::Planning,
prompt_permissions: PromptPermissionsState {
locked: true,
restore_needed: true,
restored: false,
last_warning: None,
},
gitignore_entries_ensured: true, context_cleaned: true, agent_chain: AgentChainState::initial()
.with_agents(
vec!["agent1".to_string()],
vec![vec!["model1".to_string()]],
AgentRole::Developer,
)
.with_drain(crate::agents::AgentDrain::Planning),
..PipelineState::initial(1, 0)
};
let effect = determine_next_effect(&state);
assert!(
matches!(
effect,
Effect::MaterializePlanningInputs { .. } | Effect::PreparePlanningPrompt { .. }
),
"Expected planning work, got {effect:?}"
);
}
#[test]
fn test_orchestration_derives_restore_permissions_on_interrupted() {
let state = PipelineState {
phase: PipelinePhase::Interrupted,
previous_phase: Some(PipelinePhase::AwaitingDevFix),
prompt_permissions: PromptPermissionsState {
locked: true,
restore_needed: true,
restored: false,
last_warning: None,
},
checkpoint_saved_count: 0,
..PipelineState::initial(1, 0)
};
let effect = determine_next_effect(&state);
assert!(
matches!(effect, Effect::RestorePromptPermissions),
"Expected RestorePromptPermissions, got {effect:?}"
);
}
#[test]
fn test_orchestration_saves_checkpoint_after_restore_on_interrupted() {
let state = PipelineState {
phase: PipelinePhase::Interrupted,
previous_phase: Some(PipelinePhase::AwaitingDevFix),
prompt_permissions: PromptPermissionsState {
locked: true,
restore_needed: true,
restored: true,
last_warning: None,
},
checkpoint_saved_count: 0,
..PipelineState::initial(1, 0)
};
let effect = determine_next_effect(&state);
assert!(
matches!(effect, Effect::CheckUncommittedChangesBeforeTermination),
"Expected CheckUncommittedChangesBeforeTermination, got {effect:?}"
);
}
#[test]
fn test_orchestration_saves_checkpoint_after_restore_and_safety_check_on_interrupted() {
let state = PipelineState {
phase: PipelinePhase::Interrupted,
previous_phase: Some(PipelinePhase::AwaitingDevFix),
prompt_permissions: PromptPermissionsState {
locked: true,
restore_needed: true,
restored: true,
last_warning: None,
},
checkpoint_saved_count: 0,
interrupted_by_user: false,
pre_termination_commit_checked: true,
..PipelineState::initial(1, 0)
};
let effect = determine_next_effect(&state);
assert!(
matches!(effect, Effect::SaveCheckpoint { .. }),
"Expected SaveCheckpoint, got {effect:?}"
);
}
#[test]
fn test_finalizing_always_derives_restore_permissions() {
let state = PipelineState {
phase: PipelinePhase::Finalizing,
prompt_permissions: PromptPermissionsState {
locked: true,
restore_needed: true,
restored: false,
last_warning: None,
},
..PipelineState::initial(1, 0)
};
let effect = determine_next_effect(&state);
assert!(
matches!(effect, Effect::RestorePromptPermissions),
"Finalizing must derive RestorePromptPermissions, got {effect:?}"
);
}
#[test]
fn test_interrupted_phase_restores_prompt_md_when_restore_not_needed() {
let state = PipelineState {
phase: PipelinePhase::Interrupted,
interrupted_by_user: true,
prompt_permissions: PromptPermissionsState {
locked: false,
restore_needed: false, restored: false,
last_warning: None,
},
..PipelineState::initial(1, 0)
};
let effect = determine_next_effect(&state);
assert!(
matches!(effect, Effect::RestorePromptPermissions),
"Expected RestorePromptPermissions even when restore_needed=false, got {effect:?}. \
User interrupts should ALWAYS attempt restoration for safety."
);
}
#[test]
fn test_programmatic_interrupt_requires_pre_termination_safety_check() {
let mut state = PipelineState {
phase: PipelinePhase::Interrupted,
interrupted_by_user: false,
pre_termination_commit_checked: false, prompt_permissions: PromptPermissionsState {
locked: false,
restore_needed: false,
restored: false,
last_warning: None,
},
..PipelineState::initial(1, 0)
};
state.previous_phase = Some(PipelinePhase::AwaitingDevFix);
let effect = determine_next_effect(&state);
assert!(
matches!(effect, Effect::CheckUncommittedChangesBeforeTermination),
"Expected CheckUncommittedChangesBeforeTermination for programmatic interrupt, got {effect:?}"
);
}