Add computer switching, crew reporting, job steps and markdown chat
- Bots have a current computer (bots.computer_id), switched from the chat header beside the model button or by clicking a computer the bot names ([computer:ID]); tasks run on it by default - search_computers runs one read-only command on all of a bot's computers; chat replies know their computers (compose-computers-note) - The coordinator can use every computer and grants or revokes crew access with assign_computer - Delegated jobs record requested_by_bot_id; the worker's result or failure is reported back in the coordinator's conversation - bots_queue_updates records each model turn of a job, pushed live and shown in the working-on panel - Live relay: every process pushes new messages, job steps and bot changes from the database to its own sockets, so work done elsewhere shows live - Bot messages render as markdown (react-markdown + remark-gfm, no raw HTML) with twui components; rail previews are plain text - Fix header button overflow in the model and computer selects - Bump @moduletrace/twui to 0.1.2 Co-Authored-By: Claude Opus 5.5 <[email protected]>
This commit is contained in:
@@ -0,0 +1,70 @@
|
||||
import { useState } from "react";
|
||||
import useServerEvent from "@/src/hooks/use-server-event";
|
||||
import type { BotUpdatedData } from "@/src/types";
|
||||
import type { BUN_SQLITE_COBBLE_COMPUTERS } from "@/db/types/db";
|
||||
import setBotComputer from "../(functions)/set-bot-computer";
|
||||
|
||||
export type BotComputers = {
|
||||
/**
|
||||
* The bot's computers, the one it's on first.
|
||||
*/
|
||||
computers: BUN_SQLITE_COBBLE_COMPUTERS[];
|
||||
/**
|
||||
* The computer being switched to, while the switch runs.
|
||||
*/
|
||||
switching_id?: number;
|
||||
error?: string;
|
||||
switchComputer: (params: { computer_id: number }) => Promise<void>;
|
||||
};
|
||||
|
||||
type Params = {
|
||||
bot_id: number;
|
||||
computers: BUN_SQLITE_COBBLE_COMPUTERS[];
|
||||
};
|
||||
|
||||
/**
|
||||
* Keeps the open bot's computers and switches the one it's on, in place:
|
||||
* no reload, the list comes back reordered. A switch made in another tab
|
||||
* arrives as `server:bot-updated` with the bot's `computer_id`.
|
||||
*/
|
||||
export default function useBotComputers({ bot_id, computers: initial }: Params): BotComputers {
|
||||
const [computers, setComputers] = useState(initial);
|
||||
const [switching_id, setSwitchingId] = useState<number>();
|
||||
const [error, setError] = useState<string>();
|
||||
|
||||
useServerEvent({
|
||||
event: "server:bot-updated",
|
||||
onData: (data: BotUpdatedData) => {
|
||||
const computer_id = data.computer_id;
|
||||
|
||||
if (data.id != bot_id || !computer_id) return;
|
||||
|
||||
setComputers((prev) => {
|
||||
const picked = prev.find((c) => c.id == computer_id);
|
||||
|
||||
return !picked || prev[0]?.id == computer_id
|
||||
? prev
|
||||
: [picked, ...prev.filter((c) => c.id != computer_id)];
|
||||
});
|
||||
},
|
||||
});
|
||||
|
||||
const switchComputer = async ({ computer_id }: { computer_id: number }) => {
|
||||
if (switching_id || computers[0]?.id == computer_id) return;
|
||||
|
||||
setSwitchingId(computer_id);
|
||||
setError(undefined);
|
||||
|
||||
const res = await setBotComputer({ bot_id, computer_id }).catch(() => null);
|
||||
|
||||
if (res?.success && res.payload?.length) {
|
||||
setComputers(res.payload);
|
||||
} else {
|
||||
setError(res?.msg || "Couldn't switch computers");
|
||||
}
|
||||
|
||||
setSwitchingId(undefined);
|
||||
};
|
||||
|
||||
return { computers, switching_id, error, switchComputer };
|
||||
}
|
||||
Reference in New Issue
Block a user