test: use testEffect for plugin workspace adaptor (#25052)

This commit is contained in:
Kit Langton
2026-04-30 12:54:53 -04:00
committed by GitHub
parent 79e23b7eb9
commit e4ac936eb9
@@ -1,8 +1,10 @@
import { afterAll, afterEach, describe, expect, test } from "bun:test" import { afterAll, afterEach, describe, expect } from "bun:test"
import { Effect } from "effect" import { Effect, Layer } from "effect"
import { CrossSpawnSpawner } from "@opencode-ai/core/cross-spawn-spawner"
import path from "path" import path from "path"
import { pathToFileURL } from "url" import { pathToFileURL } from "url"
import { tmpdir } from "../fixture/fixture" import { provideTmpdirInstance } from "../fixture/fixture"
import { testEffect } from "../lib/effect"
const disableDefault = process.env.OPENCODE_DISABLE_DEFAULT_PLUGINS const disableDefault = process.env.OPENCODE_DISABLE_DEFAULT_PLUGINS
process.env.OPENCODE_DISABLE_DEFAULT_PLUGINS = "1" process.env.OPENCODE_DISABLE_DEFAULT_PLUGINS = "1"
@@ -11,6 +13,7 @@ const { Flag } = await import("@opencode-ai/core/flag/flag")
const { Plugin } = await import("../../src/plugin/index") const { Plugin } = await import("../../src/plugin/index")
const { Workspace } = await import("../../src/control-plane/workspace") const { Workspace } = await import("../../src/control-plane/workspace")
const { Instance } = await import("../../src/project/instance") const { Instance } = await import("../../src/project/instance")
const it = testEffect(Layer.mergeAll(Plugin.defaultLayer, CrossSpawnSpawner.defaultLayer))
const experimental = Flag.OPENCODE_EXPERIMENTAL_WORKSPACES const experimental = Flag.OPENCODE_EXPERIMENTAL_WORKSPACES
@@ -31,79 +34,77 @@ afterAll(() => {
}) })
describe("plugin.workspace", () => { describe("plugin.workspace", () => {
test("plugin can install a workspace adaptor", async () => { it.live("plugin can install a workspace adaptor", () =>
await using tmp = await tmpdir({ provideTmpdirInstance((dir) =>
init: async (dir) => { Effect.gen(function* () {
const type = `plug-${Math.random().toString(36).slice(2)}` const type = `plug-${Math.random().toString(36).slice(2)}`
const file = path.join(dir, "plugin.ts") const file = path.join(dir, "plugin.ts")
const mark = path.join(dir, "created.json") const mark = path.join(dir, "created.json")
const space = path.join(dir, "space") const space = path.join(dir, "space")
await Bun.write( yield* Effect.promise(() =>
file, Bun.write(
[ file,
"export default async ({ experimental_workspace }) => {", [
` experimental_workspace.register(${JSON.stringify(type)}, {`, "export default async ({ experimental_workspace }) => {",
' name: "plug",', ` experimental_workspace.register(${JSON.stringify(type)}, {`,
' description: "plugin workspace adaptor",', ' name: "plug",',
" configure(input) {", ' description: "plugin workspace adaptor",',
` return { ...input, name: "plug", branch: "plug/main", directory: ${JSON.stringify(space)} }`, " configure(input) {",
" },", ` return { ...input, name: "plug", branch: "plug/main", directory: ${JSON.stringify(space)} }`,
" async create(input) {", " },",
` await Bun.write(${JSON.stringify(mark)}, JSON.stringify(input))`, " async create(input) {",
" },", ` await Bun.write(${JSON.stringify(mark)}, JSON.stringify(input))`,
" async remove() {},", " },",
" target(input) {", " async remove() {},",
' return { type: "local", directory: input.directory }', " target(input) {",
" },", ' return { type: "local", directory: input.directory }',
" })", " },",
" return {}", " })",
"}", " return {}",
"", "}",
].join("\n"), "",
) ].join("\n"),
await Bun.write(
path.join(dir, "opencode.json"),
JSON.stringify(
{
$schema: "https://opencode.ai/config.json",
plugin: [pathToFileURL(file).href],
},
null,
2,
), ),
) )
return { mark, space, type } yield* Effect.promise(() =>
}, Bun.write(
}) path.join(dir, "opencode.json"),
JSON.stringify(
{
$schema: "https://opencode.ai/config.json",
plugin: [pathToFileURL(file).href],
},
null,
2,
),
),
)
const info = await Instance.provide({ const plugin = yield* Plugin.Service
directory: tmp.path, yield* plugin.init()
fn: async () => const info = yield* Effect.promise(() =>
Effect.gen(function* () { Workspace.create({
const plugin = yield* Plugin.Service type,
yield* plugin.init()
return Workspace.create({
type: tmp.extra.type,
branch: null, branch: null,
extra: { key: "value" }, extra: { key: "value" },
projectID: Instance.project.id, projectID: Instance.project.id,
}) }),
}).pipe(Effect.provide(Plugin.defaultLayer), Effect.runPromise), )
})
expect(info.type).toBe(tmp.extra.type) expect(info.type).toBe(type)
expect(info.name).toBe("plug") expect(info.name).toBe("plug")
expect(info.branch).toBe("plug/main") expect(info.branch).toBe("plug/main")
expect(info.directory).toBe(tmp.extra.space) expect(info.directory).toBe(space)
expect(info.extra).toEqual({ key: "value" }) expect(info.extra).toEqual({ key: "value" })
expect(JSON.parse(await Bun.file(tmp.extra.mark).text())).toMatchObject({ expect(JSON.parse(yield* Effect.promise(() => Bun.file(mark).text()))).toMatchObject({
type: tmp.extra.type, type,
name: "plug", name: "plug",
branch: "plug/main", branch: "plug/main",
directory: tmp.extra.space, directory: space,
extra: { key: "value" }, extra: { key: "value" },
}) })
}) }),
),
)
}) })