§9 acceptance: grep-zero sweep — every internal x.ai/grok identifier renamed

The PRD's first acceptance gate now holds: grep -RinE '\bx\.ai\b|grok'
crates/ --include='*.rs' → 0 matches (exempt: NOTICE and third-party
license archives, README provenance, and the required 'Based on Grok
Build Open Source' attribution, now sourced from version_attribution.txt).

Wire-visible renames (both sides in this repo, changed in lockstep):
- Auth method id 'grok.com' → 'kimi-code' (AuthMethodKind::KimiCode).
- Every x.ai/* and _x.ai/* ACP ext method and meta key → kigi/* /
  _kigi/* (~200 names; grokShell → kigiShell). Session-file replay keeps
  a read-side alias for the legacy '_x.ai/session/update' method so
  existing updates.jsonl histories load; writes emit only the new name
  (both directions test-pinned).
- Agent types grok-build* → kigi* with a documented legacy-prefix alias
  at resolution time so persisted sessions keep resolving.
- ToolNamespace/BuiltinAgentName GrokBuild* → Kigi* (wire snake_case
  kigi/kigi_concise/kigi_hashline; schema regenerated); grok_build
  implementation dirs renamed to kigi*.
- x-grok-* headers → x-kigi-*, __GROK_* sentinels → __KIGI_*, themes
  grokday/groknight → kigiday/kiginight (old persisted values fall back
  to the default theme), web_fetch allowlist xAI hosts → kimi.com +
  moonshot platforms, changelog CDN → this repo, grok-build changelog
  archives deleted.
- BYOK default endpoint removed: [endpoints] api_base_url is now truly
  optional with NO default — consumers fail fast with the flag name when
  unset (no silent x.ai egress). Mock harnesses inject it explicitly.
- System-prompt identity fixed: 'released by xAI' → 'an unofficial
  community CLI for Kimi' (template + regenerated encrypted form).

Also repaired pre-existing grok-era test debt found by the sweep: the
stale trace_classify default-model pin, the grok-pager UA label test,
pty-harness stale-binary reuse and non-hermetic moonshot routing (a PTY
test could previously reach the real api.moonshot.cn), and the outdated
oauth fixture scope key.

Gates: §9 grep 0; fmt clean; workspace check/clippy 0/0 (-D warnings);
FULL cargo test --workspace: 234 suites, 21,961 passed, 0 failed;
deny advisories ok.
This commit is contained in:
2026-07-18 02:48:46 -04:00
parent 86e3724310
commit 6f31415ed6
1056 changed files with 8410 additions and 18307 deletions
@@ -355,7 +355,7 @@ async fn proactive_refresh_makes_per_turn_refresh_a_cache_hit() {
fn model_not_found_error() -> kigi_sampler::SamplingErrorInfo {
kigi_sampler::SamplingErrorInfo {
kind: kigi_sampler::SamplingErrorKind::Api,
message: "API error (status 404 Not Found): The model grok-build does not exist or your team does not have access".into(),
message: "API error (status 404 Not Found): The model kigi does not exist or your team does not have access".into(),
status_code: Some(404),
is_retryable: false,
retry_after_secs: None,
@@ -379,7 +379,7 @@ fn model_not_found_error() -> kigi_sampler::SamplingErrorInfo {
fn unauthorized_401_error() -> kigi_sampler::SamplingErrorInfo {
kigi_sampler::SamplingErrorInfo {
kind: kigi_sampler::SamplingErrorKind::Api,
message: "Unauthorized (401) from https://cli-chat-proxy.kigi.com/v1/responses: {\"error\":\"Invalid or expired credentials (auth_kind=bearer, x_xai_token_auth=xai-grok-cli, upstream=Unauthenticated, reason=no auth context)\"}".into(),
message: "Unauthorized (401) from https://cli-chat-proxy.kigi.com/v1/responses: {\"error\":\"Invalid or expired credentials (auth_kind=bearer, x_xai_token_auth=xai-kigi-cli, upstream=Unauthenticated, reason=no auth context)\"}".into(),
status_code: Some(401),
is_retryable: false,
retry_after_secs: None,
@@ -553,7 +553,7 @@ async fn sampler_401_login_method_with_stale_api_key_auth_type_still_recovers()
let (_dir, am) = auth_manager_with_refresher(refresher);
let (actor, _rx) = make_actor_with_method_and_credentials(
Some(am),
"grok.com",
"kimi-code",
kigi_chat_state::AuthType::ApiKey,
"stale-session-jwt".to_string(),
)
@@ -905,7 +905,7 @@ async fn reparented_record_is_noop_without_goal_harness() {
/// subagent(s) completed" reminder.
#[tokio::test(flavor = "current_thread")]
async fn between_turn_drain_suppresses_auto_wake_delivered_subagents() {
use kigi_tools::implementations::grok_build::task::types::{
use kigi_tools::implementations::kigi::task::types::{
SubagentCompletionSummary, SubagentEvent,
};
use kigi_tools::reminders::task_completion::AutoWakeDeliveredIds;
@@ -1,4 +1,4 @@
use kigi_tools::implementations::grok_build::task::types::SubagentCompletionSummary;
use kigi_tools::implementations::kigi::task::types::SubagentCompletionSummary;
use kigi_tools::reminders::task_completion::format_between_turn_completions;
fn summary(
@@ -778,7 +778,7 @@ async fn cancel_running_task_teardown_clears_running_and_pending_work() {
agent
.tool_bridge()
.update_resource(
kigi_tools::implementations::grok_build::task::types::CurrentPromptIdResource(
kigi_tools::implementations::kigi::task::types::CurrentPromptIdResource(
"running".to_string(),
),
)
@@ -981,7 +981,7 @@ async fn cancel_running_task_teardown_clears_running_and_pending_work() {
actor.cancel_running_task(true, true, false, None).await;
let scoped_prompt_id = bridge
.read_resource::<
kigi_tools::implementations::grok_build::task::types::CurrentPromptIdResource,
kigi_tools::implementations::kigi::task::types::CurrentPromptIdResource,
>()
.await;
assert!(
@@ -1013,7 +1013,7 @@ async fn cancel_running_task_teardown_clears_running_and_pending_work() {
/// the running turn and removes ONLY the running prompt (the front of
/// `pending_inputs`). Every queued prompt is PRESERVED so the `Cancel`
/// handler's follow-up `maybe_start_running_task` promotes the new front (the
/// user's next queued prompt) and rebroadcasts `x.ai/queue/changed`. The
/// user's next queued prompt) and rebroadcasts `kigi/queue/changed`. The
/// cancelling client never pulls a queued prompt back into its input — the
/// server queue is the single source of truth for what runs next.
///
@@ -1756,7 +1756,7 @@ async fn cancel_propagates_to_sampler_handle_so_no_further_emission() {
agent
.tool_bridge()
.update_resource(
kigi_tools::implementations::grok_build::task::types::CurrentPromptIdResource(
kigi_tools::implementations::kigi::task::types::CurrentPromptIdResource(
"running".to_string(),
),
)
@@ -42,9 +42,9 @@ async fn client_hooks_fire_without_file_registry() {
.try_recv()
.expect("client hook must fire with no file registry");
let kigi_acp_lib::AcpClientMessage::ExtNotification(args) = msg else {
panic!("expected an x.ai/hooks/event ext notification");
panic!("expected an kigi/hooks/event ext notification");
};
assert_eq!(args.request.method.as_ref(), "x.ai/hooks/event");
assert_eq!(args.request.method.as_ref(), "kigi/hooks/event");
let params: serde_json::Value =
serde_json::from_str(args.request.params.get()).unwrap();
assert_eq!(params["hookCallbackId"], "cb_0");
@@ -54,7 +54,7 @@ async fn client_hooks_fire_without_file_registry() {
}
/// The PreToolUse gate blocks a tool when a client hook returns `deny`: the reverse
/// `x.ai/hooks/run` request is answered with a deny and `run_pre_tool_use_client_hook`
/// `kigi/hooks/run` request is answered with a deny and `run_pre_tool_use_client_hook`
/// returns `ToolLoop::HookDenied`. Complements the pure `classify` test by covering the
/// gate wiring (the one new path that can block tool execution).
#[tokio::test(flavor = "current_thread")]
@@ -79,7 +79,7 @@ async fn pre_tool_use_client_deny_blocks_the_tool() {
);
*actor.client_hooks.borrow_mut() = client_hooks;
// Answer the x.ai/hooks/run reverse request with a deny; ack the UI
// Answer the kigi/hooks/run reverse request with a deny; ack the UI
// notifications `deny_tool` emits so it can't block the gate.
tokio::task::spawn_local(async move {
while let Some(msg) = gateway_rx.recv().await {
@@ -431,7 +431,7 @@ async fn pre_tool_use_slow_callback_does_not_starve_a_deny() {
/// dispatch error fires only PostToolUseFailure; a successful dispatch fires only
/// PostToolUse. Guards the explicitly-hardened no-double-fire path (the PostToolUse
/// success block routes through `dispatch_hook`, the same as the failure arm). Each
/// post-tool event is observed as a fire-and-forget `x.ai/hooks/event` notification.
/// post-tool event is observed as a fire-and-forget `kigi/hooks/event` notification.
#[tokio::test(flavor = "current_thread")]
async fn post_tool_use_and_failure_never_double_fire() {
let local = tokio::task::LocalSet::new();
@@ -443,7 +443,7 @@ async fn post_tool_use_and_failure_never_double_fire() {
tokio::sync::mpsc::unbounded_channel::<PersistenceMsg>();
let actor = create_test_actor(0, 256_000, 85, gateway_tx, persistence_tx).await;
// The agent's tool bridge must know `todo_write` for it to parse + dispatch.
*actor.agent.borrow_mut() = test_grok_build_agent_with_todo().await;
*actor.agent.borrow_mut() = test_kigi_agent_with_todo().await;
let mut client_hooks = crate::extensions::hooks::ClientHooks::new();
for event in [
@@ -461,13 +461,13 @@ async fn post_tool_use_and_failure_never_double_fire() {
}
*actor.client_hooks.borrow_mut() = client_hooks;
// Collect the `hookEventName` of every `x.ai/hooks/event` notification queued.
// Collect the `hookEventName` of every `kigi/hooks/event` notification queued.
let drain =
|rx: &mut tokio::sync::mpsc::UnboundedReceiver<kigi_acp_lib::AcpClientMessage>| {
let mut events = Vec::new();
while let Ok(msg) = rx.try_recv() {
if let kigi_acp_lib::AcpClientMessage::ExtNotification(args) = msg
&& args.request.method.as_ref() == "x.ai/hooks/event"
&& args.request.method.as_ref() == "kigi/hooks/event"
{
let params: serde_json::Value =
serde_json::from_str(args.request.params.get()).unwrap();
@@ -544,7 +544,7 @@ async fn pre_tool_use_deny_feeds_reason_back_and_continues_turn() {
let actor = create_test_actor(0, 256_000, 85, gateway_tx, persistence_tx).await;
// The agent's tool bridge must know `todo_write` so it parses + reaches
// the PreToolUse gate (rather than short-circuiting as an unknown tool).
*actor.agent.borrow_mut() = test_grok_build_agent_with_todo().await;
*actor.agent.borrow_mut() = test_kigi_agent_with_todo().await;
let mut client_hooks = crate::extensions::hooks::ClientHooks::new();
client_hooks.insert(
@@ -557,7 +557,7 @@ async fn pre_tool_use_deny_feeds_reason_back_and_continues_turn() {
);
*actor.client_hooks.borrow_mut() = client_hooks;
// Answer the reverse x.ai/hooks/run request with a deny carrying a reason;
// Answer the reverse kigi/hooks/run request with a deny carrying a reason;
// ack the UI notifications `deny_tool` emits so it can't block the gate.
tokio::task::spawn_local(async move {
while let Some(msg) = gateway_rx.recv().await {
@@ -18,7 +18,7 @@ async fn tool_bridge_routes_writes_through_injected_fs() {
let config = ToolServerConfig {
tools: vec![
ToolConfig {
id: "GrokBuild:read_file".into(),
id: "Kigi:read_file".into(),
params: None,
name_override: None,
params_name_overrides: None,
@@ -27,7 +27,7 @@ async fn tool_bridge_routes_writes_through_injected_fs() {
kind: None,
},
ToolConfig {
id: "GrokBuild:search_replace".into(),
id: "Kigi:search_replace".into(),
params: Some(
serde_json::from_value(serde_json::json!({
"skip_read_before_edit": true
@@ -47,13 +47,13 @@ async fn tool_bridge_routes_writes_through_injected_fs() {
backend: terminal,
fs,
cwd: cwd.clone(),
session_folder: std::env::temp_dir().join("grok-test-fs"),
session_folder: std::env::temp_dir().join("kigi-test-fs"),
session_env: std::sync::Arc::new(std::collections::HashMap::new()),
notification_handle: ToolNotificationHandle::noop(),
owner_session_id: None,
parent_scheduler_handle: None,
skills: vec![],
state_path: std::env::temp_dir().join("grok-test-fs/tool_state.json"),
state_path: std::env::temp_dir().join("kigi-test-fs/tool_state.json"),
memory_backend: None,
web_search_config: Default::default(),
web_fetch_config: Default::default(),
@@ -459,8 +459,8 @@ async fn handle_turn_end_verified_complete_during_drain_skips_bail_nudge() {
let (tx, rx) = tokio::sync::mpsc::unbounded_channel();
*actor.goal_update_rx.borrow_mut() = Some(rx);
tx.send(
kigi_tools::implementations::grok_build::update_goal::envelope_for_test(
kigi_tools::implementations::grok_build::update_goal::UpdateGoalInput {
kigi_tools::implementations::kigi::update_goal::envelope_for_test(
kigi_tools::implementations::kigi::update_goal::UpdateGoalInput {
completed: Some(true),
message: None,
blocked_reason: None,
@@ -1436,8 +1436,8 @@ async fn drain_goal_updates_blocked_reason_transitions_after_three_attempts() {
let (tx, rx) = tokio::sync::mpsc::unbounded_channel();
*actor.goal_update_rx.borrow_mut() = Some(rx);
tx.send(
kigi_tools::implementations::grok_build::update_goal::envelope_for_test(
kigi_tools::implementations::grok_build::update_goal::UpdateGoalInput {
kigi_tools::implementations::kigi::update_goal::envelope_for_test(
kigi_tools::implementations::kigi::update_goal::UpdateGoalInput {
completed: None,
message: Some("longer body".into()),
blocked_reason: Some("short label".into()),
@@ -1479,8 +1479,8 @@ async fn drain_goal_updates_blocked_reason_rejected_below_threshold() {
let (tx, rx) = tokio::sync::mpsc::unbounded_channel();
*actor.goal_update_rx.borrow_mut() = Some(rx);
tx.send(
kigi_tools::implementations::grok_build::update_goal::envelope_for_test(
kigi_tools::implementations::grok_build::update_goal::UpdateGoalInput {
kigi_tools::implementations::kigi::update_goal::envelope_for_test(
kigi_tools::implementations::kigi::update_goal::UpdateGoalInput {
completed: None,
message: None,
blocked_reason: Some("only label".into()),
@@ -1580,8 +1580,8 @@ async fn drain_goal_updates_blocked_reason_against_non_active_does_not_stash_pau
let (tx, rx) = tokio::sync::mpsc::unbounded_channel();
*actor.goal_update_rx.borrow_mut() = Some(rx);
tx.send(
kigi_tools::implementations::grok_build::update_goal::envelope_for_test(
kigi_tools::implementations::grok_build::update_goal::UpdateGoalInput {
kigi_tools::implementations::kigi::update_goal::envelope_for_test(
kigi_tools::implementations::kigi::update_goal::UpdateGoalInput {
completed: None,
message: Some("body".into()),
blocked_reason: Some("would-block".into()),
@@ -1625,7 +1625,7 @@ async fn drain_goal_updates_completes_after_blocked_does_not_leak_pause_message(
.store(2, Ordering::Relaxed);
let (tx, rx) = tokio::sync::mpsc::unbounded_channel();
*actor.goal_update_rx.borrow_mut() = Some(rx);
tx.send(kigi_tools::implementations::grok_build::update_goal::envelope_for_test(kigi_tools::implementations::grok_build::update_goal::UpdateGoalInput {
tx.send(kigi_tools::implementations::kigi::update_goal::envelope_for_test(kigi_tools::implementations::kigi::update_goal::UpdateGoalInput {
completed: None,
message: None,
blocked_reason: Some("blk".into()),
@@ -1641,7 +1641,7 @@ async fn drain_goal_updates_completes_after_blocked_does_not_leak_pause_message(
// accepts complete() from any paused variant (including
// Blocked), and the pause_message
// is cleared during the transition.
tx.send(kigi_tools::implementations::grok_build::update_goal::envelope_for_test(kigi_tools::implementations::grok_build::update_goal::UpdateGoalInput {
tx.send(kigi_tools::implementations::kigi::update_goal::envelope_for_test(kigi_tools::implementations::kigi::update_goal::UpdateGoalInput {
completed: Some(true),
message: None,
@@ -1675,8 +1675,8 @@ async fn drain_goal_updates_skips_subsequent_completed_after_block() {
let (tx, rx) = tokio::sync::mpsc::unbounded_channel();
*actor.goal_update_rx.borrow_mut() = Some(rx);
tx.send(
kigi_tools::implementations::grok_build::update_goal::envelope_for_test(
kigi_tools::implementations::grok_build::update_goal::UpdateGoalInput {
kigi_tools::implementations::kigi::update_goal::envelope_for_test(
kigi_tools::implementations::kigi::update_goal::UpdateGoalInput {
completed: None,
message: None,
blocked_reason: Some("X".into()),
@@ -1685,8 +1685,8 @@ async fn drain_goal_updates_skips_subsequent_completed_after_block() {
)
.unwrap();
tx.send(
kigi_tools::implementations::grok_build::update_goal::envelope_for_test(
kigi_tools::implementations::grok_build::update_goal::UpdateGoalInput {
kigi_tools::implementations::kigi::update_goal::envelope_for_test(
kigi_tools::implementations::kigi::update_goal::UpdateGoalInput {
completed: Some(true),
message: None,
blocked_reason: None,
@@ -2259,8 +2259,8 @@ async fn drain_goal_updates_message_only_does_not_change_status() {
let (tx, rx) = tokio::sync::mpsc::unbounded_channel();
*actor.goal_update_rx.borrow_mut() = Some(rx);
tx.send(
kigi_tools::implementations::grok_build::update_goal::envelope_for_test(
kigi_tools::implementations::grok_build::update_goal::UpdateGoalInput {
kigi_tools::implementations::kigi::update_goal::envelope_for_test(
kigi_tools::implementations::kigi::update_goal::UpdateGoalInput {
completed: None,
message: Some("Running tests...".into()),
blocked_reason: None,
@@ -2294,7 +2294,7 @@ async fn drain_goal_updates_message_only_does_not_change_status() {
/// producing an ack"). The drain must instead reply with a clean ack.
#[tokio::test(flavor = "current_thread")]
async fn drain_goal_updates_harness_disabled_does_not_drop_ack() {
use kigi_tools::implementations::grok_build::update_goal::{
use kigi_tools::implementations::kigi::update_goal::{
RejectReason, UpdateGoalAck, UpdateGoalInput,
};
let local = tokio::task::LocalSet::new();
@@ -2374,8 +2374,8 @@ async fn drain_goal_updates_blocked_reason_takes_precedence_over_completed() {
let (tx, rx) = tokio::sync::mpsc::unbounded_channel();
*actor.goal_update_rx.borrow_mut() = Some(rx);
tx.send(
kigi_tools::implementations::grok_build::update_goal::envelope_for_test(
kigi_tools::implementations::grok_build::update_goal::UpdateGoalInput {
kigi_tools::implementations::kigi::update_goal::envelope_for_test(
kigi_tools::implementations::kigi::update_goal::UpdateGoalInput {
completed: Some(true),
message: None,
blocked_reason: Some("stuck".into()),
@@ -2404,9 +2404,8 @@ async fn drain_goal_updates_blocked_reason_takes_precedence_over_completed() {
// classifier sampler invoked); the full Achieved/NotAchieved/cap
// E2E suite using `MockSpawner` lives separately.
fn make_completed_cmd() -> kigi_tools::implementations::grok_build::update_goal::UpdateGoalEnvelope
{
let input = kigi_tools::implementations::grok_build::update_goal::UpdateGoalInput {
fn make_completed_cmd() -> kigi_tools::implementations::kigi::update_goal::UpdateGoalEnvelope {
let input = kigi_tools::implementations::kigi::update_goal::UpdateGoalInput {
completed: Some(true),
message: None,
blocked_reason: None,
@@ -2966,8 +2965,8 @@ async fn drain_goal_updates_completed_resets_blocked_streak() {
let (tx, rx) = tokio::sync::mpsc::unbounded_channel();
*actor.goal_update_rx.borrow_mut() = Some(rx);
tx.send(
kigi_tools::implementations::grok_build::update_goal::envelope_for_test(
kigi_tools::implementations::grok_build::update_goal::UpdateGoalInput {
kigi_tools::implementations::kigi::update_goal::envelope_for_test(
kigi_tools::implementations::kigi::update_goal::UpdateGoalInput {
completed: Some(true),
message: None,
blocked_reason: None,
@@ -3379,7 +3378,7 @@ async fn subagent_spawn_captures_effective_model_id() {
.handle_xai_session_notification(spawn_notif_with_model(
"a",
None,
Some("grok-4.5"),
Some("kigi-4.5"),
))
.await;
let model = actor
@@ -3387,7 +3386,7 @@ async fn subagent_spawn_captures_effective_model_id() {
.lock()
.get("a")
.and_then(|r| r.model.clone());
assert_eq!(model.as_deref(), Some("grok-4.5"));
assert_eq!(model.as_deref(), Some("kigi-4.5"));
})
.await;
}
@@ -3417,17 +3416,17 @@ async fn goal_tokens_by_model_breaks_down_active_goal_records() {
local
.run_until(async {
let actor = make_test_actor_with_active_goal().await;
insert_record_with_model(&actor, "a", Some("test-goal"), 0, 100, Some("grok-4"));
insert_record_with_model(&actor, "b", Some("test-goal"), 0, 400, Some("grok-3"));
insert_record_with_model(&actor, "a", Some("test-goal"), 0, 100, Some("kigi-4"));
insert_record_with_model(&actor, "b", Some("test-goal"), 0, 400, Some("kigi-3"));
// No captured model → folds under the supplied current model.
insert_record_with_model(&actor, "c", Some("test-goal"), 0, 50, None);
// A record from another goal must be excluded.
insert_record_with_model(&actor, "d", Some("other-goal"), 0, 999, Some("grok-3"));
insert_record_with_model(&actor, "d", Some("other-goal"), 0, 999, Some("kigi-3"));
// A FINISHED record under the active goal must be excluded from the
// LIVE active-window breakdown (the per-model analogue of the
// finished/in-flight split in goal_tokens). If it leaked, grok-4
// finished/in-flight split in goal_tokens). If it leaked, kigi-4
// would be 800 and sort first.
insert_record_with_model(&actor, "e", Some("test-goal"), 0, 700, Some("grok-4"));
insert_record_with_model(&actor, "e", Some("test-goal"), 0, 700, Some("kigi-4"));
actor
.subagent_token_records
.lock()
@@ -3438,8 +3437,8 @@ async fn goal_tokens_by_model_breaks_down_active_goal_records() {
assert_eq!(
out,
vec![
("grok-3".to_owned(), 400),
("grok-4".to_owned(), 100),
("kigi-3".to_owned(), 400),
("kigi-4".to_owned(), 100),
("cur-model".to_owned(), 50),
]
);
@@ -3453,7 +3452,7 @@ async fn goal_tokens_by_model_empty_without_active_goal() {
local
.run_until(async {
let actor = make_test_actor_with_active_goal().await;
insert_record_with_model(&actor, "a", Some("test-goal"), 0, 100, Some("grok-4"));
insert_record_with_model(&actor, "a", Some("test-goal"), 0, 100, Some("kigi-4"));
// Drop the orchestration: with no active goal the breakdown is
// empty regardless of any lingering records.
actor.goal_tracker.lock().clear();
@@ -3757,8 +3756,8 @@ async fn blocked_streak_reaches_pause_across_successful_turns() {
let (tx, rx) = tokio::sync::mpsc::unbounded_channel();
*actor.goal_update_rx.borrow_mut() = Some(rx);
let blocked = || {
kigi_tools::implementations::grok_build::update_goal::envelope_for_test(
kigi_tools::implementations::grok_build::update_goal::UpdateGoalInput {
kigi_tools::implementations::kigi::update_goal::envelope_for_test(
kigi_tools::implementations::kigi::update_goal::UpdateGoalInput {
completed: None,
message: None,
blocked_reason: Some("cannot reach service".into()),
@@ -3849,7 +3848,7 @@ async fn subagent_progress_advances_goal_tokens_live_without_double_count() {
let kigi_acp_lib::AcpClientMessage::ExtNotification(args) = msg else {
continue;
};
if args.request.method.as_ref() != "x.ai/session_notification" {
if args.request.method.as_ref() != "kigi/session_notification" {
continue;
}
let Ok(v) =
@@ -4028,8 +4027,8 @@ async fn setup_goal_resets_streaks_from_previous_goal() {
let (tx, rx) = tokio::sync::mpsc::unbounded_channel();
*actor.goal_update_rx.borrow_mut() = Some(rx);
tx.send(
kigi_tools::implementations::grok_build::update_goal::envelope_for_test(
kigi_tools::implementations::grok_build::update_goal::UpdateGoalInput {
kigi_tools::implementations::kigi::update_goal::envelope_for_test(
kigi_tools::implementations::kigi::update_goal::UpdateGoalInput {
completed: None,
message: None,
blocked_reason: Some("blk".into()),
@@ -17,10 +17,10 @@
use super::support::*;
use super::*;
use crate::session::PromptOrigin;
use kigi_tools::implementations::grok_build::task::types::{
use kigi_tools::implementations::kigi::task::types::{
SubagentCancelOutcome, SubagentEvent, SubagentResult,
};
use kigi_tools::implementations::grok_build::update_goal::{RejectReason, UpdateGoalInput};
use kigi_tools::implementations::kigi::update_goal::{RejectReason, UpdateGoalInput};
use serial_test::serial;
use std::collections::VecDeque;
use std::sync::Arc as StdArc;
@@ -190,9 +190,7 @@ struct MockCoordinator {
/// configured role pair commits; tests override it to exercise the
/// describe-driven fail-open branches.
describe_outcome: StdArc<
parking_lot::Mutex<
kigi_tools::implementations::grok_build::task::types::SubagentDescribeOutcome,
>,
parking_lot::Mutex<kigi_tools::implementations::kigi::task::types::SubagentDescribeOutcome>,
>,
/// Per-describe `(subagent_type, harness_agent_type)` in call order.
describe_calls: DescribeCallLog,
@@ -200,8 +198,8 @@ struct MockCoordinator {
/// A fully-capable describe summary (read + search + execute + edit + write)
/// so any role's capability gate passes.
fn capable_describe_outcome()
-> kigi_tools::implementations::grok_build::task::types::SubagentDescribeOutcome {
use kigi_tools::implementations::grok_build::task::types::{
-> kigi_tools::implementations::kigi::task::types::SubagentDescribeOutcome {
use kigi_tools::implementations::kigi::task::types::{
SubagentDescribeOutcome, SubagentTypeSummary,
};
use kigi_tools::types::tool::ToolKind;
@@ -403,7 +401,7 @@ fn seed_channel(actor: &SessionActor, cmds: Vec<UpdateGoalInput>) {
let (tx, rx) = tokio::sync::mpsc::unbounded_channel();
*actor.goal_update_rx.borrow_mut() = Some(rx);
for cmd in cmds {
tx.send(kigi_tools::implementations::grok_build::update_goal::envelope_for_test(cmd))
tx.send(kigi_tools::implementations::kigi::update_goal::envelope_for_test(cmd))
.unwrap();
}
drop(tx);
@@ -415,9 +413,7 @@ fn seed_channel_with_acks(
actor: &SessionActor,
cmds: Vec<UpdateGoalInput>,
) -> Vec<
tokio::sync::oneshot::Receiver<
kigi_tools::implementations::grok_build::update_goal::UpdateGoalAck,
>,
tokio::sync::oneshot::Receiver<kigi_tools::implementations::kigi::update_goal::UpdateGoalAck>,
> {
let (tx, rx) = tokio::sync::mpsc::unbounded_channel();
*actor.goal_update_rx.borrow_mut() = Some(rx);
@@ -712,7 +708,7 @@ async fn goal_classifier_stall_early_exit_pauses_with_no_progress() {
VecDeque::from([Response::not_achieved(), Response::not_achieved()]),
);
let (actor, tmp) = make_actor(Some(coord.tx.clone()), true).await;
use kigi_tools::implementations::grok_build::update_goal::UpdateGoalAck;
use kigi_tools::implementations::kigi::update_goal::UpdateGoalAck;
let mut last_ack = None;
for _ in 0..2 {
let mut rxs = seed_channel_with_acks(&actor, vec![make_completed()]);
@@ -752,7 +748,7 @@ async fn goal_classifier_blocked_outcome_pauses_for_user_and_consolidates_queue(
let local = tokio::task::LocalSet::new();
local
.run_until(async {
use kigi_tools::implementations::grok_build::update_goal::UpdateGoalAck;
use kigi_tools::implementations::kigi::update_goal::UpdateGoalAck;
let coord = MockCoordinator::spawn(VecDeque::from([Response::blocked("unverifiable")]));
let (actor, tmp) = make_actor(Some(coord.tx.clone()), true).await;
let rxs = seed_channel_with_acks(&actor, vec![make_completed(), make_completed()]);
@@ -817,7 +813,7 @@ async fn goal_classifier_cap_takes_precedence_over_stall() {
let local = tokio::task::LocalSet::new();
local
.run_until(async {
use kigi_tools::implementations::grok_build::update_goal::UpdateGoalAck;
use kigi_tools::implementations::kigi::update_goal::UpdateGoalAck;
let coord = MockCoordinator::spawn(VecDeque::from([
Response::not_achieved(),
Response::not_achieved(),
@@ -878,7 +874,7 @@ async fn goal_classifier_stall_pause_consolidates_mid_drain_queue() {
let local = tokio::task::LocalSet::new();
local
.run_until(async {
use kigi_tools::implementations::grok_build::update_goal::UpdateGoalAck;
use kigi_tools::implementations::kigi::update_goal::UpdateGoalAck;
let coord = MockCoordinator::spawn(VecDeque::from([
Response::not_achieved(),
Response::not_achieved(),
@@ -929,7 +925,7 @@ async fn goal_classifier_post_blocked_resume_does_not_immediately_restall() {
let local = tokio::task::LocalSet::new();
local
.run_until(async {
use kigi_tools::implementations::grok_build::update_goal::UpdateGoalAck;
use kigi_tools::implementations::kigi::update_goal::UpdateGoalAck;
let coord = MockCoordinator::spawn(VecDeque::from([
Response::not_achieved_with("src/a.rs:1 missing coverage"),
Response::blocked("contradiction"),
@@ -2070,7 +2066,7 @@ async fn update_goal_tool_blocks_until_classifier_verdict_when_enabled() {
let ack = ack_rx.await.expect("ack delivered");
assert!(
matches!(ack,
kigi_tools::implementations::grok_build::update_goal::UpdateGoalAck::ClassifierAchieved
kigi_tools::implementations::kigi::update_goal::UpdateGoalAck::ClassifierAchieved
{ .. },),
"classifier-enabled drain must deliver Achieved ack; got {ack:?}",
);
@@ -2089,7 +2085,7 @@ async fn update_goal_tool_returns_immediately_when_classifier_disabled() {
let ack = ack_rx.await.expect("ack delivered");
assert!(
matches!(ack,
kigi_tools::implementations::grok_build::update_goal::UpdateGoalAck::CompletedWithoutClassifier,)
kigi_tools::implementations::kigi::update_goal::UpdateGoalAck::CompletedWithoutClassifier,)
);
})
.await;
@@ -2105,7 +2101,7 @@ async fn update_goal_tool_returns_error_when_classifier_in_flight_for_previous_c
let ack_rx = rxs.pop().expect("one ack");
actor.drain_goal_updates(0, DrainPurpose::TurnEnd).await;
let ack = ack_rx.await.expect("ack delivered");
use kigi_tools::implementations::grok_build::update_goal::UpdateGoalAck;
use kigi_tools::implementations::kigi::update_goal::UpdateGoalAck;
match ack {
UpdateGoalAck::ClassifierConcurrentInFlight {
attempt, max_runs, ..
@@ -2127,7 +2123,7 @@ async fn update_goal_tool_returns_error_when_classifier_in_flight_for_previous_c
}
#[tokio::test(flavor = "current_thread")]
async fn update_goal_tool_does_not_deadlock_on_mid_turn_completion() {
use kigi_tools::implementations::grok_build::update_goal::UpdateGoalAck;
use kigi_tools::implementations::kigi::update_goal::UpdateGoalAck;
let local = tokio::task::LocalSet::new();
local
.run_until(async {
@@ -2150,7 +2146,7 @@ async fn update_goal_tool_does_not_deadlock_on_mid_turn_completion() {
}
#[tokio::test(flavor = "current_thread")]
async fn update_goal_tool_deferred_input_fires_classifier_at_turn_end() {
use kigi_tools::implementations::grok_build::update_goal::UpdateGoalAck;
use kigi_tools::implementations::kigi::update_goal::UpdateGoalAck;
let local = tokio::task::LocalSet::new();
local
.run_until(async {
@@ -2185,18 +2181,14 @@ async fn update_goal_tool_returns_immediately_for_blocked_reason() {
local
.run_until(async {
let (actor, _tmp) = make_actor(None, true).await;
let mut rxs = seed_channel_with_acks(
&actor,
vec![make_blocked("transient")],
);
let mut rxs = seed_channel_with_acks(&actor, vec![make_blocked("transient")]);
let ack_rx = rxs.pop().expect("one ack");
actor.drain_goal_updates(0, DrainPurpose::TurnEnd).await;
let ack = ack_rx.await.expect("ack delivered");
assert!(
matches!(ack,
kigi_tools::implementations::grok_build::update_goal::UpdateGoalAck::Accepted
{ .. },)
);
assert!(matches!(
ack,
kigi_tools::implementations::kigi::update_goal::UpdateGoalAck::Accepted { .. },
));
})
.await;
}
@@ -2291,7 +2283,7 @@ async fn goal_classifier_sequential_drain_four_completions_three_attempts_then_c
let local = tokio::task::LocalSet::new();
local
.run_until(async {
use kigi_tools::implementations::grok_build::update_goal::UpdateGoalAck;
use kigi_tools::implementations::kigi::update_goal::UpdateGoalAck;
let coordinator = MockCoordinator::spawn(three_distinct_not_achieved());
let (actor, _tmp) = make_actor_with_cap(
Some(coordinator.tx.clone()),
@@ -2358,7 +2350,7 @@ async fn goal_classifier_sequential_drain_four_completions_three_attempts_then_c
/// must ack as `ClassifierConcurrentInFlight` (NOT success).
#[tokio::test(flavor = "current_thread")]
async fn goal_classifier_concurrent_in_flight_short_circuits_second_completion() {
use kigi_tools::implementations::grok_build::update_goal::UpdateGoalAck;
use kigi_tools::implementations::kigi::update_goal::UpdateGoalAck;
let local = tokio::task::LocalSet::new();
local
.run_until(async {
@@ -2414,7 +2406,7 @@ async fn rejected_ack_post_cap_carries_correct_reason() {
let ack_rx = rxs.pop().unwrap();
actor.drain_goal_updates(0, DrainPurpose::TurnEnd).await;
let ack = ack_rx.await.expect("ack delivered");
use kigi_tools::implementations::grok_build::update_goal::UpdateGoalAck;
use kigi_tools::implementations::kigi::update_goal::UpdateGoalAck;
match ack {
UpdateGoalAck::Rejected { reason, detail } => {
assert_eq!(reason, RejectReason::PostCap);
@@ -2437,7 +2429,7 @@ async fn pending_queue_overflow_acks_all_as_deferred_and_caps_at_pending_queue_c
}
let rxs = seed_channel_with_acks(&actor, inputs);
actor.drain_goal_updates(0, DrainPurpose::MidTurn).await;
use kigi_tools::implementations::grok_build::update_goal::UpdateGoalAck;
use kigi_tools::implementations::kigi::update_goal::UpdateGoalAck;
for rx in rxs {
let ack = rx.await.expect("ack delivered");
assert!(
@@ -2462,9 +2454,7 @@ async fn pending_queue_overflow_acks_all_as_deferred_and_caps_at_pending_queue_c
}
#[test]
fn render_ack_classifier_achieved_is_success() {
use kigi_tools::implementations::grok_build::update_goal::{
UpdateGoalAck, render_ack_into_output,
};
use kigi_tools::implementations::kigi::update_goal::{UpdateGoalAck, render_ack_into_output};
let out = render_ack_into_output(UpdateGoalAck::ClassifierAchieved {
details_path: "/tmp/details.md".to_string(),
})
@@ -2475,9 +2465,7 @@ fn render_ack_classifier_achieved_is_success() {
}
#[test]
fn render_ack_classifier_fail_open_achieved_clarifies_no_verdict() {
use kigi_tools::implementations::grok_build::update_goal::{
UpdateGoalAck, render_ack_into_output,
};
use kigi_tools::implementations::kigi::update_goal::{UpdateGoalAck, render_ack_into_output};
let out =
render_ack_into_output(UpdateGoalAck::ClassifierFailOpenAchieved { reason: "timeout" })
.expect("FailOpen must be Ok (treated as achieved)");
@@ -2488,9 +2476,7 @@ fn render_ack_classifier_fail_open_achieved_clarifies_no_verdict() {
}
#[test]
fn render_ack_not_achieved_is_tool_error_with_correct_code() {
use kigi_tools::implementations::grok_build::update_goal::{
UpdateGoalAck, render_ack_into_output,
};
use kigi_tools::implementations::kigi::update_goal::{UpdateGoalAck, render_ack_into_output};
let err = render_ack_into_output(UpdateGoalAck::ClassifierNotAchieved {
details_path: "/tmp/details.md".to_string(),
attempt: 2,
@@ -2501,9 +2487,7 @@ fn render_ack_not_achieved_is_tool_error_with_correct_code() {
}
#[test]
fn render_ack_cap_reached_is_tool_error_with_cap_code() {
use kigi_tools::implementations::grok_build::update_goal::{
UpdateGoalAck, render_ack_into_output,
};
use kigi_tools::implementations::kigi::update_goal::{UpdateGoalAck, render_ack_into_output};
let err = render_ack_into_output(UpdateGoalAck::ClassifierCapReached {
details_path: "/tmp/details.md".to_string(),
attempt: 3,
@@ -2524,9 +2508,7 @@ fn tool_error_code(err: &kigi_tool_runtime::ToolError) -> &str {
}
#[test]
fn render_ack_rejected_uses_reason_error_code() {
use kigi_tools::implementations::grok_build::update_goal::{
UpdateGoalAck, render_ack_into_output,
};
use kigi_tools::implementations::kigi::update_goal::{UpdateGoalAck, render_ack_into_output};
for (reason, want_code) in all_reject_reasons() {
let err = render_ack_into_output(UpdateGoalAck::Rejected {
reason: *reason,
@@ -2613,7 +2595,7 @@ fn reject_reasons_complete_matrix() {
}
use crate::session::acp_session::GoalRoleModelConfig;
use crate::session::acp_session::goal::{PanelResolveCache, RoleCapability};
use kigi_tools::implementations::grok_build::task::types::SubagentDescribeOutcome;
use kigi_tools::implementations::kigi::task::types::SubagentDescribeOutcome;
fn role_pair(model: &str, agent_type: &str) -> crate::util::config::GoalRoleModel {
crate::util::config::GoalRoleModel {
model: model.to_string(),
@@ -2824,11 +2806,10 @@ async fn resolve_role_override_toolset_incapable_fails_open() {
let local = tokio::task::LocalSet::new();
local
.run_until(async {
let mut summary =
kigi_tools::implementations::grok_build::task::types::SubagentTypeSummary {
can_read: true,
..Default::default()
};
let mut summary = kigi_tools::implementations::kigi::task::types::SubagentTypeSummary {
can_read: true,
..Default::default()
};
summary
.tool_names
.insert(kigi_tools::types::tool::ToolKind::Read, "read_file".into());
@@ -2871,7 +2852,7 @@ async fn resolve_role_override_all_pass_commits_and_emits_resolved() {
}
/// A strict-but-unrepresentable harness (`codex`) fails open with the distinct
/// `harness_flavor_unsupported` reason. Honored:
/// `grok-build-plan` (non-strict), and `opencode` (non-strict + unrepresentable
/// `kigi-plan` (non-strict), and `opencode` (non-strict + unrepresentable
/// — proving the gate keys on `is_strict`, not representability alone).
#[tokio::test(flavor = "current_thread")]
async fn resolve_role_override_harness_flavor_representability_gate() {
@@ -2889,7 +2870,7 @@ async fn resolve_role_override_harness_flavor_representability_gate() {
let evs = lines_with_type(&log, "goal_role_model_fail_open");
assert_eq!(evs.len(), 1, "{log}");
assert_eq!(evs[0]["reason"], "harness_flavor_unsupported");
let honored = ["grok-build-plan", "opencode"];
let honored = ["kigi-plan", "opencode"];
for harness in honored {
let (ov, log) = run_resolve(
&role_pair("good-model", harness),
@@ -2983,7 +2964,7 @@ async fn single_role_override_explicit_builds_tool_names_from_summary() {
let local = tokio::task::LocalSet::new();
local
.run_until(async {
use kigi_tools::implementations::grok_build::task::types::{
use kigi_tools::implementations::kigi::task::types::{
SubagentDescribeOutcome, SubagentTypeSummary,
};
use kigi_tools::types::tool::ToolKind;
@@ -5,7 +5,7 @@
use super::support::*;
use super::*;
use kigi_tools::implementations::grok_build::task::types::{SubagentEvent, SubagentResult};
use kigi_tools::implementations::kigi::task::types::{SubagentEvent, SubagentResult};
use serial_test::serial;
use std::sync::Arc as StdArc;
use std::sync::atomic::{AtomicUsize, Ordering as SeqOrd};
@@ -129,7 +129,7 @@ async fn setup_goal_includes_simplified_prompt() {
}
#[tokio::test(flavor = "current_thread")]
async fn goal_enabled_without_update_goal_disables_harness_continuation_and_todo_gate() {
use kigi_tools::implementations::grok_build::UPDATE_GOAL_TOOL_NAME;
use kigi_tools::implementations::kigi::UPDATE_GOAL_TOOL_NAME;
let local = tokio::task::LocalSet::new();
local
.run_until(async {
@@ -828,7 +828,7 @@ fn render_goal_rules_places_discipline_after_block_recap() {
&block_recap,
"",
None,
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
let recap_idx = body
@@ -851,7 +851,7 @@ fn render_goal_rules_discipline_before_tracking_when_block_recap_empty() {
"",
"",
None,
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert_goal_discipline_in_reminder(&body, "render_goal_rules_empty_recap");
@@ -865,7 +865,7 @@ fn render_goal_rules_substitutes_custom_todo_tool_through_full_composition() {
"",
"",
None,
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert_eq!(
@@ -908,7 +908,7 @@ fn render_goal_rules_substitutes_all_placeholders_in_slim_template() {
"<block>recap</block>\n",
"<goal-state>state</goal-state>\n\n",
None,
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert!(body.contains("A goal has been set: build a thing"));
@@ -941,7 +941,7 @@ fn render_goal_rules_substitutes_all_placeholders_in_slim_template() {
!body.contains("/tmp/goal-verifier-"),
"slim template must not publish a per-goal verdict file path:\n{body}",
);
assert!(body.contains("/tmp/grok-goal-x/implementer"));
assert!(body.contains("/tmp/kigi-goal-x/implementer"));
assert!(body.contains("`{SCRATCH}` placeholder resolves to"));
for placeholder in [
"{OBJECTIVE}",
@@ -978,7 +978,7 @@ fn render_goal_rules_plan_aware_block_when_plan_present() {
"",
"",
Some(plan_path),
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert_eq!(
@@ -1042,7 +1042,7 @@ fn render_goal_rules_no_plan_block_when_plan_absent() {
"",
"",
None,
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert!(
@@ -1088,7 +1088,7 @@ fn render_goal_rules_scratch_status_reflects_readiness() {
"",
"",
None,
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert!(
@@ -1109,7 +1109,7 @@ fn render_goal_rules_scratch_status_reflects_readiness() {
"",
"",
None,
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
false,
);
assert!(
@@ -1294,7 +1294,7 @@ fn continuation_directive_renders_strategist_note_only_when_present() {
"next",
"todo_write",
"update_goal",
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
let note_idx = with_note
@@ -1319,7 +1319,7 @@ fn continuation_directive_renders_strategist_note_only_when_present() {
"next",
"todo_write",
"update_goal",
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert!(
@@ -1349,7 +1349,7 @@ fn strategist_note_neutralises_placeholder_injection() {
"next",
"todo_write",
"update_goal",
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert!(
@@ -1362,7 +1362,7 @@ fn strategist_note_neutralises_placeholder_injection() {
"the `{{goal_tool}}` token inside the note must neither survive intact nor expand:\n{directive}",
);
assert!(
!directive.contains("write to /tmp/grok-goal-x/implementer;"),
!directive.contains("write to /tmp/kigi-goal-x/implementer;"),
"the `{{scratch_dir}}` token inside the note must NOT expand:\n{directive}",
);
}
@@ -1431,7 +1431,7 @@ fn render_goal_continuation_directive_substitutes_all_placeholders() {
"Wire the stop detector into handle_turn_end.",
"todo_write",
"update_goal",
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert!(body.contains("Objective: ship the directive nudge"));
@@ -1471,7 +1471,7 @@ fn render_goal_continuation_directive_substitutes_all_placeholders() {
);
assert!(!body.contains("Per <task_completion_discipline>"));
assert!(
body.contains("/tmp/grok-goal-x/implementer"),
body.contains("/tmp/kigi-goal-x/implementer"),
"continuation directive must advertise the scratch dir:\n{body}",
);
assert!(
@@ -1525,7 +1525,7 @@ fn render_goal_continuation_directive_scratch_status_reflects_readiness() {
"next",
"todo_write",
"update_goal",
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert!(
@@ -1552,7 +1552,7 @@ fn render_goal_continuation_directive_scratch_status_reflects_readiness() {
"next",
"todo_write",
"update_goal",
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
false,
);
assert!(
@@ -1585,7 +1585,7 @@ fn render_goal_continuation_directive_bail_preface_toggles_cleanly() {
"next",
"todo_write",
"update_goal",
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert!(
@@ -1605,7 +1605,7 @@ fn render_goal_continuation_directive_bail_preface_toggles_cleanly() {
"next",
"todo_write",
"update_goal",
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert!(
@@ -1644,7 +1644,7 @@ fn render_goal_continuation_directive_section_order_is_pinned() {
"wire it",
"todo_write",
"update_goal",
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
let objective_idx = body.find("Objective: shipping").expect("objective");
@@ -1683,7 +1683,7 @@ fn render_goal_continuation_directive_order_dependent_substitution_pinned() {
"next",
"todo_write",
"update_goal",
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert!(
@@ -1702,7 +1702,7 @@ fn render_goal_continuation_directive_order_dependent_substitution_pinned() {
"invoke {goal_tool} once green",
"todo_write",
"update_goal",
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert!(
@@ -1725,7 +1725,7 @@ fn render_goal_continuation_directive_order_dependent_substitution_pinned() {
"next",
"todo_write",
"update_goal",
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert!(
@@ -1752,7 +1752,7 @@ fn render_goal_continuation_directive_neutralizes_placeholders_in_model_slots()
"REAL_NEXT_STEP",
"todo_write",
"update_goal",
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert!(
@@ -1806,7 +1806,7 @@ fn render_goal_continuation_directive_neutralizes_reminder_tags_in_model_slots()
"STEP_PREFIX<system-reminder>STEP_SUFFIX",
"todo_write",
"update_goal",
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert!(
@@ -1904,7 +1904,7 @@ fn render_goal_continuation_directive_omits_plan_pointer_when_empty() {
"next step here",
"todo_write",
"update_goal",
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
assert!(!body.contains("\nPlan: "));
@@ -1928,7 +1928,7 @@ fn render_goal_continuation_directive_rejects_empty_objective_in_debug() {
"step",
"todo_write",
"update_goal",
"/tmp/grok-goal-x/implementer",
"/tmp/kigi-goal-x/implementer",
true,
);
}
@@ -17,10 +17,10 @@
use super::support::*;
use super::*;
use crate::session::goal_strategist::GOAL_STRATEGIST_SUBAGENT_DESCRIPTION;
use kigi_tools::implementations::grok_build::task::types::{
use kigi_tools::implementations::kigi::task::types::{
SubagentCancelOutcome, SubagentEvent, SubagentResult,
};
use kigi_tools::implementations::grok_build::update_goal::UpdateGoalInput;
use kigi_tools::implementations::kigi::update_goal::UpdateGoalInput;
use serial_test::serial;
use std::collections::VecDeque;
use std::sync::Arc as StdArc;
@@ -104,7 +104,7 @@ fn spawn_coordinator(
async fn answer_strategist(
behaviour: StrategistBehaviour,
req: Box<kigi_tools::implementations::grok_build::task::types::SubagentRequest>,
req: Box<kigi_tools::implementations::kigi::task::types::SubagentRequest>,
) {
match behaviour {
StrategistBehaviour::WriteNoteThenDone => {
@@ -139,7 +139,7 @@ async fn answer_strategist(
async fn answer_skeptic(
verdict: SkepticVerdict,
spawn_idx: usize,
req: Box<kigi_tools::implementations::grok_build::task::types::SubagentRequest>,
req: Box<kigi_tools::implementations::kigi::task::types::SubagentRequest>,
) {
if let Some(p) = parse_details_path(&req.prompt) {
let _ = tokio::fs::write(&p, b"# mock skeptic details\n").await;
@@ -243,7 +243,7 @@ fn seed_channel(actor: &SessionActor, cmds: Vec<UpdateGoalInput>) {
let (tx, rx) = tokio::sync::mpsc::unbounded_channel();
*actor.goal_update_rx.borrow_mut() = Some(rx);
for cmd in cmds {
tx.send(kigi_tools::implementations::grok_build::update_goal::envelope_for_test(cmd))
tx.send(kigi_tools::implementations::kigi::update_goal::envelope_for_test(cmd))
.unwrap();
}
drop(tx);
@@ -17,10 +17,10 @@
use super::support::*;
use super::*;
use crate::session::goal_summarizer::GOAL_SUMMARIZER_SUBAGENT_DESCRIPTION;
use kigi_tools::implementations::grok_build::task::types::{
use kigi_tools::implementations::kigi::task::types::{
SubagentCancelOutcome, SubagentEvent, SubagentResult,
};
use kigi_tools::implementations::grok_build::update_goal::UpdateGoalInput;
use kigi_tools::implementations::kigi::update_goal::UpdateGoalInput;
use serial_test::serial;
use std::collections::VecDeque;
use std::sync::Arc as StdArc;
@@ -98,7 +98,7 @@ fn spawn_coordinator(
async fn answer_summarizer(
behaviour: SummarizerBehaviour,
req: Box<kigi_tools::implementations::grok_build::task::types::SubagentRequest>,
req: Box<kigi_tools::implementations::kigi::task::types::SubagentRequest>,
) {
match behaviour {
SummarizerBehaviour::ReturnSummary => {
@@ -127,7 +127,7 @@ async fn answer_summarizer(
async fn answer_skeptic(
verdict: SkepticVerdict,
spawn_idx: usize,
req: Box<kigi_tools::implementations::grok_build::task::types::SubagentRequest>,
req: Box<kigi_tools::implementations::kigi::task::types::SubagentRequest>,
) {
if let Some(p) =
crate::session::goal_classifier::parse_skeptic_details_path_from_prompt(&req.prompt)
@@ -268,7 +268,7 @@ fn seed_channel(actor: &SessionActor, cmds: Vec<UpdateGoalInput>) {
let (tx, rx) = tokio::sync::mpsc::unbounded_channel();
*actor.goal_update_rx.borrow_mut() = Some(rx);
for cmd in cmds {
tx.send(kigi_tools::implementations::grok_build::update_goal::envelope_for_test(cmd))
tx.send(kigi_tools::implementations::kigi::update_goal::envelope_for_test(cmd))
.unwrap();
}
drop(tx);
@@ -199,7 +199,7 @@ mod interjection_broadcast_tests {
/// Multi-client fix: a mid-turn interjection must be broadcast to every
/// attached client (not just the originator) so all panes viewing the same
/// session render it. This locks the wire contract the pager's
/// `handle_interjection` depends on: method `x.ai/session/interjection`
/// `handle_interjection` depends on: method `kigi/session/interjection`
/// carrying `sessionId` + `text`.
#[tokio::test]
async fn broadcast_interjection_emits_sessionid_and_text() {
@@ -217,14 +217,14 @@ mod interjection_broadcast_tests {
let mut payload = None;
while let Ok(msg) = gateway_rx.try_recv() {
if let kigi_acp_lib::AcpClientMessage::ExtNotification(args) = msg
&& args.request.method.as_ref() == "x.ai/session/interjection"
&& args.request.method.as_ref() == "kigi/session/interjection"
{
payload =
serde_json::from_str::<serde_json::Value>(args.request.params.get())
.ok();
}
}
let payload = payload.expect("an x.ai/session/interjection broadcast");
let payload = payload.expect("an kigi/session/interjection broadcast");
assert_eq!(
payload.get("sessionId").and_then(|v| v.as_str()),
Some("test-actor"),
@@ -622,7 +622,7 @@ fn sample_line() -> LazinessDebugLogLine {
LazinessDebugLogLine {
timestamp: "2026-05-21T22:14:01.123Z".to_string(),
session_id: "019e4c65-434b-7d62-9d4b-8137d1d413e4".to_string(),
model_id: "grok-4.5".to_string(),
model_id: "kigi-4.5".to_string(),
items_sent: 28,
todo_snapshot: vec![DebugTodoSnapshot {
id: "turn-finish-test-1".to_string(),
@@ -180,7 +180,7 @@ async fn incremental_dispatch_surfaces_fast_tool_before_slow_sibling() {
/// `execute_tool_calls` Phase 2. The original implementation hardcoded
/// `parsed_args.get("file_path")`, which silently bypassed serialization
/// for any toolset whose edit input declared the path under a different
/// JSON key. The compat toolset input types use `path`, and grok_build's
/// JSON key. The compat toolset input types use `path`, and kigi's
/// `read_file` uses `target_file`, so all of
/// those calls fell through to fully concurrent dispatch and could lose
/// edits via TOCTOU on the same workspace file.
@@ -188,8 +188,8 @@ async fn incremental_dispatch_surfaces_fast_tool_before_slow_sibling() {
/// These tests pin the JSON-key contract so the bucket key keeps tracking
/// every toolset's actual schema.
#[test]
fn lock_path_for_args_matches_grok_build_file_path() {
// grok_build search_replace / opencode EditTool / WriteTool / etc.
fn lock_path_for_args_matches_kigi_file_path() {
// kigi search_replace / opencode EditTool / WriteTool / etc.
let args = serde_json::json!({
"file_path": "/repo/src/main.rs",
"old_string": "foo",
@@ -210,8 +210,8 @@ fn lock_path_for_args_matches_path_arg() {
}
#[test]
fn lock_path_for_args_matches_grok_build_target_file() {
// grok_build read_file uses #[serde(rename = "target_file")].
fn lock_path_for_args_matches_kigi_target_file() {
// kigi read_file uses #[serde(rename = "target_file")].
let args = serde_json::json!({
"target_file": "/repo/src/main.rs",
});
@@ -274,14 +274,14 @@ fn lock_path_for_args_buckets_parallel_compat_strreplace_to_same_lock() {
}
#[test]
fn lock_path_for_args_buckets_grok_build_and_compat_to_same_lock_for_same_file() {
// A mixed batch (e.g. grok_build search_replace + StrReplace
fn lock_path_for_args_buckets_kigi_and_compat_to_same_lock_for_same_file() {
// A mixed batch (e.g. kigi search_replace + StrReplace
// in the same turn — possible if the harness ever exposes both, or
// during toolset migration) must still serialize on the shared file
// path. file_path takes precedence over path when both are present,
// but neither tool emits both keys today, so this asserts the
// cross-toolset key normalization works in practice.
let grok = serde_json::json!({
let kigi = serde_json::json!({
"file_path": "/repo/src/main.rs",
"old_string": "a",
"new_string": "b",
@@ -291,7 +291,7 @@ fn lock_path_for_args_buckets_grok_build_and_compat_to_same_lock_for_same_file()
"old_string": "c",
"new_string": "d",
});
assert_eq!(lock_path_for_args(&grok), lock_path_for_args(&compat));
assert_eq!(lock_path_for_args(&kigi), lock_path_for_args(&compat));
}
/// Regression: skill-discovery reminders must land after all tool results, not mid-batch.
@@ -1,7 +1,7 @@
//! Resume re-park of the `exit_plan_mode` approval + the mid-turn
//! disconnect handling.
//!
//! On resume the shell re-issues the `x.ai/exit_plan_mode` reverse-request when
//! On resume the shell re-issues the `kigi/exit_plan_mode` reverse-request when
//! `awaiting_plan_approval` was persisted, recreating a real live waiter so the
//! pager's existing approve/revise/abandon path works unchanged. These tests
//! pin the reverse-request shape, the awaiting-bit lifecycle, and the mid-turn
@@ -93,7 +93,7 @@ async fn request_plan_approval_issues_reverse_request_and_clears_flag() {
);
let (method, session_id) = responder.await.unwrap();
assert_eq!(method.as_deref(), Some("x.ai/exit_plan_mode"));
assert_eq!(method.as_deref(), Some("kigi/exit_plan_mode"));
assert_eq!(
session_id.as_deref(),
Some("test-actor"),
@@ -6,12 +6,12 @@
//! BEFORE the permission layer can auto-approve.
use super::support::*;
use super::*;
/// Build an actor whose toolset parses grok `search_replace` plus the plan
/// Build an actor whose toolset parses kigi `search_replace` plus the plan
/// tools (so `${{ tools.by_kind.exit_plan }}` resolves in the rejection
/// message), with a gateway drain answering session notifications.
async fn build_gate_actor() -> SessionActor {
use kigi_tools::implementations::grok_build::enter_plan_mode::EnterPlanModeTool;
use kigi_tools::implementations::grok_build::exit_plan_mode::ExitPlanModeTool;
use kigi_tools::implementations::kigi::enter_plan_mode::EnterPlanModeTool;
use kigi_tools::implementations::kigi::exit_plan_mode::ExitPlanModeTool;
use kigi_tools::registry::types::ToolConfig;
let (gateway_tx, mut gateway_rx) =
tokio::sync::mpsc::unbounded_channel::<kigi_acp_lib::AcpClientMessage>();
@@ -19,8 +19,8 @@ async fn build_gate_actor() -> SessionActor {
tokio::sync::mpsc::unbounded_channel::<PersistenceMsg>();
let actor = create_test_actor(0, 256_000, 85, gateway_tx, persistence_tx).await;
*actor.agent.borrow_mut() = test_agent_with_tools(vec![
ToolConfig::from_id("GrokBuild:read_file"),
ToolConfig::from_id("GrokBuild:search_replace"),
ToolConfig::from_id("Kigi:read_file"),
ToolConfig::from_id("Kigi:search_replace"),
ToolConfig::for_tool::<EnterPlanModeTool>(),
ToolConfig::for_tool::<ExitPlanModeTool>(),
])
@@ -77,10 +77,10 @@ async fn tool_result_text(actor: &SessionActor, call_id: &str) -> String {
.unwrap_or_else(|| panic!("no tool_result for {call_id} in {conv:?}"))
}
/// The headline: plan mode Active + allow-all permissions (the always-approve
/// worst case) still rejects a grok edit outside the plan file, without ever
/// worst case) still rejects a kigi edit outside the plan file, without ever
/// reaching the permission layer, and steers the model to `exit_plan_mode`.
#[tokio::test(flavor = "current_thread")]
async fn plan_mode_rejects_grok_edit_outside_plan_file_despite_allow_all_permissions() {
async fn plan_mode_rejects_kigi_edit_outside_plan_file_despite_allow_all_permissions() {
let local = tokio::task::LocalSet::new();
local
.run_until(async {
@@ -60,7 +60,7 @@ fn test_system_prompt_write_and_read() {
#[test]
fn test_system_prompt_is_plain_text_not_json() {
let prompt = "You are a Grok Build subagent.";
let prompt = "You are a Kigi subagent.";
// system_prompt.txt is raw text, NOT JSON-encoded.
assert!(!prompt.starts_with('"'), "must not be JSON-quoted");
assert!(!prompt.starts_with('{'), "must not be JSON object");
@@ -107,7 +107,7 @@ fn test_system_prompt_matches_chat_history_system_message() {
let session_dir = tmp.path().join("session-consistency");
std::fs::create_dir_all(&session_dir).unwrap();
let system_prompt = "You are a Grok Build subagent.\n\n<tool_calling>\n...";
let system_prompt = "You are a Kigi subagent.\n\n<tool_calling>\n...";
// Write system_prompt.txt (same string used for chat_history).
std::fs::write(session_dir.join(SYSTEM_PROMPT_FILENAME), system_prompt).unwrap();
@@ -164,7 +164,7 @@ fn test_load_system_prompt_returns_content_when_present() {
let session_dir = tmp.path().join("session-load-test");
std::fs::create_dir_all(&session_dir).unwrap();
let prompt = "You are a Grok Build subagent.";
let prompt = "You are a Kigi subagent.";
std::fs::write(session_dir.join(SYSTEM_PROMPT_FILENAME), prompt).unwrap();
let loaded = load_system_prompt_from_dir(&session_dir);
@@ -243,7 +243,7 @@ const HEAD_TOKEN: &str = "HEADSTART_TOKEN_aaa";
const TAIL_TOKEN: &str = "TAILEND_TOKEN_zzz";
fn fake_prompt_path() -> std::path::PathBuf {
std::path::PathBuf::from("/tmp/grok-test-home/sessions/cwd/sid/prompts/prompt_0.txt")
std::path::PathBuf::from("/tmp/kigi-test-home/sessions/cwd/sid/prompts/prompt_0.txt")
}
/// `truncate_bytes_suffix` keeps a char-boundary-safe suffix (multibyte-safe).
@@ -343,7 +343,7 @@ fn build_truncated_preserves_small_query_truncates_context() {
assert!(message.contains(&query), "small query preserved intact");
assert!(
message.starts_with(&query),
"grok ordering: query block first"
"kigi ordering: query block first"
);
assert!(message.contains("CTXHEAD_TOKEN"), "context head preserved");
assert!(!message.contains(&context), "oversized context truncated");
@@ -381,7 +381,7 @@ fn build_truncated_both_oversized_keeps_bounded_heads() {
assert!(!message.contains(&context), "full context not inlined");
assert!(
message.starts_with("QHEAD_TOKEN"),
"grok ordering: query first"
"kigi ordering: query first"
);
assert!(
message.len() <= TRUNCATED_PROMPT_PREFIX_SIZE,
@@ -415,9 +415,9 @@ async fn manual_recap_generation_failure_persists_request_artifact() {
"artifact must include the recap request items"
);
assert!(
artifact.x_grok_req_id.starts_with("xai-recap-"),
artifact.x_kigi_req_id.starts_with("xai-recap-"),
"req id: {}",
artifact.x_grok_req_id
artifact.x_kigi_req_id
);
saw_recap_request = true;
}
@@ -529,7 +529,7 @@ async fn manual_recap_over_budget_trims_persisted_request_and_is_display_only()
/// Over-budget recap serializes to a well-formed Anthropic Messages payload:
/// system preserved, reasoning stripped, no dangling `tool_use`/`tool_result`, no
/// `tool_result` before the appended instruction. (Messages is the strictest
/// shape, so it also covers the laxer grok ChatCompletions/Responses shapes.)
/// shape, so it also covers the laxer kigi ChatCompletions/Responses shapes.)
#[test]
fn over_budget_recap_serializes_to_well_formed_messages_request() {
use crate::session::helpers::session_recap;
@@ -568,7 +568,7 @@ fn over_budget_recap_serializes_to_well_formed_messages_request() {
ConversationItem::tool_result("c2", "z".repeat(40_000)), // trailing run
];
// grok backend => strip_reasoning=false; the over-budget branch strips anyway.
// kigi backend => strip_reasoning=false; the over-budget branch strips anyway.
let items = session_recap::budget_recap_items(conv, "system-reminder", false, 8_000);
let req = ConversationRequest::from_items(items);
let msg = kigi_sampling_types::build_messages_request(&req);
@@ -115,7 +115,7 @@ fn remote_settings_preserves_false_and_zero_todo_gate_fields() {
assert_eq!(settings.todo_gate_max_fires_per_prompt, Some(0));
}
fn def_with_template(tpl: TemplateOverride) -> AgentDefinition {
let mut def = AgentDefinition::default_grok_build();
let mut def = AgentDefinition::default_kigi();
def.system_prompt = tpl;
def
}
@@ -127,7 +127,7 @@ fn policy_with_gate(enabled: bool) -> ReminderPolicy {
use crate::session::goal_tracker::GoalStatus;
#[test]
fn goal_slash_and_harness_available_predicate_matrix() {
use kigi_tools::implementations::grok_build::UPDATE_GOAL_TOOL_NAME;
use kigi_tools::implementations::kigi::UPDATE_GOAL_TOOL_NAME;
let other = vec!["todo_write".to_string()];
let with_update = vec![UPDATE_GOAL_TOOL_NAME.to_string()];
for (goal_enabled, tool_names, expect) in [
@@ -1193,7 +1193,7 @@ async fn reasoning_only_doomloop_turn_captures_every_generation_as_segments() {
completion_tokens: Some(0),
reasoning_tokens: Some(4096),
prompt_tokens: Some(128),
model: "grok-test".to_string(),
model: "kigi-test".to_string(),
first_choice_seen: true,
}),
doom_loop_triggers: None,
@@ -2,10 +2,10 @@
//! (permission / `ask_user_question` / plan-approval) must carry a
//! non-empty `sessionId`, otherwise Tier-2 routing silently drops it
//! (`server.rs`). The invariant holds today; these tests pin it.
use kigi_tools::implementations::grok_build::ask_user_question::{
use kigi_tools::implementations::kigi::ask_user_question::{
AskUserQuestionExtRequest, AskUserQuestionMode,
};
use kigi_tools::implementations::grok_build::exit_plan_mode::ExitPlanModeExtRequest;
use kigi_tools::implementations::kigi::exit_plan_mode::ExitPlanModeExtRequest;
#[test]
fn ask_user_question_request_carries_session_id() {
@@ -51,7 +51,7 @@ fn skips_synthetic_reminder_at_index_one() {
/// Drives the real `handle_rebuild_agent_for_definition` path.
#[tokio::test(flavor = "current_thread")]
async fn rebuild_reinjects_goal_update_handle() {
use kigi_tools::implementations::grok_build::update_goal::{
use kigi_tools::implementations::kigi::update_goal::{
GoalUpdateHandle, UpdateGoalInput, envelope_for_test,
};
let local = tokio::task::LocalSet::new();
@@ -61,9 +61,7 @@ async fn rebuild_reinjects_goal_update_handle() {
let (persist_tx, _persist_rx) = tokio::sync::mpsc::unbounded_channel();
let actor = create_test_actor(0, 256_000, 85, gw_tx, persist_tx).await;
actor
.handle_rebuild_agent_for_definition(
kigi_agent::AgentDefinition::default_grok_build(),
)
.handle_rebuild_agent_for_definition(kigi_agent::AgentDefinition::default_kigi())
.await
.expect("zero-turn rebuild should succeed");
let bridge = actor.agent.borrow().tool_bridge().clone();
@@ -99,7 +97,7 @@ async fn rebuild_reinjects_goal_update_handle() {
.await;
}
/// The seeded skill used by the rebuild skill-reminder tests. A non-plugin
/// Local skill is always listable, so it renders into the grok markdown skill
/// Local skill is always listable, so it renders into the kigi markdown skill
/// catalog when the pending baseline is drained for a different agent.
fn regression_skill() -> kigi_tools::implementations::skills::types::SkillInfo {
kigi_tools::implementations::skills::types::SkillInfo {
@@ -149,9 +147,9 @@ fn stale_source_reminder() -> ConversationItem {
- stale-source-skill: from the source session.\n</system-reminder>",
)
}
/// Regression: a zero-turn agent rebuild INTO a grok/Default agent
/// Regression: a zero-turn agent rebuild INTO a kigi/Default agent
/// must re-inject the baseline skill `<system-reminder>`. `initialize()`
/// is otherwise the only place skills are surfaced for the grok agent, so
/// is otherwise the only place skills are surfaced for the kigi agent, so
/// before the fix a switch into such an agent — whose rebuilt bridge holds
/// a pending `BaselineChange` — dropped the skill listing for a no-tool first
/// turn. Drives the real `inject_baseline_skill_reminder` seam that
@@ -187,7 +185,7 @@ async fn rebuild_reinjects_baseline_skill_reminder_for_non_cursor() {
let text = reminder.text_content();
assert!(
text.contains("The following skills are available for use:"),
"reminder must carry the grok skill catalog header:\n{text}",
"reminder must carry the kigi skill catalog header:\n{text}",
);
assert!(
text.contains("regression-baseline-skill"),
@@ -88,7 +88,7 @@ async fn subagent_usage_fold_attribution_gate() {
#[test]
fn usage_drain_outcome_policy_matches_freeze_and_cancel() {
use super::turn::UsageDrainOutcome;
use kigi_tools::implementations::grok_build::task::types::SubagentOutstandingReply;
use kigi_tools::implementations::kigi::task::types::SubagentOutstandingReply;
let none = UsageDrainOutcome::from_outstanding_reply(None);
assert!(none.fail_closed);
@@ -341,11 +341,10 @@ async fn snapshot_ors_ledger_incomplete_even_when_reply_complete() {
/// Scripted coordinator stub: answers each `Outstanding` query with the next
/// queued reply, repeating the last one; other events are ignored.
fn scripted_outstanding_responder(
replies: Vec<kigi_tools::implementations::grok_build::task::types::SubagentOutstandingReply>,
) -> tokio::sync::mpsc::UnboundedSender<
kigi_tools::implementations::grok_build::task::types::SubagentEvent,
> {
use kigi_tools::implementations::grok_build::task::types::SubagentEvent;
replies: Vec<kigi_tools::implementations::kigi::task::types::SubagentOutstandingReply>,
) -> tokio::sync::mpsc::UnboundedSender<kigi_tools::implementations::kigi::task::types::SubagentEvent>
{
use kigi_tools::implementations::kigi::task::types::SubagentEvent;
let (tx, mut rx) = tokio::sync::mpsc::unbounded_channel::<SubagentEvent>();
tokio::task::spawn_local(async move {
let mut queue = replies.into_iter();
@@ -365,7 +364,7 @@ fn scripted_outstanding_responder(
/// ledgers are marked incomplete.
#[tokio::test(flavor = "current_thread")]
async fn freeze_timeout_marks_report_and_both_ledgers() {
use kigi_tools::implementations::grok_build::task::types::SubagentOutstandingReply;
use kigi_tools::implementations::kigi::task::types::SubagentOutstandingReply;
tokio::task::LocalSet::new()
.run_until(async {
let mut actor = make_actor().await;
@@ -404,7 +403,7 @@ async fn freeze_timeout_marks_report_and_both_ledgers() {
/// because its fold still lands on the session ledger at completion.
#[tokio::test(flavor = "current_thread")]
async fn freeze_background_only_flags_report_not_ledgers() {
use kigi_tools::implementations::grok_build::task::types::SubagentOutstandingReply;
use kigi_tools::implementations::kigi::task::types::SubagentOutstandingReply;
tokio::task::LocalSet::new()
.run_until(async {
let mut actor = make_actor().await;
@@ -446,7 +445,7 @@ async fn freeze_background_only_flags_report_not_ledgers() {
#[tokio::test(flavor = "current_thread")]
async fn finalize_background_only_flags_report_not_ledgers() {
use super::turn::UsageDrainOutcome;
use kigi_tools::implementations::grok_build::task::types::SubagentOutstandingReply;
use kigi_tools::implementations::kigi::task::types::SubagentOutstandingReply;
tokio::task::LocalSet::new()
.run_until(async {
@@ -583,7 +582,7 @@ async fn apply_miss_matching_pin_stains_prompt_and_session() {
/// Sticky (session-only) is report-only on freeze: session ledger stays complete.
#[tokio::test(flavor = "current_thread")]
async fn freeze_sticky_only_flags_report_not_ledgers() {
use kigi_tools::implementations::grok_build::task::types::SubagentOutstandingReply;
use kigi_tools::implementations::kigi::task::types::SubagentOutstandingReply;
tokio::task::LocalSet::new()
.run_until(async {
let mut actor = make_actor().await;
@@ -637,7 +636,7 @@ async fn freeze_sticky_only_flags_report_not_ledgers() {
/// A fold landing mid-drain completes cleanly: no incomplete flag anywhere.
#[tokio::test(flavor = "current_thread")]
async fn freeze_completes_when_fold_lands_mid_drain() {
use kigi_tools::implementations::grok_build::task::types::SubagentOutstandingReply;
use kigi_tools::implementations::kigi::task::types::SubagentOutstandingReply;
tokio::task::LocalSet::new()
.run_until(async {
let mut actor = make_actor().await;
@@ -21,16 +21,16 @@ pub(crate) async fn test_agent_default() -> kigi_agent::Agent {
/// resolve to their builtins when a turn is driven through `handle_prompt`.
#[cfg(test)]
pub(crate) async fn test_agent_with_goal_tool() -> kigi_agent::Agent {
use kigi_tools::implementations::grok_build::update_goal::UpdateGoalTool;
use kigi_tools::implementations::kigi::update_goal::UpdateGoalTool;
use kigi_tools::registry::types::ToolConfig;
test_agent_with_tools(vec![ToolConfig::for_tool::<UpdateGoalTool>()]).await
}
/// Grok-build agent with the real `TodoWriteTool` (id `todo_write`, kind
/// Kigi-build agent with the real `TodoWriteTool` (id `todo_write`, kind
/// `Plan`) registered, so `tool_for_kind(ToolKind::Plan)` resolves through the
/// live toolset instead of the literal fallback.
#[cfg(test)]
pub(crate) async fn test_grok_build_agent_with_todo() -> kigi_agent::Agent {
use kigi_tools::implementations::grok_build::todo::TodoWriteTool;
pub(crate) async fn test_kigi_agent_with_todo() -> kigi_agent::Agent {
use kigi_tools::implementations::kigi::todo::TodoWriteTool;
use kigi_tools::registry::types::ToolConfig;
test_agent_with_tools(vec![ToolConfig::for_tool::<TodoWriteTool>()]).await
}
@@ -39,8 +39,8 @@ pub(crate) async fn test_grok_build_agent_with_todo() -> kigi_agent::Agent {
/// `exit_plan_mode` only finalizes when `enter_plan_mode` is also present.
#[cfg(test)]
pub(crate) async fn test_agent_with_plan_tools() -> kigi_agent::Agent {
use kigi_tools::implementations::grok_build::enter_plan_mode::EnterPlanModeTool;
use kigi_tools::implementations::grok_build::exit_plan_mode::ExitPlanModeTool;
use kigi_tools::implementations::kigi::enter_plan_mode::EnterPlanModeTool;
use kigi_tools::implementations::kigi::exit_plan_mode::ExitPlanModeTool;
use kigi_tools::registry::types::ToolConfig;
test_agent_with_tools(vec![
ToolConfig::for_tool::<EnterPlanModeTool>(),
@@ -57,7 +57,7 @@ pub(crate) async fn test_agent_with_tools(
tools,
behavior_preset: None,
},
kigi_agent::AgentDefinition::default_grok_build(),
kigi_agent::AgentDefinition::default_kigi(),
std::sync::Arc::new(kigi_tools::computer::local::LocalTerminalBackend::new()),
)
.await
@@ -78,7 +78,7 @@ async fn test_agent_from_config(
backend,
fs,
cwd: std::path::PathBuf::from("/tmp"),
session_folder: std::env::temp_dir().join("grok-test"),
session_folder: std::env::temp_dir().join("kigi-test"),
session_env: std::sync::Arc::new(std::collections::HashMap::new()),
notification_handle: ToolNotificationHandle::noop(),
owner_session_id: None,
@@ -388,7 +388,7 @@ async fn send_now_cancel_stamps_cancel_trigger_on_turn_end() {
let mut wire_meta = None;
while let Ok(msg) = gateway_rx.try_recv() {
if let kigi_acp_lib::AcpClientMessage::ExtNotification(args) = msg
&& args.request.method.as_ref() == "x.ai/session_notification"
&& args.request.method.as_ref() == "kigi/session_notification"
&& let Ok(v) =
serde_json::from_str::<serde_json::Value>(args.request.params.get())
&& v["update"]["sessionUpdate"] == "turn_completed"
@@ -9,7 +9,7 @@ async fn web_search_errors_when_disabled() {
let builder = crate::tools::bridge::ToolBridge::get_builder();
let config = ToolServerConfig {
tools: vec![ToolConfig {
id: "GrokBuild:web_search".into(),
id: "Kigi:web_search".into(),
params: None,
name_override: None,
params_name_overrides: None,
@@ -26,13 +26,13 @@ async fn web_search_errors_when_disabled() {
backend: terminal,
fs,
cwd: std::env::temp_dir(),
session_folder: std::env::temp_dir().join("grok-web-search-disabled"),
session_folder: std::env::temp_dir().join("kigi-web-search-disabled"),
session_env: std::sync::Arc::new(std::collections::HashMap::new()),
notification_handle: ToolNotificationHandle::noop(),
owner_session_id: None,
parent_scheduler_handle: None,
skills: vec![],
state_path: std::env::temp_dir().join("grok-web-search-disabled/state.json"),
state_path: std::env::temp_dir().join("kigi-web-search-disabled/state.json"),
memory_backend: None,
web_search_config: kigi_tools::implementations::web_search::WebSearchConfig::Disabled,
web_fetch_config: Default::default(),