@opencode/server 2.0.8 → 2.0.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (104) hide show
  1. package/dist/api.d.ts +4 -4
  2. package/dist/api.js +10 -9
  3. package/dist/auth.js +12 -17
  4. package/dist/chunks/fetch-00nn3k4b.js +20 -0
  5. package/dist/chunks/fetch-04xw3v55.js +23 -0
  6. package/dist/chunks/fetch-0d9kah4z.js +23 -0
  7. package/dist/chunks/fetch-19c9ysa1.js +61 -0
  8. package/dist/chunks/fetch-1c4qas2w.js +346 -0
  9. package/dist/chunks/fetch-254zvkj6.js +22 -0
  10. package/dist/chunks/fetch-3kzx88w9.js +26 -0
  11. package/dist/chunks/fetch-4cf3x1kw.js +21 -0
  12. package/dist/chunks/fetch-4g0fa6m0.js +32 -0
  13. package/dist/chunks/fetch-4vn5bvkr.js +25 -0
  14. package/dist/chunks/fetch-5rwqcaw2.js +33 -0
  15. package/dist/chunks/fetch-6gkz39ey.js +55 -0
  16. package/dist/chunks/fetch-6nvan4e0.js +17 -0
  17. package/dist/chunks/fetch-7rzt3wm8.js +13 -0
  18. package/dist/chunks/fetch-8bajbwjh.js +40 -0
  19. package/dist/chunks/fetch-99sfd1j8.js +83 -0
  20. package/dist/chunks/fetch-9rqn6x4v.js +16 -0
  21. package/dist/chunks/fetch-a6yp8301.js +156 -0
  22. package/dist/chunks/fetch-arj41x43.js +77 -0
  23. package/dist/chunks/fetch-b0b71rwa.js +39 -0
  24. package/dist/chunks/fetch-bjrwanme.js +22 -0
  25. package/dist/chunks/fetch-br99j6q1.js +35 -0
  26. package/dist/chunks/fetch-ceh2h0m9.js +25 -0
  27. package/dist/chunks/fetch-csspsf0t.js +99 -0
  28. package/dist/chunks/fetch-d4bshj6j.js +37 -0
  29. package/dist/chunks/fetch-hezj1jdf.js +7 -0
  30. package/dist/chunks/fetch-hjnxtxmk.js +34 -0
  31. package/dist/chunks/fetch-j2pfq4q6.js +42 -0
  32. package/dist/chunks/fetch-m6wvgbfq.js +60 -0
  33. package/dist/chunks/fetch-n0er2m55.js +163 -0
  34. package/dist/chunks/fetch-pnqq1zxv.js +29 -0
  35. package/dist/chunks/fetch-q0ycym90.js +13 -0
  36. package/dist/chunks/fetch-q4bn6dy8.js +39 -0
  37. package/dist/chunks/fetch-qm92ga5h.js +26 -0
  38. package/dist/chunks/fetch-qnwpcgp7.js +22 -0
  39. package/dist/chunks/fetch-r7e9r02j.js +13 -0
  40. package/dist/chunks/fetch-rcg4y18n.js +59 -0
  41. package/dist/chunks/fetch-req22b70.js +22 -0
  42. package/dist/chunks/fetch-s4aja1df.js +36 -0
  43. package/dist/chunks/fetch-smaf4a18.js +28 -0
  44. package/dist/chunks/fetch-t8yzmczr.js +18 -0
  45. package/dist/chunks/fetch-vgpejxxy.js +149 -0
  46. package/dist/chunks/fetch-xsrtpxyd.js +23 -0
  47. package/dist/chunks/fetch-yc7nft6q.js +5 -0
  48. package/dist/chunks/fetch-ychamt23.js +139 -0
  49. package/dist/chunks/fetch-ysabas57.js +13 -0
  50. package/dist/chunks/fetch-z5shrcz9.js +19 -0
  51. package/dist/chunks/fetch-zp2jm6dt.js +15 -0
  52. package/dist/chunks/fetch-zyv89x5n.js +30 -0
  53. package/dist/cors.js +10 -36
  54. package/dist/event-feed.js +20 -60
  55. package/dist/fetch.js +53 -11
  56. package/dist/handlers/agent.js +11 -17
  57. package/dist/handlers/command.js +11 -5
  58. package/dist/handlers/config.js +11 -16
  59. package/dist/handlers/credential.js +11 -14
  60. package/dist/handlers/debug.js +11 -11
  61. package/dist/handlers/event.js +12 -27
  62. package/dist/handlers/form.js +11 -9
  63. package/dist/handlers/fs.js +11 -22
  64. package/dist/handlers/generate.js +11 -15
  65. package/dist/handlers/integration.js +10 -142
  66. package/dist/handlers/location.js +11 -16
  67. package/dist/handlers/mcp.js +11 -31
  68. package/dist/handlers/message.js +10 -42
  69. package/dist/handlers/migration.js +11 -7
  70. package/dist/handlers/model.js +11 -14
  71. package/dist/handlers/permission.js +11 -57
  72. package/dist/handlers/persistent-pty.js +12 -135
  73. package/dist/handlers/plugin.js +11 -47
  74. package/dist/handlers/project.js +11 -9
  75. package/dist/handlers/provider.js +11 -20
  76. package/dist/handlers/pty-socket.js +6 -4
  77. package/dist/handlers/pty.js +13 -107
  78. package/dist/handlers/reference.js +11 -5
  79. package/dist/handlers/rpc.js +11 -15
  80. package/dist/handlers/server.js +12 -13
  81. package/dist/handlers/session-error.js +12 -26
  82. package/dist/handlers/session.js +10 -311
  83. package/dist/handlers/shell.js +11 -25
  84. package/dist/handlers/skill.js +11 -5
  85. package/dist/handlers/vcs.js +11 -19
  86. package/dist/handlers/websearch.js +11 -31
  87. package/dist/handlers/worktree.js +11 -37
  88. package/dist/handlers.d.ts +1 -1
  89. package/dist/handlers.js +46 -33
  90. package/dist/location.js +15 -49
  91. package/dist/middleware/authorization.js +11 -49
  92. package/dist/middleware/form-location.js +10 -25
  93. package/dist/middleware/schema-error.js +8 -15
  94. package/dist/middleware/session-location.js +10 -19
  95. package/dist/options.js +5 -1
  96. package/dist/process.js +108 -28
  97. package/dist/pty-environment.js +12 -9
  98. package/dist/request-tracing.js +6 -2
  99. package/dist/routes.d.ts +2 -2
  100. package/dist/routes.js +52 -118
  101. package/dist/server-info.js +12 -22
  102. package/dist/service-status.js +8 -11
  103. package/dist/workerd.js +80 -12
  104. package/package.json +8 -8
@@ -1,43 +1,11 @@
1
- import { SessionMessage } from "@opencode/core/session/message";
2
- import { Session } from "@opencode/core/session";
3
- import { Effect, Schema } from "effect";
4
- import { HttpApiBuilder } from "effect/unstable/httpapi";
5
- import { Api } from "../api";
6
- import { InvalidCursorError } from "@opencode/protocol/errors";
7
- import { failedMessageDecode, missingSession } from "./session-error";
8
- const DefaultMessagesLimit = 50, Cursor = Schema.Struct({
9
- id: SessionMessage.ID,
10
- order: Schema.Union([Schema.Literal("asc"), Schema.Literal("desc")]),
11
- direction: Schema.Union([Schema.Literal("previous"), Schema.Literal("next")])
12
- }), decodeCursor = Schema.decodeUnknownSync(Cursor), cursor = {
13
- encode(message, order, direction) {
14
- return Buffer.from(JSON.stringify({ id: message.id, order, direction })).toString("base64url");
15
- },
16
- decode(input) {
17
- return decodeCursor(JSON.parse(Buffer.from(input, "base64url").toString("utf8")));
18
- }
1
+ import {
2
+ MessageHandler2
3
+ } from "../chunks/fetch-rcg4y18n.js";
4
+ import"../chunks/fetch-z5shrcz9.js";
5
+ import"../chunks/fetch-3kzx88w9.js";
6
+ import"../chunks/fetch-5rwqcaw2.js";
7
+ import"../chunks/fetch-6gkz39ey.js";
8
+ import"../chunks/fetch-smaf4a18.js";
9
+ export {
10
+ MessageHandler2 as MessageHandler
19
11
  };
20
- export const MessageHandler = HttpApiBuilder.group(Api, "server.message", (handlers) => Effect.gen(function* () {
21
- const session = yield* Session.Service;
22
- return handlers.handle("session.messages", Effect.fn(function* (ctx) {
23
- if (ctx.query.cursor && ctx.query.order !== void 0)
24
- return yield* new InvalidCursorError({ message: "Cursor cannot be combined with order" });
25
- const decoded = yield* Effect.try({
26
- try: () => ctx.query.cursor ? cursor.decode(ctx.query.cursor) : void 0,
27
- catch: () => new InvalidCursorError({ message: "Invalid cursor" })
28
- }), order = decoded?.order ?? ctx.query.order ?? "desc", messages = yield* session.messages({
29
- sessionID: ctx.params.sessionID,
30
- limit: ctx.query.limit ?? DefaultMessagesLimit,
31
- order,
32
- type: ctx.query.type,
33
- cursor: decoded ? { id: decoded.id, direction: decoded.direction } : void 0
34
- }).pipe(Effect.catchTag("Session.NotFoundError", missingSession), Effect.catchTag("Session.MessageDecodeError", failedMessageDecode)), first = messages[0], last = messages.at(-1);
35
- return {
36
- data: messages,
37
- cursor: {
38
- previous: first ? cursor.encode(first, order, "previous") : void 0,
39
- next: last ? cursor.encode(last, order, "next") : void 0
40
- }
41
- };
42
- }));
43
- }));
@@ -1,7 +1,11 @@
1
- import { V1Migration } from "@opencode/core/database/v1-migration";
2
- import { HttpApiBuilder } from "effect/unstable/httpapi";
3
- import { Effect } from "effect";
4
- import { Api } from "../api";
5
- export const MigrationHandler = HttpApiBuilder.group(Api, "server.migration", (handlers) => handlers.handle("migration.v1.status", Effect.fn(function* () {
6
- return yield* V1Migration.status();
7
- })));
1
+ import {
2
+ MigrationHandler2
3
+ } from "../chunks/fetch-7rzt3wm8.js";
4
+ import"../chunks/fetch-z5shrcz9.js";
5
+ import"../chunks/fetch-3kzx88w9.js";
6
+ import"../chunks/fetch-5rwqcaw2.js";
7
+ import"../chunks/fetch-6gkz39ey.js";
8
+ import"../chunks/fetch-smaf4a18.js";
9
+ export {
10
+ MigrationHandler2 as MigrationHandler
11
+ };
@@ -1,14 +1,11 @@
1
- import { Model } from "@opencode/core/model";
2
- import { Effect } from "effect";
3
- import { HttpApiBuilder } from "effect/unstable/httpapi";
4
- import { Api } from "../api";
5
- import { response } from "../location";
6
- export const ModelHandler = HttpApiBuilder.group(Api, "server.model", (handlers) => Effect.gen(function* () {
7
- return handlers.handle("model.list", Effect.fn(function* () {
8
- const models = yield* Model.Service;
9
- return yield* response(models.available());
10
- })).handle("model.default", Effect.fn(function* () {
11
- const models = yield* Model.Service;
12
- return yield* response(models.default());
13
- }));
14
- }));
1
+ import {
2
+ ModelHandler2
3
+ } from "../chunks/fetch-254zvkj6.js";
4
+ import"../chunks/fetch-z5shrcz9.js";
5
+ import"../chunks/fetch-3kzx88w9.js";
6
+ import"../chunks/fetch-5rwqcaw2.js";
7
+ import"../chunks/fetch-6gkz39ey.js";
8
+ import"../chunks/fetch-smaf4a18.js";
9
+ export {
10
+ ModelHandler2 as ModelHandler
11
+ };
@@ -1,57 +1,11 @@
1
- import { Instance } from "@opencode/core/instance/service";
2
- import { Location } from "@opencode/core/location";
3
- import { Permission } from "@opencode/core/permission";
4
- import { PermissionSaved } from "@opencode/core/permission/saved";
5
- import { Session } from "@opencode/core/session";
6
- import { Effect } from "effect";
7
- import { HttpApiBuilder, HttpApiSchema } from "effect/unstable/httpapi";
8
- import { Api } from "../api";
9
- import { PermissionNotFoundError } from "@opencode/protocol/errors";
10
- import { response, sessionInfo } from "../location";
11
- import { missingSession } from "./session-error";
12
- function missingRequest(id) {
13
- return new PermissionNotFoundError({ requestID: id, message: `Permission request not found: ${id}` });
14
- }
15
- export const PermissionHandler = HttpApiBuilder.group(Api, "server.permission", (handlers) => Effect.gen(function* () {
16
- const instances = yield* Instance.Service, sessions = yield* Session.Service, requireOwnedRequest = Effect.fnUntraced(function* (sessionID, requestID) {
17
- const permission = yield* Permission.Service, request = yield* permission.get(requestID);
18
- if (!request || request.sessionID !== sessionID)
19
- return yield* missingRequest(requestID);
20
- return { permission, request };
21
- });
22
- return handlers.handle("permission.request.list", Effect.fn(function* () {
23
- const permission = yield* Permission.Service;
24
- return yield* response(permission.list());
25
- })).handle("session.permission.create", Effect.fn(function* (ctx) {
26
- return {
27
- data: yield* (yield* Permission.Service).ask({
28
- id: ctx.payload.id,
29
- sessionID: ctx.params.sessionID,
30
- action: ctx.payload.action,
31
- resources: ctx.payload.resources,
32
- save: ctx.payload.save,
33
- metadata: ctx.payload.metadata,
34
- source: ctx.payload.source,
35
- agent: ctx.payload.agent
36
- }).pipe(Effect.catchTag("Session.NotFoundError", missingSession))
37
- };
38
- })).handle("session.permission.list", Effect.fn(function* (ctx) {
39
- const session = yield* sessionInfo(sessions, ctx.params.sessionID);
40
- return { data: yield* Permission.Service.use((permission) => permission.forSession(ctx.params.sessionID)).pipe(instances.provide(session)) };
41
- })).handle("session.permission.get", Effect.fn(function* (ctx) {
42
- return { data: (yield* requireOwnedRequest(ctx.params.sessionID, ctx.params.requestID)).request };
43
- })).handle("session.permission.reply", Effect.fn(function* (ctx) {
44
- yield* (yield* requireOwnedRequest(ctx.params.sessionID, ctx.params.requestID)).permission.reply({ requestID: ctx.params.requestID, reply: ctx.payload.decision, message: ctx.payload.message }).pipe(Effect.catchTag("Permission.NotFoundError", () => missingRequest(ctx.params.requestID)));
45
- return HttpApiSchema.NoContent.make();
46
- })).handle("permission.saved.list", Effect.fn(function* (ctx) {
47
- const location = yield* Location.Service;
48
- return {
49
- data: yield* (yield* PermissionSaved.Service).list({
50
- projectID: ctx.query.projectID ?? location.project.id
51
- })
52
- };
53
- })).handle("permission.saved.remove", Effect.fn(function* (ctx) {
54
- yield* (yield* PermissionSaved.Service).remove(ctx.params.id);
55
- return HttpApiSchema.NoContent.make();
56
- }));
57
- }));
1
+ import {
2
+ PermissionHandler2
3
+ } from "../chunks/fetch-arj41x43.js";
4
+ import"../chunks/fetch-z5shrcz9.js";
5
+ import"../chunks/fetch-3kzx88w9.js";
6
+ import"../chunks/fetch-5rwqcaw2.js";
7
+ import"../chunks/fetch-6gkz39ey.js";
8
+ import"../chunks/fetch-smaf4a18.js";
9
+ export {
10
+ PermissionHandler2 as PermissionHandler
11
+ };
@@ -1,136 +1,13 @@
1
- import { PersistentPty } from "@opencode/core/persistent-pty";
2
- import { PtyTicket } from "@opencode/core/pty/ticket";
3
- import { ForbiddenError, PtyNotFoundError, ServiceUnavailableError } from "@opencode/protocol/errors";
4
1
  import {
5
- PTY_CONNECT_TICKET_QUERY,
6
- PTY_CONNECT_TOKEN_HEADER,
7
- PTY_CONNECT_TOKEN_HEADER_VALUE
8
- } from "@opencode/protocol/groups/persistent-pty";
9
- import { Effect, Queue, Semaphore } from "effect";
10
- import { HttpServerRequest, HttpServerResponse } from "effect/unstable/http";
11
- import { HttpApiBuilder, HttpApiSchema } from "effect/unstable/httpapi";
12
- import { Socket } from "effect/unstable/socket";
13
- import { Api } from "../api";
14
- import { CorsConfig, isAllowedRequestOrigin } from "../cors";
15
- import { runPtySocket } from "./pty-socket";
16
- export const PersistentPtyHandler = HttpApiBuilder.group(Api, "server.experimental", (handlers) => Effect.gen(function* () {
17
- const tickets = yield* PtyTicket.Service, cors = yield* CorsConfig, pty = yield* PersistentPty.Service;
18
- return handlers.handle("persistentPty.read", Effect.fn(function* (ctx) {
19
- return { data: yield* pty.read(ctx.params.sessionID, ctx.query.lines).pipe(mapUnavailable) };
20
- })).handle("persistentPty.list", Effect.fn(function* (ctx) {
21
- return { data: yield* pty.list(ctx.params.sessionID).pipe(mapUnavailable) };
22
- })).handle("persistentPty.create", Effect.fn(function* (ctx) {
23
- return {
24
- data: yield* pty.create(ctx.params.sessionID, {
25
- command: ctx.payload.command,
26
- args: ctx.payload.args,
27
- cwd: ctx.payload.cwd,
28
- title: ctx.payload.title,
29
- env: ctx.payload.env,
30
- cols: ctx.payload.size?.cols,
31
- rows: ctx.payload.size?.rows
32
- }).pipe(Effect.catchTag("PersistentPty.UnavailableError", unavailable))
33
- };
34
- })).handle("persistentPty.shutdown", Effect.fn(function* () {
35
- yield* pty.shutdown().pipe(mapUnavailable);
36
- return HttpApiSchema.NoContent.make();
37
- })).handle("persistentPty.handoff", Effect.fn(function* () {
38
- return { handoff: yield* pty.handoff().pipe(mapUnavailable) };
39
- })).handle("persistentPty.get", Effect.fn(function* (ctx) {
40
- return { data: yield* pty.get(ctx.params.ptyID).pipe(mapTerminalError) };
41
- })).handle("persistentPty.update", Effect.fn(function* (ctx) {
42
- yield* pty.resize(ctx.params.ptyID, ctx.payload.size.cols, ctx.payload.size.rows, ctx.payload.attachmentID).pipe(mapTerminalError);
43
- return { data: yield* pty.get(ctx.params.ptyID).pipe(mapTerminalError) };
44
- })).handle("persistentPty.snapshot", Effect.fn(function* (ctx) {
45
- return { data: yield* pty.snapshot(ctx.params.ptyID).pipe(mapTerminalError) };
46
- })).handle("persistentPty.remove", Effect.fn(function* (ctx) {
47
- yield* pty.remove(ctx.params.ptyID).pipe(mapTerminalError);
48
- return HttpApiSchema.NoContent.make();
49
- })).handle("persistentPty.connectToken", Effect.fn(function* (ctx) {
50
- const request = yield* HttpServerRequest.HttpServerRequest;
51
- if (request.headers[PTY_CONNECT_TOKEN_HEADER] !== PTY_CONNECT_TOKEN_HEADER_VALUE || !isAllowedRequestOrigin(request.headers.origin, request.headers.host, cors))
52
- return yield* new ForbiddenError({ message: "Invalid persistent PTY connect token request" });
53
- yield* pty.get(ctx.params.ptyID).pipe(mapTerminalError);
54
- return { data: yield* tickets.issue({ ptyID: ctx.params.ptyID }) };
55
- })).handleRaw("persistentPty.connect", Effect.fn("PersistentPtyHandler.connect")(function* (ctx) {
56
- const url = new URL(ctx.request.url, "http://localhost"), ticket = url.searchParams.get(PTY_CONNECT_TICKET_QUERY);
57
- if (ticket) {
58
- if (!(isAllowedRequestOrigin(ctx.request.headers.origin, ctx.request.headers.host, cors) ? yield* tickets.consume({ ticket, ptyID: ctx.params.ptyID }) : !1))
59
- return HttpServerResponse.empty({ status: 403 });
60
- }
61
- const cursor = Number(url.searchParams.get("cursor") ?? "0"), role = url.searchParams.get("role") === "observer" ? "observer" : "controller", framedInput = url.searchParams.get("input_protocol") === "1", attachmentID = url.searchParams.get("attachment_id") ?? crypto.randomUUID();
62
- if (!Number.isSafeInteger(cursor) || cursor < 0)
63
- return HttpServerResponse.empty({ status: 400 });
64
- const socket = yield* Effect.orDie(ctx.request.upgrade), write = yield* socket.writer, outbox = yield* Queue.unbounded(), input = yield* Semaphore.make(1);
65
- let attachment;
66
- const onOpen = Effect.gen(function* () {
67
- attachment = yield* pty.attach(ctx.params.ptyID, {
68
- cursor,
69
- attachmentID,
70
- role,
71
- takeover: url.searchParams.get("takeover") === "true",
72
- onEvent: (event) => {
73
- if (event.type === "output")
74
- Queue.offerUnsafe(outbox, event.data);
75
- if (event.type === "resized")
76
- Queue.offerUnsafe(outbox, JSON.stringify({ ...event, checkpoint: Buffer.from(event.checkpoint).toString("base64") }));
77
- if (event.type !== "output" && event.type !== "resized")
78
- Queue.offerUnsafe(outbox, JSON.stringify(event));
79
- },
80
- onEnd: () => Queue.offerUnsafe(outbox, new Socket.CloseEvent(1000))
81
- }).pipe(Effect.catchTags({
82
- "PersistentPty.NotFoundError": () => Effect.succeed(void 0),
83
- "PersistentPty.UnavailableError": () => Effect.succeed(void 0)
84
- }));
85
- if (!attachment) {
86
- Queue.offerUnsafe(outbox, new Socket.CloseEvent(4404, "terminal unavailable"));
87
- return;
88
- }
89
- Queue.offerUnsafe(outbox, JSON.stringify({
90
- type: "attached",
91
- attachmentID,
92
- inputProtocol: framedInput ? 1 : 0,
93
- info: attachment.info,
94
- role: attachment.role,
95
- generation: attachment.generation,
96
- replay: {
97
- requestedOffset: attachment.replay.requestedOffset,
98
- availableOffset: attachment.replay.availableOffset,
99
- endOffset: attachment.replay.endOffset,
100
- truncated: attachment.replay.truncated
101
- }
102
- }));
103
- if (attachment.replay.data.length > 0)
104
- Queue.offerUnsafe(outbox, attachment.replay.data);
105
- Queue.offerUnsafe(outbox, JSON.stringify({ type: "replay_complete", endOffset: attachment.replay.endOffset }));
106
- attachment.activate();
107
- }), drain = Effect.gen(function* () {
108
- while (!0) {
109
- const item = yield* Queue.take(outbox);
110
- yield* write(item);
111
- if (item instanceof Socket.CloseEvent)
112
- return;
113
- }
114
- });
115
- yield* runPtySocket(drain, socket.runRaw((message) => input.withPermit(Effect.suspend(() => {
116
- if (!attachment)
117
- return Effect.void;
118
- const data = typeof message === "string" ? Buffer.from(message) : message;
119
- if (!framedInput)
120
- return pty.input(ctx.params.ptyID, attachmentID, attachment.info.size.cols, attachment.info.size.rows, data).pipe(Effect.ignore);
121
- if (data.byteLength < 5)
122
- return Effect.void;
123
- const view = new DataView(data.buffer, data.byteOffset, data.byteLength), type = data[0], cols = view.getUint16(1), rows = view.getUint16(3);
124
- if (type !== 0 && type !== 1 || cols === 0 || rows === 0)
125
- return Effect.void;
126
- if (type === 0)
127
- return pty.control(ctx.params.ptyID, attachmentID, cols, rows).pipe(Effect.ignore);
128
- return pty.input(ctx.params.ptyID, attachmentID, cols, rows, data.subarray(5)).pipe(Effect.ignore);
129
- })), { onOpen }), () => attachment?.detach()).pipe(Effect.catchReason("SocketError", "SocketCloseError", () => Effect.void), Effect.orDie);
130
- return HttpServerResponse.empty();
131
- }));
132
- }));
133
- const mapUnavailable = (effect) => effect.pipe(Effect.catchTag("PersistentPty.UnavailableError", unavailable)), mapTerminalError = (effect) => effect.pipe(Effect.catchTags({
134
- "PersistentPty.NotFoundError": (error) => new PtyNotFoundError({ ptyID: error.ptyID, message: `PTY session not found: ${error.ptyID}` }),
135
- "PersistentPty.UnavailableError": unavailable
136
- })), unavailable = (error) => new ServiceUnavailableError({ message: error.message, service: "opencode-pty" });
2
+ PersistentPtyHandler2
3
+ } from "../chunks/fetch-n0er2m55.js";
4
+ import"../chunks/fetch-hezj1jdf.js";
5
+ import"../chunks/fetch-q4bn6dy8.js";
6
+ import"../chunks/fetch-z5shrcz9.js";
7
+ import"../chunks/fetch-3kzx88w9.js";
8
+ import"../chunks/fetch-5rwqcaw2.js";
9
+ import"../chunks/fetch-6gkz39ey.js";
10
+ import"../chunks/fetch-smaf4a18.js";
11
+ export {
12
+ PersistentPtyHandler2 as PersistentPtyHandler
13
+ };
@@ -1,47 +1,11 @@
1
- import { Plugin } from "@opencode/core/plugin";
2
- import { PluginUpdate } from "@opencode/core/plugin/update";
3
- import { InvalidRequestError, ServiceUnavailableError } from "@opencode/protocol/errors";
4
- import { Cause, Effect, Exit } from "effect";
5
- import { HttpApiBuilder } from "effect/unstable/httpapi";
6
- import { Api } from "../api";
7
- import { response } from "../location";
8
- export const PluginHandler = HttpApiBuilder.group(Api, "server.plugin", (handlers) => handlers.handle("plugin.list", () => Effect.gen(function* () {
9
- return yield* response(Plugin.Service.use((plugin) => plugin.list()));
10
- })).handle("plugin.check", (ctx) => Effect.gen(function* () {
11
- const inventory = yield* (yield* Plugin.Service).list(), targets = [
12
- ...new Set(inventory.flatMap((plugin) => plugin.source.type === "package" ? [plugin.source.target] : []))
13
- ].filter((target) => ctx.payload.target === void 0 || target === ctx.payload.target);
14
- if (ctx.payload.target !== void 0 && !targets.length)
15
- return yield* new InvalidRequestError({
16
- message: `Plugin package is not in the current server inventory: ${ctx.payload.target}`,
17
- field: "target"
18
- });
19
- const updates = yield* PluginUpdate.Service, outdated = new Map(yield* Effect.forEach(targets, (target) => updates.check(target, { refresh: !0 }).pipe(Effect.map((value) => [target, value])), { concurrency: "unbounded" }));
20
- return yield* response(Effect.succeed(inventory.map((plugin) => {
21
- if (plugin.source.type !== "package" || !outdated.has(plugin.source.target))
22
- return plugin;
23
- return {
24
- ...plugin,
25
- source: {
26
- type: "package",
27
- target: plugin.source.target,
28
- ...plugin.source.version ? { version: plugin.source.version } : {},
29
- ...outdated.get(plugin.source.target) ? { outdated: !0 } : {},
30
- ...plugin.source.updating ? { updating: !0 } : {}
31
- }
32
- };
33
- })));
34
- })).handle("plugin.update", (ctx) => Effect.gen(function* () {
35
- const plugins = yield* Plugin.Service, inventory = new Set((yield* plugins.list()).flatMap((plugin) => plugin.source.type === "package" ? [plugin.source.target] : [])), unknown = ctx.payload.targets.filter((target) => !inventory.has(target));
36
- if (unknown.length)
37
- return yield* new InvalidRequestError({
38
- message: `Plugin packages are not in the current server inventory: ${unknown.join(", ")}`,
39
- field: "targets"
40
- });
41
- const updates = yield* PluginUpdate.Service, failures = yield* Effect.forEach(ctx.payload.targets, (target) => updates.update(target).pipe(Effect.exit, Effect.map((exit) => Exit.isFailure(exit) ? [`${target}: ${Cause.pretty(exit.cause)}`] : [])), { concurrency: "unbounded" }).pipe(Effect.map((results) => results.flat()));
42
- if (failures.length)
43
- return yield* new ServiceUnavailableError({
44
- message: `Failed to update plugin packages: ${failures.join("; ")}`,
45
- service: "plugin"
46
- });
47
- })));
1
+ import {
2
+ PluginHandler2
3
+ } from "../chunks/fetch-19c9ysa1.js";
4
+ import"../chunks/fetch-z5shrcz9.js";
5
+ import"../chunks/fetch-3kzx88w9.js";
6
+ import"../chunks/fetch-5rwqcaw2.js";
7
+ import"../chunks/fetch-6gkz39ey.js";
8
+ import"../chunks/fetch-smaf4a18.js";
9
+ export {
10
+ PluginHandler2 as PluginHandler
11
+ };
@@ -1,9 +1,11 @@
1
- import { Project } from "@opencode/core/project";
2
- import { Effect } from "effect";
3
- import { HttpApiBuilder } from "effect/unstable/httpapi";
4
- import { Api } from "../api";
5
- import { ProjectNotFoundError } from "@opencode/protocol/errors";
6
- export const ProjectHandler = HttpApiBuilder.group(Api, "server.project", (handlers) => handlers.handle("project.list", () => Project.Service.use((project) => project.list())).handle("project.update", (ctx) => Project.Service.use((project) => project.update({ ...ctx.payload, projectID: ctx.params.projectID }).pipe(Effect.mapError(() => new ProjectNotFoundError({
7
- projectID: ctx.params.projectID,
8
- message: `Project not found: ${ctx.params.projectID}`
9
- }))))));
1
+ import {
2
+ ProjectHandler2
3
+ } from "../chunks/fetch-zp2jm6dt.js";
4
+ import"../chunks/fetch-z5shrcz9.js";
5
+ import"../chunks/fetch-3kzx88w9.js";
6
+ import"../chunks/fetch-5rwqcaw2.js";
7
+ import"../chunks/fetch-6gkz39ey.js";
8
+ import"../chunks/fetch-smaf4a18.js";
9
+ export {
10
+ ProjectHandler2 as ProjectHandler
11
+ };
@@ -1,20 +1,11 @@
1
- import { Provider } from "@opencode/core/provider";
2
- import { ProviderNotFoundError } from "@opencode/protocol/errors";
3
- import { Effect } from "effect";
4
- import { HttpApiBuilder } from "effect/unstable/httpapi";
5
- import { Api } from "../api";
6
- import { response } from "../location";
7
- export const ProviderHandler = HttpApiBuilder.group(Api, "server.provider", (handlers) => Effect.gen(function* () {
8
- return handlers.handle("provider.list", Effect.fn(function* () {
9
- const providers = yield* Provider.Service;
10
- return yield* response(providers.available());
11
- })).handle("provider.get", Effect.fn(function* (ctx) {
12
- const provider = yield* (yield* Provider.Service).get(ctx.params.providerID);
13
- if (!provider)
14
- return yield* new ProviderNotFoundError({
15
- providerID: ctx.params.providerID,
16
- message: `Provider not found: ${ctx.params.providerID}`
17
- });
18
- return yield* response(Effect.succeed(provider));
19
- }));
20
- }));
1
+ import {
2
+ ProviderHandler2
3
+ } from "../chunks/fetch-pnqq1zxv.js";
4
+ import"../chunks/fetch-z5shrcz9.js";
5
+ import"../chunks/fetch-3kzx88w9.js";
6
+ import"../chunks/fetch-5rwqcaw2.js";
7
+ import"../chunks/fetch-6gkz39ey.js";
8
+ import"../chunks/fetch-smaf4a18.js";
9
+ export {
10
+ ProviderHandler2 as ProviderHandler
11
+ };
@@ -1,4 +1,6 @@
1
- import { Effect } from "effect";
2
- export function runPtySocket(drain, socket, detach) {
3
- return Effect.raceFirst(drain, socket).pipe(Effect.ensuring(Effect.sync(detach)));
4
- }
1
+ import {
2
+ runPtySocket2
3
+ } from "../chunks/fetch-hezj1jdf.js";
4
+ export {
5
+ runPtySocket2 as runPtySocket
6
+ };
@@ -1,108 +1,14 @@
1
- import { Pty } from "@opencode/core/pty";
2
- import { PtyProtocol } from "@opencode/core/pty/protocol";
3
- import { PtyTicket } from "@opencode/core/pty/ticket";
4
- import { Location } from "@opencode/core/location";
5
- import { Effect, Queue } from "effect";
6
- import { HttpServerRequest, HttpServerResponse } from "effect/unstable/http";
7
- import { HttpApiBuilder, HttpApiSchema } from "effect/unstable/httpapi";
8
- import { Socket } from "effect/unstable/socket";
9
- import { Api } from "../api";
10
- import { CorsConfig, isAllowedRequestOrigin } from "../cors";
11
- import { ForbiddenError, PtyNotFoundError } from "@opencode/protocol/errors";
12
1
  import {
13
- PTY_CONNECT_TICKET_QUERY,
14
- PTY_CONNECT_TOKEN_HEADER,
15
- PTY_CONNECT_TOKEN_HEADER_VALUE
16
- } from "@opencode/protocol/groups/pty";
17
- import { response } from "../location";
18
- import { PtyEnvironment } from "../pty-environment";
19
- import { runPtySocket } from "./pty-socket";
20
- const ticketScope = Effect.gen(function* () {
21
- const location = yield* Location.Service;
22
- return { directory: location.directory, workspaceID: location.workspaceID };
23
- });
24
- export const PtyHandler = HttpApiBuilder.group(Api, "server.pty", (handlers) => Effect.gen(function* () {
25
- const tickets = yield* PtyTicket.Service, cors = yield* CorsConfig, environment = yield* PtyEnvironment.Service;
26
- return handlers.handle("pty.list", Effect.fn(function* () {
27
- const pty = yield* Pty.Service;
28
- return yield* response(pty.list());
29
- })).handle("pty.create", Effect.fn(function* (ctx) {
30
- const pty = yield* Pty.Service, location = yield* Location.Service, cwd = ctx.payload.cwd || location.directory;
31
- return yield* response(pty.create({
32
- ...ctx.payload,
33
- args: ctx.payload.args ? [...ctx.payload.args] : void 0,
34
- cwd,
35
- env: {
36
- ...ctx.payload.env,
37
- ...yield* environment.get({ directory: location.directory, cwd })
38
- }
39
- }));
40
- })).handle("pty.get", Effect.fn(function* (ctx) {
41
- const pty = yield* Pty.Service;
42
- return yield* response(pty.get(ctx.params.ptyID).pipe(Effect.catchTag("Pty.NotFoundError", () => new PtyNotFoundError({
43
- ptyID: ctx.params.ptyID,
44
- message: `PTY session not found: ${ctx.params.ptyID}`
45
- }))));
46
- })).handle("pty.update", Effect.fn(function* (ctx) {
47
- const pty = yield* Pty.Service;
48
- return yield* response(pty.update(ctx.params.ptyID, {
49
- ...ctx.payload,
50
- size: ctx.payload.size ? { ...ctx.payload.size } : void 0
51
- }).pipe(Effect.catchTag("Pty.NotFoundError", () => new PtyNotFoundError({
52
- ptyID: ctx.params.ptyID,
53
- message: `PTY session not found: ${ctx.params.ptyID}`
54
- }))));
55
- })).handle("pty.remove", Effect.fn(function* (ctx) {
56
- yield* (yield* Pty.Service).remove(ctx.params.ptyID).pipe(Effect.catchTag("Pty.NotFoundError", () => new PtyNotFoundError({
57
- ptyID: ctx.params.ptyID,
58
- message: `PTY session not found: ${ctx.params.ptyID}`
59
- })));
60
- return HttpApiSchema.NoContent.make();
61
- })).handle("pty.connectToken", Effect.fn(function* (ctx) {
62
- const request = yield* HttpServerRequest.HttpServerRequest;
63
- if (request.headers[PTY_CONNECT_TOKEN_HEADER] !== PTY_CONNECT_TOKEN_HEADER_VALUE || !isAllowedRequestOrigin(request.headers.origin, request.headers.host, cors))
64
- return yield* new ForbiddenError({ message: "Invalid PTY connect token request" });
65
- yield* (yield* Pty.Service).get(ctx.params.ptyID).pipe(Effect.catchTag("Pty.NotFoundError", () => new PtyNotFoundError({
66
- ptyID: ctx.params.ptyID,
67
- message: `PTY session not found: ${ctx.params.ptyID}`
68
- })));
69
- return yield* response(tickets.issue({ ptyID: ctx.params.ptyID, ...yield* ticketScope }));
70
- })).handleRaw("pty.connect", Effect.fn("PtyHandler.connect")(function* (ctx) {
71
- const pty = yield* Pty.Service;
72
- if (!(yield* pty.get(ctx.params.ptyID).pipe(Effect.as(!0), Effect.catchTag("Pty.NotFoundError", () => Effect.succeed(!1)))))
73
- return HttpServerResponse.empty({ status: 404 });
74
- const url = new URL(ctx.request.url, "http://localhost"), ticket = url.searchParams.get(PTY_CONNECT_TICKET_QUERY);
75
- if (ticket) {
76
- if (!(isAllowedRequestOrigin(ctx.request.headers.origin, ctx.request.headers.host, cors) ? yield* tickets.consume({ ticket, ptyID: ctx.params.ptyID, ...yield* ticketScope }) : !1))
77
- return HttpServerResponse.empty({ status: 403 });
78
- }
79
- const parsedCursor = url.searchParams.get("cursor"), cursorNumber = parsedCursor === null ? void 0 : Number(parsedCursor), cursor = cursorNumber !== void 0 && Number.isSafeInteger(cursorNumber) && cursorNumber >= -1 ? cursorNumber : void 0, socket = yield* Effect.orDie(ctx.request.upgrade), write = yield* socket.writer, closeAccepted = (event) => socket.runRaw(() => Effect.void, { onOpen: write(event).pipe(Effect.catch(() => Effect.void)) }).pipe(Effect.timeout("1 second"), Effect.catchReason("SocketError", "SocketCloseError", () => Effect.void), Effect.catch(() => Effect.void)), outbox = yield* Queue.unbounded(), attachment = yield* pty.attach(ctx.params.ptyID, {
80
- cursor,
81
- onData: (chunk) => Queue.offerUnsafe(outbox, chunk),
82
- onEnd: () => Queue.offerUnsafe(outbox, new Socket.CloseEvent(1000))
83
- }).pipe(Effect.catchTags({
84
- "Pty.NotFoundError": () => closeAccepted(new Socket.CloseEvent(4404, "session not found")).pipe(Effect.as(void 0)),
85
- "Pty.ExitedError": () => closeAccepted(new Socket.CloseEvent(4404, "session exited")).pipe(Effect.as(void 0))
86
- }));
87
- if (!attachment)
88
- return HttpServerResponse.empty();
89
- for (const chunk of PtyProtocol.chunks(attachment.replay))
90
- Queue.offerUnsafe(outbox, chunk);
91
- Queue.offerUnsafe(outbox, PtyProtocol.metaFrame(attachment.cursor));
92
- attachment.activate();
93
- const drain = Effect.gen(function* () {
94
- while (!0) {
95
- const item = yield* Queue.take(outbox);
96
- yield* write(item);
97
- if (item instanceof Socket.CloseEvent)
98
- return;
99
- }
100
- });
101
- yield* runPtySocket(drain, socket.runRaw((message) => {
102
- const decoded = PtyProtocol.decodeInput(message);
103
- if (decoded !== void 0)
104
- attachment.write(decoded);
105
- }), attachment.detach).pipe(Effect.catchReason("SocketError", "SocketCloseError", () => Effect.void), Effect.orDie);
106
- return HttpServerResponse.empty();
107
- }));
108
- }));
2
+ PtyHandler2
3
+ } from "../chunks/fetch-ychamt23.js";
4
+ import"../chunks/fetch-hezj1jdf.js";
5
+ import"../chunks/fetch-q4bn6dy8.js";
6
+ import"../chunks/fetch-0d9kah4z.js";
7
+ import"../chunks/fetch-z5shrcz9.js";
8
+ import"../chunks/fetch-3kzx88w9.js";
9
+ import"../chunks/fetch-5rwqcaw2.js";
10
+ import"../chunks/fetch-6gkz39ey.js";
11
+ import"../chunks/fetch-smaf4a18.js";
12
+ export {
13
+ PtyHandler2 as PtyHandler
14
+ };
@@ -1,5 +1,11 @@
1
- import { Reference } from "@opencode/core/reference";
2
- import { HttpApiBuilder } from "effect/unstable/httpapi";
3
- import { Api } from "../api";
4
- import { response } from "../location";
5
- export const ReferenceHandler = HttpApiBuilder.group(Api, "server.reference", (handlers) => handlers.handle("reference.list", () => response(Reference.Service.use((reference) => reference.list()))));
1
+ import {
2
+ ReferenceHandler2
3
+ } from "../chunks/fetch-ysabas57.js";
4
+ import"../chunks/fetch-z5shrcz9.js";
5
+ import"../chunks/fetch-3kzx88w9.js";
6
+ import"../chunks/fetch-5rwqcaw2.js";
7
+ import"../chunks/fetch-6gkz39ey.js";
8
+ import"../chunks/fetch-smaf4a18.js";
9
+ export {
10
+ ReferenceHandler2 as ReferenceHandler
11
+ };
@@ -1,15 +1,11 @@
1
- import { Rpc } from "@opencode/core/rpc";
2
- import { Plugin } from "@opencode/core/plugin";
3
- import { RpcError, RpcInternalError } from "@opencode/protocol/errors";
4
- import { Effect } from "effect";
5
- import { HttpApiBuilder } from "effect/unstable/httpapi";
6
- import { Api } from "../api";
7
- export const RpcHandler = HttpApiBuilder.group(Api, "server.rpc", (handlers) => handlers.handle("rpc.call", ({ params, payload }) => Effect.gen(function* () {
8
- yield* Plugin.awaitActivation;
9
- const output = yield* (yield* Rpc.Service).call(params.rpcID, params.method, payload.input);
10
- return output === void 0 ? {} : { output };
11
- }).pipe(Effect.mapError((error) => error.type === "rpc.invalid_output" || error.type === "rpc.internal" ? new RpcInternalError({ type: error.type, message: error.message }) : new RpcError({
12
- type: error.type,
13
- message: error.message,
14
- ...error.data === void 0 ? {} : { data: error.data }
15
- })), Effect.catchDefect((defect) => Effect.logError("rpc call failed", { rpc: params.rpcID, method: params.method, defect }).pipe(Effect.andThen(Effect.fail(new RpcInternalError({ type: "rpc.internal", message: "RPC call failed" }))))))));
1
+ import {
2
+ RpcHandler2
3
+ } from "../chunks/fetch-bjrwanme.js";
4
+ import"../chunks/fetch-z5shrcz9.js";
5
+ import"../chunks/fetch-3kzx88w9.js";
6
+ import"../chunks/fetch-5rwqcaw2.js";
7
+ import"../chunks/fetch-6gkz39ey.js";
8
+ import"../chunks/fetch-smaf4a18.js";
9
+ export {
10
+ RpcHandler2 as RpcHandler
11
+ };