TUI: Remove core protocol dependency [3/7] (#20174)

## Why

This is part 3 of a 7-PR stack to remove direct
`codex_protocol::protocol` usage from `codex-tui` while keeping each
layer reviewable and shippable.

With `AppCommand` now explicit, the internal app event bus can carry TUI
commands directly instead of bouncing through core `Op` values.

## What changed

- Changed `AppEvent::CodexOp` and `AppEvent::SubmitThreadOp` to carry
`AppCommand`.
- Updated app-event senders and direct emitters to submit `AppCommand`
values.
- Adjusted tests to match `AppCommand` or convert back through
`into_core()` where they intentionally assert legacy payload equality.

## Verification

- `cargo test -p codex-tui --no-run`
This commit is contained in:
Eric Traut authored and GitHub committed 2026-04-29 10:52:10 -07:00
1 parent 445629815c
commit d0204c3dcc
19 files changed
+165 -152

No files matched your search

+44 -55
View File
@@ -8313,22 +8313,19 @@ impl ChatWidget {
let default_effort: ReasoningEffortConfig = preset.default_reasoning_effort;
let switch_actions: Vec<SelectionAction> = vec![Box::new(move |tx| {
tx.send(AppEvent::CodexOp(
AppCommand::override_turn_context(
/*cwd*/ None,
/*approval_policy*/ None,
/*approvals_reviewer*/ None,
/*permission_profile*/ None,
/*windows_sandbox_level*/ None,
Some(switch_model_for_events.clone()),
Some(Some(default_effort)),
/*summary*/ None,
/*service_tier*/ None,
/*collaboration_mode*/ None,
/*personality*/ None,
)
.into_core(),
));
tx.send(AppEvent::CodexOp(AppCommand::override_turn_context(
/*cwd*/ None,
/*approval_policy*/ None,
/*approvals_reviewer*/ None,
/*permission_profile*/ None,
/*windows_sandbox_level*/ None,
Some(switch_model_for_events.clone()),
Some(Some(default_effort)),
/*summary*/ None,
/*service_tier*/ None,
/*collaboration_mode*/ None,
/*personality*/ None,
)));
tx.send(AppEvent::UpdateModel(switch_model_for_events.clone()));
tx.send(AppEvent::UpdateReasoningEffort(Some(default_effort)));
})];
@@ -8537,22 +8534,19 @@ impl ChatWidget {
let name = Self::personality_label(personality).to_string();
let description = Some(Self::personality_description(personality).to_string());
let actions: Vec<SelectionAction> = vec![Box::new(move |tx| {
tx.send(AppEvent::CodexOp(
AppCommand::override_turn_context(
/*cwd*/ None,
/*approval_policy*/ None,
/*approvals_reviewer*/ None,
/*permission_profile*/ None,
/*windows_sandbox_level*/ None,
/*model*/ None,
/*effort*/ None,
/*summary*/ None,
/*service_tier*/ None,
/*collaboration_mode*/ None,
Some(personality),
)
.into_core(),
));
tx.send(AppEvent::CodexOp(AppCommand::override_turn_context(
/*cwd*/ None,
/*approval_policy*/ None,
/*approvals_reviewer*/ None,
/*permission_profile*/ None,
/*windows_sandbox_level*/ None,
/*model*/ None,
/*effort*/ None,
/*summary*/ None,
/*service_tier*/ None,
/*collaboration_mode*/ None,
Some(personality),
)));
tx.send(AppEvent::UpdatePersonality(personality));
tx.send(AppEvent::PersistPersonalitySelection { personality });
})];
@@ -9567,7 +9561,7 @@ impl ChatWidget {
self.app_event_tx.send(AppEvent::SubmitThreadOp {
thread_id,
op: Op::ApproveGuardianDeniedAction { event },
op: AppCommand::from(Op::ApproveGuardianDeniedAction { event }),
});
self.add_info_message(
"Approval recorded for one retry of the selected auto-review denial.".to_string(),
@@ -9605,22 +9599,19 @@ impl ChatWidget {
) -> Vec<SelectionAction> {
vec![Box::new(move |tx| {
let permission_profile_clone = permission_profile.clone();
tx.send(AppEvent::CodexOp(
AppCommand::override_turn_context(
/*cwd*/ None,
Some(approval),
Some(approvals_reviewer),
Some(permission_profile_clone.clone()),
/*windows_sandbox_level*/ None,
/*model*/ None,
/*effort*/ None,
/*summary*/ None,
/*service_tier*/ None,
/*collaboration_mode*/ None,
/*personality*/ None,
)
.into_core(),
));
tx.send(AppEvent::CodexOp(AppCommand::override_turn_context(
/*cwd*/ None,
Some(approval),
Some(approvals_reviewer),
Some(permission_profile_clone.clone()),
/*windows_sandbox_level*/ None,
/*model*/ None,
/*effort*/ None,
/*summary*/ None,
/*service_tier*/ None,
/*collaboration_mode*/ None,
/*personality*/ None,
)));
tx.send(AppEvent::UpdateAskForApprovalPolicy(approval));
tx.send(AppEvent::UpdatePermissionProfile(permission_profile_clone));
tx.send(AppEvent::UpdateApprovalsReviewer(approvals_reviewer));
@@ -10457,8 +10448,8 @@ impl ChatWidget {
self.config.notices.fast_default_opt_out = Some(true);
}
self.set_service_tier(service_tier);
self.app_event_tx.send(AppEvent::CodexOp(
AppCommand::override_turn_context(
self.app_event_tx
.send(AppEvent::CodexOp(AppCommand::override_turn_context(
/*cwd*/ None,
/*approval_policy*/ None,
/*approvals_reviewer*/ None,
@@ -10470,9 +10461,7 @@ impl ChatWidget {
Some(service_tier),
/*collaboration_mode*/ None,
/*personality*/ None,
)
.into_core(),
));
)));
self.app_event_tx
.send(AppEvent::PersistServiceTierSelection { service_tier });
}
@@ -11539,7 +11528,7 @@ impl ChatWidget {
}
}
CodexOpTarget::AppEvent => {
self.app_event_tx.send(AppEvent::CodexOp(op.into()));
self.app_event_tx.send(AppEvent::CodexOp(op));
}
}
true