From 5f60fc01d748594318318d1f160bd4a93595c3b3 Mon Sep 17 00:00:00 2001 From: Cristina Poncela Cubeiro <140309543+cristinaponcela@users.noreply.github.com> Date: Thu, 18 Jun 2026 13:09:48 +0200 Subject: [PATCH] feat: machine and instance storage --- packages/orchestrator/src/index.ts | 2 + packages/orchestrator/src/ipc/protocol.ts | 4 +- packages/orchestrator/src/storage.ts | 62 +++++++++++++++++++++++ packages/orchestrator/src/types.ts | 18 +++++++ 4 files changed, 85 insertions(+), 1 deletion(-) create mode 100644 packages/orchestrator/src/storage.ts create mode 100644 packages/orchestrator/src/types.ts diff --git a/packages/orchestrator/src/index.ts b/packages/orchestrator/src/index.ts index 196332d8..4f017322 100644 --- a/packages/orchestrator/src/index.ts +++ b/packages/orchestrator/src/index.ts @@ -2,3 +2,5 @@ export * from "./config.ts"; export * from "./ipc/client.ts"; export * from "./ipc/protocol.ts"; export * from "./ipc/server.ts"; +export * from "./storage.ts"; +export * from "./types.ts"; diff --git a/packages/orchestrator/src/ipc/protocol.ts b/packages/orchestrator/src/ipc/protocol.ts index ebb2815f..87c24c7a 100644 --- a/packages/orchestrator/src/ipc/protocol.ts +++ b/packages/orchestrator/src/ipc/protocol.ts @@ -1,3 +1,5 @@ +import type { InstanceStatus } from "../types.ts"; + export interface SpawnRequest { type: "spawn"; cwd: string; @@ -31,7 +33,7 @@ export type OrchestratorRequest = RequestMap[keyof RequestMap]; export interface InstanceSummary { id: string; - status: "starting" | "online" | "stopping" | "stopped" | "error"; + status: InstanceStatus; cwd: string; label?: string; sessionId?: string; diff --git a/packages/orchestrator/src/storage.ts b/packages/orchestrator/src/storage.ts new file mode 100644 index 00000000..29eb3213 --- /dev/null +++ b/packages/orchestrator/src/storage.ts @@ -0,0 +1,62 @@ +import { existsSync, mkdirSync, readFileSync, writeFileSync } from "node:fs"; +import { getInstancesPath, getMachinePath, getOrchestratorDir } from "./config.ts"; +import type { InstanceRecord, MachineRecord } from "./types.ts"; + +function ensureOrchestratorDir(): void { + const orchestratorDir = getOrchestratorDir(); + if (!existsSync(orchestratorDir)) { + mkdirSync(orchestratorDir, { recursive: true }); + } +} + +export function loadMachine(): MachineRecord | undefined { + const machinePath = getMachinePath(); + if (!existsSync(machinePath)) { + return undefined; + } + + const data = readFileSync(machinePath, "utf-8"); + return JSON.parse(data) as MachineRecord; +} + +export function saveMachine(machine: MachineRecord): void { + ensureOrchestratorDir(); + writeFileSync(getMachinePath(), JSON.stringify(machine, null, 2)); +} + +export function loadInstances(): InstanceRecord[] { + const instancesPath = getInstancesPath(); + if (!existsSync(instancesPath)) { + return []; + } + + const data = readFileSync(instancesPath, "utf-8"); + return JSON.parse(data) as InstanceRecord[]; +} + +export function saveInstances(instances: InstanceRecord[]): void { + ensureOrchestratorDir(); + writeFileSync(getInstancesPath(), JSON.stringify(instances, null, 2)); +} + +export function getInstance(instanceId: string): InstanceRecord | undefined { + return loadInstances().find((instance) => instance.id === instanceId); +} + +export function upsertInstance(instance: InstanceRecord): void { + const instances = loadInstances(); + const index = instances.findIndex((existing) => existing.id === instance.id); + if (index === -1) { + instances.push(instance); + saveInstances(instances); + return; + } + + instances[index] = instance; + saveInstances(instances); +} + +export function removeInstance(instanceId: string): void { + const instances = loadInstances().filter((instance) => instance.id !== instanceId); + saveInstances(instances); +} diff --git a/packages/orchestrator/src/types.ts b/packages/orchestrator/src/types.ts new file mode 100644 index 00000000..d2e4d06e --- /dev/null +++ b/packages/orchestrator/src/types.ts @@ -0,0 +1,18 @@ +export type InstanceStatus = "starting" | "online" | "stopping" | "stopped" | "error"; + +export interface MachineRecord { + id: string; + createdAt: string; + lastSeenAt?: string; + label?: string; +} + +export interface InstanceRecord { + id: string; + status: InstanceStatus; + cwd: string; + createdAt: string; + lastSeenAt?: string; + label?: string; + sessionId?: string; +}