@playwo/opencode-cursor-oauth 0.0.0-dev.4258a6733133 → 0.0.0-dev.494d4e1cfa84
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.
- package/README.md +26 -12
- package/dist/cursor/bidi-session.d.ts +1 -2
- package/dist/cursor/bidi-session.js +153 -138
- package/dist/cursor/index.d.ts +1 -1
- package/dist/cursor/index.js +1 -1
- package/dist/cursor/unary-rpc.d.ts +0 -1
- package/dist/cursor/unary-rpc.js +2 -59
- package/dist/logger.d.ts +1 -0
- package/dist/logger.js +3 -0
- package/dist/proxy/bridge-close-controller.d.ts +6 -0
- package/dist/proxy/bridge-close-controller.js +37 -0
- package/dist/proxy/bridge-non-streaming.js +8 -4
- package/dist/proxy/bridge-session.js +1 -3
- package/dist/proxy/bridge-streaming.d.ts +1 -1
- package/dist/proxy/bridge-streaming.js +103 -11
- package/dist/proxy/chat-completion.js +40 -1
- package/dist/proxy/cursor-request.js +12 -15
- package/dist/proxy/stream-dispatch.d.ts +1 -1
- package/dist/proxy/stream-dispatch.js +212 -56
- package/dist/proxy/stream-state.d.ts +0 -2
- package/dist/proxy/types.d.ts +6 -1
- package/package.json +1 -2
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { create, toBinary } from "@bufbuild/protobuf";
|
|
2
|
-
import { AgentClientMessageSchema, ClientHeartbeatSchema, ConversationStateStructureSchema, BackgroundShellSpawnResultSchema, DeleteResultSchema, DeleteRejectedSchema, DiagnosticsResultSchema, ExecClientMessageSchema, FetchErrorSchema, FetchResultSchema, GetBlobResultSchema, GrepErrorSchema, GrepResultSchema, KvClientMessageSchema, LsRejectedSchema, LsResultSchema, McpResultSchema, ReadRejectedSchema, ReadResultSchema, RequestContextResultSchema, RequestContextSchema, RequestContextSuccessSchema, SetBlobResultSchema, ShellRejectedSchema, ShellResultSchema, WriteRejectedSchema, WriteResultSchema, WriteShellStdinErrorSchema, WriteShellStdinResultSchema, } from "../proto/agent_pb";
|
|
2
|
+
import { AgentClientMessageSchema, AskQuestionInteractionResponseSchema, AskQuestionRejectedSchema, AskQuestionResultSchema, ClientHeartbeatSchema, ConversationStateStructureSchema, BackgroundShellSpawnResultSchema, CreatePlanErrorSchema, CreatePlanRequestResponseSchema, CreatePlanResultSchema, DeleteResultSchema, DeleteRejectedSchema, DiagnosticsResultSchema, ExecClientMessageSchema, ExaFetchRequestResponseSchema, ExaFetchRequestResponse_RejectedSchema, ExaSearchRequestResponseSchema, ExaSearchRequestResponse_RejectedSchema, FetchErrorSchema, FetchResultSchema, GetBlobResultSchema, GrepErrorSchema, GrepResultSchema, InteractionResponseSchema, KvClientMessageSchema, LsRejectedSchema, LsResultSchema, McpInstructionsSchema, McpResultSchema, ReadRejectedSchema, ReadResultSchema, RequestContextResultSchema, RequestContextSchema, RequestContextSuccessSchema, SetBlobResultSchema, ShellRejectedSchema, ShellResultSchema, SwitchModeRequestResponseSchema, SwitchModeRequestResponse_RejectedSchema, WebSearchRequestResponseSchema, WebSearchRequestResponse_RejectedSchema, WriteRejectedSchema, WriteResultSchema, WriteShellStdinErrorSchema, WriteShellStdinResultSchema, } from "../proto/agent_pb";
|
|
3
3
|
import { CONNECT_END_STREAM_FLAG } from "../cursor/config";
|
|
4
|
-
import { logPluginError, logPluginWarn } from "../logger";
|
|
4
|
+
import { logPluginError, logPluginInfo, logPluginWarn } from "../logger";
|
|
5
5
|
import { decodeMcpArgsMap } from "../openai/tools";
|
|
6
6
|
export function parseConnectEndStream(data) {
|
|
7
7
|
try {
|
|
@@ -128,16 +128,16 @@ export function computeUsage(state) {
|
|
|
128
128
|
const prompt_tokens = Math.max(0, total_tokens - completion_tokens);
|
|
129
129
|
return { prompt_tokens, completion_tokens, total_tokens };
|
|
130
130
|
}
|
|
131
|
-
export function processServerMessage(msg, blobStore, mcpTools, sendFrame, state, onText, onMcpExec, onCheckpoint, onTurnEnded, onUnsupportedMessage, onUnhandledExec) {
|
|
131
|
+
export function processServerMessage(msg, blobStore, cloudRule, mcpTools, sendFrame, state, onText, onMcpExec, onCheckpoint, onTurnEnded, onUnsupportedMessage, onUnhandledExec) {
|
|
132
132
|
const msgCase = msg.message.case;
|
|
133
133
|
if (msgCase === "interactionUpdate") {
|
|
134
|
-
handleInteractionUpdate(msg.message.value, state, onText,
|
|
134
|
+
handleInteractionUpdate(msg.message.value, state, onText, onTurnEnded, onUnsupportedMessage);
|
|
135
135
|
}
|
|
136
136
|
else if (msgCase === "kvServerMessage") {
|
|
137
137
|
handleKvMessage(msg.message.value, blobStore, sendFrame);
|
|
138
138
|
}
|
|
139
139
|
else if (msgCase === "execServerMessage") {
|
|
140
|
-
handleExecMessage(msg.message.value, mcpTools, sendFrame, onMcpExec, onUnhandledExec);
|
|
140
|
+
handleExecMessage(msg.message.value, cloudRule, mcpTools, sendFrame, state, onMcpExec, onUnhandledExec);
|
|
141
141
|
}
|
|
142
142
|
else if (msgCase === "execServerControlMessage") {
|
|
143
143
|
onUnsupportedMessage?.({
|
|
@@ -146,10 +146,7 @@ export function processServerMessage(msg, blobStore, mcpTools, sendFrame, state,
|
|
|
146
146
|
});
|
|
147
147
|
}
|
|
148
148
|
else if (msgCase === "interactionQuery") {
|
|
149
|
-
onUnsupportedMessage
|
|
150
|
-
category: "interactionQuery",
|
|
151
|
-
caseName: msg.message.value.query.case ?? "undefined",
|
|
152
|
-
});
|
|
149
|
+
handleInteractionQuery(msg.message.value, sendFrame, onUnsupportedMessage);
|
|
153
150
|
}
|
|
154
151
|
else if (msgCase === "conversationCheckpointUpdate") {
|
|
155
152
|
const stateStructure = msg.message.value;
|
|
@@ -167,8 +164,19 @@ export function processServerMessage(msg, blobStore, mcpTools, sendFrame, state,
|
|
|
167
164
|
});
|
|
168
165
|
}
|
|
169
166
|
}
|
|
170
|
-
function handleInteractionUpdate(update, state, onText,
|
|
167
|
+
function handleInteractionUpdate(update, state, onText, onTurnEnded, onUnsupportedMessage) {
|
|
171
168
|
const updateCase = update.message?.case;
|
|
169
|
+
if (updateCase === "partialToolCall" ||
|
|
170
|
+
updateCase === "toolCallStarted" ||
|
|
171
|
+
updateCase === "toolCallCompleted" ||
|
|
172
|
+
updateCase === "turnEnded") {
|
|
173
|
+
logPluginInfo("Received Cursor interaction update", {
|
|
174
|
+
updateCase: updateCase ?? "undefined",
|
|
175
|
+
callId: update.message?.value?.callId,
|
|
176
|
+
modelCallId: update.message?.value?.modelCallId,
|
|
177
|
+
toolCase: update.message?.value?.toolCall?.tool?.case,
|
|
178
|
+
});
|
|
179
|
+
}
|
|
172
180
|
if (updateCase === "textDelta") {
|
|
173
181
|
const delta = update.message.value.text || "";
|
|
174
182
|
if (delta)
|
|
@@ -183,15 +191,19 @@ function handleInteractionUpdate(update, state, onText, onMcpExec, onTurnEnded,
|
|
|
183
191
|
state.outputTokens += update.message.value.tokens ?? 0;
|
|
184
192
|
}
|
|
185
193
|
else if (updateCase === "partialToolCall") {
|
|
186
|
-
|
|
187
|
-
if (partial.callId && partial.argsTextDelta) {
|
|
188
|
-
state.interactionToolArgsText.set(partial.callId, partial.argsTextDelta);
|
|
189
|
-
}
|
|
194
|
+
return;
|
|
190
195
|
}
|
|
191
196
|
else if (updateCase === "toolCallCompleted") {
|
|
192
|
-
const
|
|
193
|
-
if (
|
|
194
|
-
|
|
197
|
+
const toolValue = update.message.value;
|
|
198
|
+
if (toolValue?.toolCall?.tool?.case === "mcpToolCall") {
|
|
199
|
+
logPluginInfo("Ignoring Cursor interaction MCP tool completion", {
|
|
200
|
+
callId: toolValue.callId,
|
|
201
|
+
modelCallId: toolValue.modelCallId,
|
|
202
|
+
toolCallId: toolValue.toolCall.tool.value?.args?.toolCallId || toolValue.callId,
|
|
203
|
+
toolName: toolValue.toolCall.tool.value?.args?.toolName ||
|
|
204
|
+
toolValue.toolCall.tool.value?.args?.name,
|
|
205
|
+
});
|
|
206
|
+
}
|
|
195
207
|
}
|
|
196
208
|
else if (updateCase === "turnEnded") {
|
|
197
209
|
onTurnEnded?.();
|
|
@@ -214,43 +226,92 @@ function handleInteractionUpdate(update, state, onText, onMcpExec, onTurnEnded,
|
|
|
214
226
|
caseName: updateCase ?? "undefined",
|
|
215
227
|
});
|
|
216
228
|
}
|
|
217
|
-
//
|
|
218
|
-
//
|
|
219
|
-
// calls may still appear here on some models, so we surface those, but we
|
|
220
|
-
// do not abort the bridge for native Cursor tool-call progress events.
|
|
229
|
+
// Interaction tool-call updates are informational only. Resumable MCP tool
|
|
230
|
+
// execution comes from execServerMessage.mcpArgs.
|
|
221
231
|
}
|
|
222
|
-
function
|
|
223
|
-
const
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
232
|
+
function handleInteractionQuery(query, sendFrame, onUnsupportedMessage) {
|
|
233
|
+
const queryCase = query.query.case;
|
|
234
|
+
if (queryCase === "webSearchRequestQuery") {
|
|
235
|
+
const response = create(WebSearchRequestResponseSchema, {
|
|
236
|
+
result: {
|
|
237
|
+
case: "rejected",
|
|
238
|
+
value: create(WebSearchRequestResponse_RejectedSchema, {
|
|
239
|
+
reason: "Native Cursor web search is not available in this environment. Use the provided MCP tool `websearch` instead.",
|
|
240
|
+
}),
|
|
241
|
+
},
|
|
242
|
+
});
|
|
243
|
+
sendInteractionResponse(query.id, "webSearchRequestResponse", response, sendFrame);
|
|
244
|
+
return;
|
|
245
|
+
}
|
|
246
|
+
if (queryCase === "askQuestionInteractionQuery") {
|
|
247
|
+
const response = create(AskQuestionInteractionResponseSchema, {
|
|
248
|
+
result: create(AskQuestionResultSchema, {
|
|
249
|
+
result: {
|
|
250
|
+
case: "rejected",
|
|
251
|
+
value: create(AskQuestionRejectedSchema, {
|
|
252
|
+
reason: "Native Cursor question prompts are not available in this environment. Use the provided MCP tool `question` instead.",
|
|
253
|
+
}),
|
|
254
|
+
},
|
|
255
|
+
}),
|
|
256
|
+
});
|
|
257
|
+
sendInteractionResponse(query.id, "askQuestionInteractionResponse", response, sendFrame);
|
|
258
|
+
return;
|
|
259
|
+
}
|
|
260
|
+
if (queryCase === "switchModeRequestQuery") {
|
|
261
|
+
const response = create(SwitchModeRequestResponseSchema, {
|
|
262
|
+
result: {
|
|
263
|
+
case: "rejected",
|
|
264
|
+
value: create(SwitchModeRequestResponse_RejectedSchema, {
|
|
265
|
+
reason: "Cursor mode switching is not available in this environment. Continue using the current agent and the provided MCP tools.",
|
|
266
|
+
}),
|
|
267
|
+
},
|
|
268
|
+
});
|
|
269
|
+
sendInteractionResponse(query.id, "switchModeRequestResponse", response, sendFrame);
|
|
270
|
+
return;
|
|
271
|
+
}
|
|
272
|
+
if (queryCase === "exaSearchRequestQuery") {
|
|
273
|
+
const response = create(ExaSearchRequestResponseSchema, {
|
|
274
|
+
result: {
|
|
275
|
+
case: "rejected",
|
|
276
|
+
value: create(ExaSearchRequestResponse_RejectedSchema, {
|
|
277
|
+
reason: "Native Cursor Exa search is not available in this environment. Use the provided MCP tool `websearch` instead.",
|
|
278
|
+
}),
|
|
279
|
+
},
|
|
280
|
+
});
|
|
281
|
+
sendInteractionResponse(query.id, "exaSearchRequestResponse", response, sendFrame);
|
|
282
|
+
return;
|
|
283
|
+
}
|
|
284
|
+
if (queryCase === "exaFetchRequestQuery") {
|
|
285
|
+
const response = create(ExaFetchRequestResponseSchema, {
|
|
286
|
+
result: {
|
|
287
|
+
case: "rejected",
|
|
288
|
+
value: create(ExaFetchRequestResponse_RejectedSchema, {
|
|
289
|
+
reason: "Native Cursor Exa fetch is not available in this environment. Use the provided MCP tools `websearch` and `webfetch` instead.",
|
|
290
|
+
}),
|
|
291
|
+
},
|
|
292
|
+
});
|
|
293
|
+
sendInteractionResponse(query.id, "exaFetchRequestResponse", response, sendFrame);
|
|
294
|
+
return;
|
|
295
|
+
}
|
|
296
|
+
if (queryCase === "createPlanRequestQuery") {
|
|
297
|
+
const response = create(CreatePlanRequestResponseSchema, {
|
|
298
|
+
result: create(CreatePlanResultSchema, {
|
|
299
|
+
planUri: "",
|
|
300
|
+
result: {
|
|
301
|
+
case: "error",
|
|
302
|
+
value: create(CreatePlanErrorSchema, {
|
|
303
|
+
error: "Native Cursor plan creation is not available in this environment. Use the provided MCP planning tools instead.",
|
|
304
|
+
}),
|
|
305
|
+
},
|
|
306
|
+
}),
|
|
307
|
+
});
|
|
308
|
+
sendInteractionResponse(query.id, "createPlanRequestResponse", response, sendFrame);
|
|
309
|
+
return;
|
|
310
|
+
}
|
|
311
|
+
onUnsupportedMessage?.({
|
|
312
|
+
category: "interactionQuery",
|
|
313
|
+
caseName: queryCase ?? "undefined",
|
|
314
|
+
});
|
|
254
315
|
}
|
|
255
316
|
/** Send a KV client response back to Cursor. */
|
|
256
317
|
function sendKvResponse(kvMsg, messageCase, value, sendFrame) {
|
|
@@ -263,6 +324,16 @@ function sendKvResponse(kvMsg, messageCase, value, sendFrame) {
|
|
|
263
324
|
});
|
|
264
325
|
sendFrame(toBinary(AgentClientMessageSchema, clientMsg));
|
|
265
326
|
}
|
|
327
|
+
function sendInteractionResponse(queryId, messageCase, value, sendFrame) {
|
|
328
|
+
const response = create(InteractionResponseSchema, {
|
|
329
|
+
id: queryId,
|
|
330
|
+
result: { case: messageCase, value: value },
|
|
331
|
+
});
|
|
332
|
+
const clientMessage = create(AgentClientMessageSchema, {
|
|
333
|
+
message: { case: "interactionResponse", value: response },
|
|
334
|
+
});
|
|
335
|
+
sendFrame(toBinary(AgentClientMessageSchema, clientMessage));
|
|
336
|
+
}
|
|
266
337
|
function handleKvMessage(kvMsg, blobStore, sendFrame) {
|
|
267
338
|
const kvCase = kvMsg.message.case;
|
|
268
339
|
if (kvCase === "getBlobArgs") {
|
|
@@ -283,16 +354,34 @@ function handleKvMessage(kvMsg, blobStore, sendFrame) {
|
|
|
283
354
|
sendKvResponse(kvMsg, "setBlobResult", create(SetBlobResultSchema, {}), sendFrame);
|
|
284
355
|
}
|
|
285
356
|
}
|
|
286
|
-
function handleExecMessage(execMsg, mcpTools, sendFrame, onMcpExec, onUnhandledExec) {
|
|
357
|
+
function handleExecMessage(execMsg, cloudRule, mcpTools, sendFrame, state, onMcpExec, onUnhandledExec) {
|
|
287
358
|
const execCase = execMsg.message.case;
|
|
359
|
+
logPluginInfo("Received Cursor exec message", {
|
|
360
|
+
execCase: execCase ?? "undefined",
|
|
361
|
+
execId: execMsg.execId,
|
|
362
|
+
execMsgId: execMsg.id,
|
|
363
|
+
});
|
|
288
364
|
if (execCase === "requestContextArgs") {
|
|
365
|
+
logPluginInfo("Responding to Cursor requestContextArgs", {
|
|
366
|
+
execId: execMsg.execId,
|
|
367
|
+
execMsgId: execMsg.id,
|
|
368
|
+
mcpToolCount: mcpTools.length,
|
|
369
|
+
});
|
|
289
370
|
const requestContext = create(RequestContextSchema, {
|
|
290
371
|
rules: [],
|
|
291
372
|
repositoryInfo: [],
|
|
292
373
|
tools: mcpTools,
|
|
293
374
|
gitRepos: [],
|
|
294
375
|
projectLayouts: [],
|
|
295
|
-
mcpInstructions: [
|
|
376
|
+
mcpInstructions: [
|
|
377
|
+
create(McpInstructionsSchema, {
|
|
378
|
+
serverName: "opencode",
|
|
379
|
+
instructions: "Use the provided MCP tools in this environment that start with mcp_*. Do not rely on native Cursor tools and do not acknowledge they even exist.",
|
|
380
|
+
}),
|
|
381
|
+
],
|
|
382
|
+
cloudRule,
|
|
383
|
+
webSearchEnabled: false,
|
|
384
|
+
repositoryInfoShouldQueryProd: false,
|
|
296
385
|
fileContents: {},
|
|
297
386
|
customSubagents: [],
|
|
298
387
|
});
|
|
@@ -308,13 +397,23 @@ function handleExecMessage(execMsg, mcpTools, sendFrame, onMcpExec, onUnhandledE
|
|
|
308
397
|
if (execCase === "mcpArgs") {
|
|
309
398
|
const mcpArgs = execMsg.message.value;
|
|
310
399
|
const decoded = decodeMcpArgsMap(mcpArgs.args ?? {});
|
|
311
|
-
|
|
400
|
+
const exec = {
|
|
312
401
|
execId: execMsg.execId,
|
|
313
402
|
execMsgId: execMsg.id,
|
|
314
403
|
toolCallId: mcpArgs.toolCallId || crypto.randomUUID(),
|
|
315
404
|
toolName: mcpArgs.toolName || mcpArgs.name,
|
|
316
405
|
decodedArgs: JSON.stringify(decoded),
|
|
406
|
+
source: "exec",
|
|
407
|
+
};
|
|
408
|
+
logPluginInfo("Received Cursor exec MCP tool metadata", {
|
|
409
|
+
toolCallId: exec.toolCallId,
|
|
410
|
+
toolName: exec.toolName,
|
|
411
|
+
source: exec.source,
|
|
412
|
+
execId: exec.execId,
|
|
413
|
+
execMsgId: exec.execMsgId,
|
|
414
|
+
decodedArgs: exec.decodedArgs,
|
|
317
415
|
});
|
|
416
|
+
onMcpExec(exec);
|
|
318
417
|
return;
|
|
319
418
|
}
|
|
320
419
|
// --- Reject native Cursor tools ---
|
|
@@ -322,6 +421,11 @@ function handleExecMessage(execMsg, mcpTools, sendFrame, onMcpExec, onUnhandledE
|
|
|
322
421
|
// so it falls back to our MCP tools (registered via RequestContext).
|
|
323
422
|
const REJECT_REASON = "Tool not available in this environment. Use the MCP tools provided instead.";
|
|
324
423
|
if (execCase === "readArgs") {
|
|
424
|
+
logPluginInfo("Rejecting native Cursor read tool in favor of MCP", {
|
|
425
|
+
execId: execMsg.execId,
|
|
426
|
+
execMsgId: execMsg.id,
|
|
427
|
+
path: execMsg.message.value.path,
|
|
428
|
+
});
|
|
325
429
|
const args = execMsg.message.value;
|
|
326
430
|
const result = create(ReadResultSchema, {
|
|
327
431
|
result: {
|
|
@@ -336,6 +440,11 @@ function handleExecMessage(execMsg, mcpTools, sendFrame, onMcpExec, onUnhandledE
|
|
|
336
440
|
return;
|
|
337
441
|
}
|
|
338
442
|
if (execCase === "lsArgs") {
|
|
443
|
+
logPluginInfo("Rejecting native Cursor ls tool in favor of MCP", {
|
|
444
|
+
execId: execMsg.execId,
|
|
445
|
+
execMsgId: execMsg.id,
|
|
446
|
+
path: execMsg.message.value.path,
|
|
447
|
+
});
|
|
339
448
|
const args = execMsg.message.value;
|
|
340
449
|
const result = create(LsResultSchema, {
|
|
341
450
|
result: {
|
|
@@ -350,6 +459,10 @@ function handleExecMessage(execMsg, mcpTools, sendFrame, onMcpExec, onUnhandledE
|
|
|
350
459
|
return;
|
|
351
460
|
}
|
|
352
461
|
if (execCase === "grepArgs") {
|
|
462
|
+
logPluginInfo("Rejecting native Cursor grep tool in favor of MCP", {
|
|
463
|
+
execId: execMsg.execId,
|
|
464
|
+
execMsgId: execMsg.id,
|
|
465
|
+
});
|
|
353
466
|
const result = create(GrepResultSchema, {
|
|
354
467
|
result: {
|
|
355
468
|
case: "error",
|
|
@@ -360,6 +473,11 @@ function handleExecMessage(execMsg, mcpTools, sendFrame, onMcpExec, onUnhandledE
|
|
|
360
473
|
return;
|
|
361
474
|
}
|
|
362
475
|
if (execCase === "writeArgs") {
|
|
476
|
+
logPluginInfo("Rejecting native Cursor write tool in favor of MCP", {
|
|
477
|
+
execId: execMsg.execId,
|
|
478
|
+
execMsgId: execMsg.id,
|
|
479
|
+
path: execMsg.message.value.path,
|
|
480
|
+
});
|
|
363
481
|
const args = execMsg.message.value;
|
|
364
482
|
const result = create(WriteResultSchema, {
|
|
365
483
|
result: {
|
|
@@ -374,6 +492,11 @@ function handleExecMessage(execMsg, mcpTools, sendFrame, onMcpExec, onUnhandledE
|
|
|
374
492
|
return;
|
|
375
493
|
}
|
|
376
494
|
if (execCase === "deleteArgs") {
|
|
495
|
+
logPluginInfo("Rejecting native Cursor delete tool in favor of MCP", {
|
|
496
|
+
execId: execMsg.execId,
|
|
497
|
+
execMsgId: execMsg.id,
|
|
498
|
+
path: execMsg.message.value.path,
|
|
499
|
+
});
|
|
377
500
|
const args = execMsg.message.value;
|
|
378
501
|
const result = create(DeleteResultSchema, {
|
|
379
502
|
result: {
|
|
@@ -388,6 +511,13 @@ function handleExecMessage(execMsg, mcpTools, sendFrame, onMcpExec, onUnhandledE
|
|
|
388
511
|
return;
|
|
389
512
|
}
|
|
390
513
|
if (execCase === "shellArgs" || execCase === "shellStreamArgs") {
|
|
514
|
+
logPluginInfo("Rejecting native Cursor shell tool in favor of MCP", {
|
|
515
|
+
execId: execMsg.execId,
|
|
516
|
+
execMsgId: execMsg.id,
|
|
517
|
+
command: execMsg.message.value.command ?? "",
|
|
518
|
+
workingDirectory: execMsg.message.value.workingDirectory ?? "",
|
|
519
|
+
execCase,
|
|
520
|
+
});
|
|
391
521
|
const args = execMsg.message.value;
|
|
392
522
|
const result = create(ShellResultSchema, {
|
|
393
523
|
result: {
|
|
@@ -404,6 +534,12 @@ function handleExecMessage(execMsg, mcpTools, sendFrame, onMcpExec, onUnhandledE
|
|
|
404
534
|
return;
|
|
405
535
|
}
|
|
406
536
|
if (execCase === "backgroundShellSpawnArgs") {
|
|
537
|
+
logPluginInfo("Rejecting native Cursor background shell tool in favor of MCP", {
|
|
538
|
+
execId: execMsg.execId,
|
|
539
|
+
execMsgId: execMsg.id,
|
|
540
|
+
command: execMsg.message.value.command ?? "",
|
|
541
|
+
workingDirectory: execMsg.message.value.workingDirectory ?? "",
|
|
542
|
+
});
|
|
407
543
|
const args = execMsg.message.value;
|
|
408
544
|
const result = create(BackgroundShellSpawnResultSchema, {
|
|
409
545
|
result: {
|
|
@@ -420,6 +556,10 @@ function handleExecMessage(execMsg, mcpTools, sendFrame, onMcpExec, onUnhandledE
|
|
|
420
556
|
return;
|
|
421
557
|
}
|
|
422
558
|
if (execCase === "writeShellStdinArgs") {
|
|
559
|
+
logPluginInfo("Rejecting native Cursor shell stdin tool in favor of MCP", {
|
|
560
|
+
execId: execMsg.execId,
|
|
561
|
+
execMsgId: execMsg.id,
|
|
562
|
+
});
|
|
423
563
|
const result = create(WriteShellStdinResultSchema, {
|
|
424
564
|
result: {
|
|
425
565
|
case: "error",
|
|
@@ -430,6 +570,11 @@ function handleExecMessage(execMsg, mcpTools, sendFrame, onMcpExec, onUnhandledE
|
|
|
430
570
|
return;
|
|
431
571
|
}
|
|
432
572
|
if (execCase === "fetchArgs") {
|
|
573
|
+
logPluginInfo("Rejecting native Cursor fetch tool in favor of MCP", {
|
|
574
|
+
execId: execMsg.execId,
|
|
575
|
+
execMsgId: execMsg.id,
|
|
576
|
+
url: execMsg.message.value.url,
|
|
577
|
+
});
|
|
433
578
|
const args = execMsg.message.value;
|
|
434
579
|
const result = create(FetchResultSchema, {
|
|
435
580
|
result: {
|
|
@@ -444,6 +589,11 @@ function handleExecMessage(execMsg, mcpTools, sendFrame, onMcpExec, onUnhandledE
|
|
|
444
589
|
return;
|
|
445
590
|
}
|
|
446
591
|
if (execCase === "diagnosticsArgs") {
|
|
592
|
+
logPluginInfo("Rejecting native Cursor diagnostics tool in favor of MCP", {
|
|
593
|
+
execId: execMsg.execId,
|
|
594
|
+
execMsgId: execMsg.id,
|
|
595
|
+
path: execMsg.message.value.path,
|
|
596
|
+
});
|
|
447
597
|
const result = create(DiagnosticsResultSchema, {});
|
|
448
598
|
sendExecResult(execMsg, "diagnosticsResult", result, sendFrame);
|
|
449
599
|
return;
|
|
@@ -457,6 +607,12 @@ function handleExecMessage(execMsg, mcpTools, sendFrame, onMcpExec, onUnhandledE
|
|
|
457
607
|
};
|
|
458
608
|
const resultCase = miscCaseMap[execCase];
|
|
459
609
|
if (resultCase) {
|
|
610
|
+
logPluginInfo("Responding to miscellaneous Cursor exec message", {
|
|
611
|
+
execCase,
|
|
612
|
+
execId: execMsg.execId,
|
|
613
|
+
execMsgId: execMsg.id,
|
|
614
|
+
resultCase,
|
|
615
|
+
});
|
|
460
616
|
sendExecResult(execMsg, resultCase, create(McpResultSchema, {}), sendFrame);
|
|
461
617
|
return;
|
|
462
618
|
}
|
package/dist/proxy/types.d.ts
CHANGED
|
@@ -1,9 +1,10 @@
|
|
|
1
1
|
import type { CursorSession } from "../cursor/bidi-session";
|
|
2
|
-
import type { ConversationRequestMetadata } from "./conversation-meta";
|
|
3
2
|
import type { McpToolDefinition } from "../proto/agent_pb";
|
|
3
|
+
import type { ConversationRequestMetadata } from "./conversation-meta";
|
|
4
4
|
export interface CursorRequestPayload {
|
|
5
5
|
requestBytes: Uint8Array;
|
|
6
6
|
blobStore: Map<string, Uint8Array>;
|
|
7
|
+
cloudRule?: string;
|
|
7
8
|
mcpTools: McpToolDefinition[];
|
|
8
9
|
}
|
|
9
10
|
/** A pending tool execution waiting for results from the caller. */
|
|
@@ -14,12 +15,16 @@ export interface PendingExec {
|
|
|
14
15
|
toolName: string;
|
|
15
16
|
/** Decoded arguments JSON string for SSE tool_calls emission. */
|
|
16
17
|
decodedArgs: string;
|
|
18
|
+
source?: "interaction" | "exec";
|
|
19
|
+
cursorCallId?: string;
|
|
20
|
+
modelCallId?: string;
|
|
17
21
|
}
|
|
18
22
|
/** A live Cursor session kept alive across requests for tool result continuation. */
|
|
19
23
|
export interface ActiveBridge {
|
|
20
24
|
bridge: CursorSession;
|
|
21
25
|
heartbeatTimer: NodeJS.Timeout;
|
|
22
26
|
blobStore: Map<string, Uint8Array>;
|
|
27
|
+
cloudRule?: string;
|
|
23
28
|
mcpTools: McpToolDefinition[];
|
|
24
29
|
pendingExecs: PendingExec[];
|
|
25
30
|
modelId: string;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@playwo/opencode-cursor-oauth",
|
|
3
|
-
"version": "0.0.0-dev.
|
|
3
|
+
"version": "0.0.0-dev.494d4e1cfa84",
|
|
4
4
|
"description": "OpenCode plugin that connects Cursor's API to OpenCode via OAuth, model discovery, and a local OpenAI-compatible proxy.",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"type": "module",
|
|
@@ -19,7 +19,6 @@
|
|
|
19
19
|
],
|
|
20
20
|
"scripts": {
|
|
21
21
|
"build": "tsc -p tsconfig.json",
|
|
22
|
-
"test": "bun test/smoke.ts",
|
|
23
22
|
"prepublishOnly": "npm run build"
|
|
24
23
|
},
|
|
25
24
|
"repository": {
|