feat(app): UDS bridge (channel/invoke/emit) + xterm.js terminal, M0 e2e works
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,75 @@
|
||||
import { invoke, Channel } from "@tauri-apps/api/core";
|
||||
import { listen } from "@tauri-apps/api/event";
|
||||
|
||||
export interface WorkspaceStatus {
|
||||
workspace_id: string;
|
||||
path: string;
|
||||
surfaces: string[];
|
||||
}
|
||||
|
||||
export async function openWorkspace(path: string): Promise<string> {
|
||||
const data = await invoke<{ workspace_id: string }>("open", { path });
|
||||
return data.workspace_id;
|
||||
}
|
||||
|
||||
export async function newSurface(
|
||||
workspaceId: string,
|
||||
cols: number,
|
||||
rows: number,
|
||||
command?: string,
|
||||
args: string[] = []
|
||||
): Promise<string> {
|
||||
const data = await invoke<{ surface_id: string }>("new_surface", {
|
||||
workspaceId,
|
||||
command: command ?? null,
|
||||
args,
|
||||
cols,
|
||||
rows,
|
||||
});
|
||||
return data.surface_id;
|
||||
}
|
||||
|
||||
export async function sendInput(surfaceId: string, data: Uint8Array): Promise<void> {
|
||||
await invoke("input", { surfaceId, data: Array.from(data) });
|
||||
}
|
||||
|
||||
export async function resizeSurface(surfaceId: string, cols: number, rows: number): Promise<void> {
|
||||
await invoke("resize", { surfaceId, cols, rows });
|
||||
}
|
||||
|
||||
export interface AttachResult {
|
||||
snapshot: string;
|
||||
cols: number;
|
||||
rows: number;
|
||||
}
|
||||
|
||||
export async function attachSurface(
|
||||
surfaceId: string,
|
||||
onOutput: (bytes: Uint8Array) => void
|
||||
): Promise<AttachResult> {
|
||||
const channel = new Channel<number[]>();
|
||||
channel.onmessage = (msg) => onOutput(new Uint8Array(msg));
|
||||
return await invoke<AttachResult>("attach", { surfaceId, onOutput: channel });
|
||||
}
|
||||
|
||||
export async function detachSurface(surfaceId: string): Promise<void> {
|
||||
await invoke("detach", { surfaceId });
|
||||
}
|
||||
|
||||
export async function getStatus(): Promise<WorkspaceStatus[]> {
|
||||
const data = await invoke<{ workspaces: WorkspaceStatus[] }>("status");
|
||||
return data.workspaces;
|
||||
}
|
||||
|
||||
export type DaemonEvt =
|
||||
| { evt: "exit"; data: { surface_id: string; code: number } }
|
||||
| { evt: "surface_created"; data: { surface_id: string; workspace_id: string } }
|
||||
| { evt: "surface_closed"; data: { surface_id: string } };
|
||||
|
||||
export function onDaemonEvent(handler: (evt: DaemonEvt) => void): Promise<() => void> {
|
||||
return listen<DaemonEvt>("spacesh:evt", (e) => handler(e.payload));
|
||||
}
|
||||
|
||||
export function onDaemonRawEvent(name: string, handler: () => void): Promise<() => void> {
|
||||
return listen(name, () => handler());
|
||||
}
|
||||
Reference in New Issue
Block a user