mod under_said;
use crate::boundary::config::ConfigFile;
use crate::boundary::config::Write;
use crate::boundary::line::tests::ctx;
use crate::boundary::line::{Context, parse, spell};
use crate::boundary::{Action, Gesture, help};
use crate::config_edit::branch::edit::EditOrigin;
use crate::model_pick::{Effort, Tuning};
fn rt(gesture: Gesture) {
let line = spell(&gesture);
assert_eq!(parse(&line, &ctx()), Ok(gesture.clone()), "via {line}");
let verb = line
.split_whitespace()
.next()
.unwrap_or_default()
.trim_start_matches('/');
assert!(help::known(verb), "/{verb} has no help page");
}
fn applying(file: ConfigFile) -> Gesture {
Gesture::Act(Action::Config(Write::Apply {
file,
text: "roles:\n worker:\n provider: codex".to_owned(),
}))
}
fn brazen() -> ConfigFile {
ConfigFile::Brazen {
workspace: "ws".to_owned(),
}
}
fn branch(origin: EditOrigin) -> ConfigFile {
ConfigFile::Branch {
workspace: "ws".to_owned(),
lineage: "default".to_owned(),
origin,
path: "providers.yaml".to_owned(),
}
}
#[test]
fn every_config_destination_round_trips_as_a_line() {
for file in [
brazen(),
ConfigFile::LitanyModels,
ConfigFile::Cadence,
ConfigFile::LitanyWorkflow {
name: "review".to_owned(),
},
branch(EditOrigin::Advance),
branch(EditOrigin::Fork {
source: "base".to_owned(),
}),
branch(EditOrigin::Orphan),
] {
rt(applying(file));
}
}
#[test]
fn a_marks_amendment_and_a_pick_round_trip_as_lines() {
for branch in ["balls/tasks", "balls/agents/corp"] {
rt(Gesture::Act(Action::Config(Write::Marks {
workspace: "ws".to_owned(),
branch: branch.to_owned(),
})));
}
rt(Gesture::Act(Action::Config(Write::Pick {
workspace: "ws".to_owned(),
role: "worker".to_owned(),
provider: "codex".to_owned(),
model: "gpt-5.4".to_owned(),
})));
}
#[test]
fn every_tuning_arm_round_trips_as_a_line() {
for level in [
Some(Effort::Low),
Some(Effort::Medium),
Some(Effort::High),
None,
] {
rt(Gesture::Act(Action::Config(Write::Tune(Tuning::Effort {
workspace: "ws".to_owned(),
role: "worker".to_owned(),
level,
}))));
}
for on in [true, false] {
rt(Gesture::Act(Action::Config(Write::Tune(
Tuning::Priority {
workspace: "ws".to_owned(),
role: "compactor".to_owned(),
on,
},
))));
}
}
#[test]
fn a_word_outside_either_vocabulary_refuses_naming_the_whole_of_it() {
for line in [
"/effort worker highest",
"/effort worker",
"/effort worker low extra",
] {
let said = crate::boundary::line::parse(line, &ctx()).expect_err("refused");
assert!(said.contains("low|medium|high|off"), "{line}: {said}");
}
for line in ["/priority worker yes", "/priority worker", "/priority"] {
let said = crate::boundary::line::parse(line, &ctx()).expect_err("refused");
assert!(said.contains("on|off"), "{line}: {said}");
}
}
#[test]
fn the_text_is_the_whole_tail_and_no_flag_is_read_out_of_it() {
let read = parse("/config cadence a: 1\n--body: not a flag", &ctx());
assert_eq!(
read,
Ok(Gesture::Act(Action::Config(Write::Apply {
file: ConfigFile::Cadence,
text: "a: 1\n--body: not a flag".to_owned(),
})))
);
}
#[test]
fn a_lineage_destination_takes_its_workspace_from_the_seat() {
let read = parse("/config branch strict workflow.yaml events: {}", &ctx());
assert_eq!(
read,
Ok(Gesture::Act(Action::Config(Write::Apply {
file: ConfigFile::Branch {
workspace: "ws".to_owned(),
lineage: "strict".to_owned(),
origin: EditOrigin::Advance,
path: "workflow.yaml".to_owned(),
},
text: "events: {}".to_owned(),
})))
);
let err = parse("/config branch strict workflow.yaml x", &Context::default()).unwrap_err();
assert!(err.contains("no workspace in context"), "{err}");
}