export * as CommandV2 from "./command" import { makeLocationNode } from "./effect/app-node" import { Context, Effect, Layer, Types } from "effect" import { Command } from "@opencode-ai/schema/command" import { State } from "./state" export const Info = Command.Info export type Info = Command.Info export type Data = { commands: Map> } export type Draft = { list: () => readonly Info[] get: (name: string) => Info | undefined update: (name: string, update: (command: Types.DeepMutable) => void) => void remove: (name: string) => void } export interface Interface extends State.Transformable { readonly get: (name: string) => Effect.Effect readonly list: () => Effect.Effect } export class Service extends Context.Service()("@opencode/v2/Command") {} export const layer = Layer.effect( Service, Effect.sync(() => { const state = State.create({ initial: () => ({ commands: new Map() }), draft: (draft) => ({ list: () => Array.from(draft.commands.values()) as Info[], get: (name) => draft.commands.get(name), update: (name, update) => { const current = draft.commands.get(name) ?? ({ name, template: "" } as Types.DeepMutable) if (!draft.commands.has(name)) draft.commands.set(name, current) update(current) current.name = name }, remove: (name) => { draft.commands.delete(name) }, }), }) return Service.of({ reload: state.reload, transform: state.transform, get: Effect.fn("CommandV2.get")(function* (name) { return state.get().commands.get(name) }), list: Effect.fn("CommandV2.list")(function* () { return Array.from(state.get().commands.values()) }), }) }), ) export const locationLayer = layer export const node = makeLocationNode({ service: Service, layer, deps: [] })