huskies: merge 1106 story Chat bootstrap Phase 1: new project chat command spawns a bare project container and registers it with the gateway
This commit is contained in:
@@ -1,5 +1,6 @@
|
||||
//! Matrix bot context — shared state for the Matrix bot (rooms, history, permissions).
|
||||
use crate::chat::ChatTransport;
|
||||
use crate::service::gateway::config::ProjectEntry;
|
||||
use crate::service::timer::TimerStore;
|
||||
use crate::services::Services;
|
||||
use matrix_sdk::ruma::{OwnedEventId, OwnedRoomId, OwnedUserId};
|
||||
@@ -94,6 +95,11 @@ pub struct BotContext {
|
||||
/// Used to proxy bot commands to the active project over WebSocket (`/ws`).
|
||||
/// Empty in standalone mode.
|
||||
pub gateway_project_urls: BTreeMap<String, String>,
|
||||
/// In gateway mode: shared live projects map from [`GatewayState`].
|
||||
///
|
||||
/// The `new project` command writes here so HTTP handlers see the new entry
|
||||
/// immediately without requiring a gateway restart. `None` in standalone mode.
|
||||
pub gateway_projects_store: Option<Arc<RwLock<BTreeMap<String, ProjectEntry>>>>,
|
||||
/// Pipeline transition events buffered since the last LLM turn.
|
||||
///
|
||||
/// A background task appends one compact audit line per real stage
|
||||
@@ -300,6 +306,7 @@ mod tests {
|
||||
gateway_active_project,
|
||||
gateway_projects,
|
||||
gateway_project_urls,
|
||||
gateway_projects_store: None,
|
||||
pending_pipeline_events: Arc::new(TokioMutex::new(Vec::new())),
|
||||
pending_gateway_events: Arc::new(TokioMutex::new(Vec::new())),
|
||||
handled_incoming_event_ids: Arc::new(TokioMutex::new(SeenEventIds::new(
|
||||
|
||||
@@ -193,7 +193,7 @@ pub(in crate::chat::transport::matrix::bot) async fn on_room_message(
|
||||
if ctx.is_gateway() {
|
||||
// Commands that are meaningful on the gateway itself (no project state needed).
|
||||
const GATEWAY_LOCAL_COMMANDS: &[&str] =
|
||||
&["help", "ambient", "reset", "switch", "all_status"];
|
||||
&["help", "ambient", "reset", "switch", "all_status", "new"];
|
||||
|
||||
let stripped = crate::chat::util::strip_bot_mention(
|
||||
&user_message,
|
||||
@@ -260,6 +260,38 @@ pub(in crate::chat::transport::matrix::bot) async fn on_room_message(
|
||||
// Gateway-local commands and freeform text fall through to normal handling below.
|
||||
}
|
||||
|
||||
// In gateway mode, handle the "new project <name>" command to bootstrap a
|
||||
// bare project container and register it with the gateway.
|
||||
if ctx.is_gateway()
|
||||
&& let Some(project_name) = super::super::super::new_project::extract_new_project_command(
|
||||
&user_message,
|
||||
&ctx.services.bot_name,
|
||||
ctx.matrix_user_id.as_str(),
|
||||
)
|
||||
{
|
||||
slog!("[matrix-bot] Handling new project command from {sender}: name={project_name:?}");
|
||||
let response = if let Some(ref store) = ctx.gateway_projects_store {
|
||||
super::super::super::new_project::handle_new_project(
|
||||
&project_name,
|
||||
store,
|
||||
&ctx.services.project_root,
|
||||
)
|
||||
.await
|
||||
} else {
|
||||
"Gateway projects store unavailable — cannot create project.".to_string()
|
||||
};
|
||||
let html = markdown_to_html(&response);
|
||||
if let Ok(msg_id) = ctx
|
||||
.transport
|
||||
.send_message(&room_id_str, &response, &html)
|
||||
.await
|
||||
&& let Ok(event_id) = msg_id.parse()
|
||||
{
|
||||
ctx.bot_sent_event_ids.lock().await.insert(event_id);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
// Check for bot-level commands (help, status, ambient, …) before invoking
|
||||
// the LLM. All commands are registered in commands.rs — no special-casing
|
||||
// needed here.
|
||||
|
||||
@@ -30,6 +30,13 @@ pub async fn run_bot(
|
||||
gateway_active_project: Option<Arc<RwLock<String>>>,
|
||||
gateway_projects: Vec<String>,
|
||||
gateway_project_urls: std::collections::BTreeMap<String, String>,
|
||||
gateway_projects_store: Option<
|
||||
Arc<
|
||||
RwLock<
|
||||
std::collections::BTreeMap<String, crate::service::gateway::config::ProjectEntry>,
|
||||
>,
|
||||
>,
|
||||
>,
|
||||
timer_store: Arc<TimerStore>,
|
||||
gateway_event_rx: Option<
|
||||
tokio::sync::broadcast::Receiver<crate::service::gateway::GatewayStatusEvent>,
|
||||
@@ -399,6 +406,7 @@ pub async fn run_bot(
|
||||
gateway_active_project,
|
||||
gateway_projects,
|
||||
gateway_project_urls,
|
||||
gateway_projects_store,
|
||||
pending_pipeline_events,
|
||||
pending_gateway_events,
|
||||
handled_incoming_event_ids: Arc::new(TokioMutex::new(super::context::SeenEventIds::new(
|
||||
|
||||
Reference in New Issue
Block a user