pi-cursor-sdk 0.4.0 → 0.5.0
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/CHANGELOG.md +30 -0
- package/README.md +65 -13
- package/dist/context-window-cache.js +0 -6
- package/dist/context.js +8 -0
- package/dist/cursor-cloud-lifecycle.js +122 -98
- package/dist/cursor-durable-fs.js +97 -3
- package/dist/cursor-fallback-models.generated.js +288 -1
- package/dist/cursor-fallback-warning.js +2 -2
- package/dist/cursor-http1.js +8 -8
- package/dist/cursor-live-run-coordinator.js +9 -13
- package/dist/cursor-native-replay-routing.js +1 -1
- package/dist/cursor-native-tool-display-registration.js +46 -22
- package/dist/cursor-native-tool-display-state.js +57 -22
- package/dist/cursor-native-tool-display-tools.js +5 -6
- package/dist/cursor-pi-tool-bridge-constants.js +23 -2
- package/dist/cursor-pi-tool-bridge-run.js +7 -3
- package/dist/cursor-pi-tool-bridge-snapshot.js +1 -1
- package/dist/cursor-pi-tool-bridge.js +31 -9
- package/dist/cursor-provider-binding.js +58 -0
- package/dist/cursor-provider-errors.js +28 -7
- package/dist/cursor-provider-lazy.js +23 -11
- package/dist/cursor-provider-live-run-drain.js +15 -12
- package/dist/cursor-provider-run-finalizer.js +19 -8
- package/dist/cursor-provider-turn-coordinator.js +1 -0
- package/dist/cursor-provider-turn-display-router.js +4 -0
- package/dist/cursor-provider-turn-emit.js +1 -0
- package/dist/cursor-provider-turn-finalize.js +29 -20
- package/dist/cursor-provider-turn-prepare.js +24 -11
- package/dist/cursor-provider-turn-runner.js +37 -11
- package/dist/cursor-provider-turn-send.js +22 -9
- package/dist/cursor-provider-turn-summary.js +89 -0
- package/dist/cursor-provider.js +9 -3
- package/dist/cursor-request-provenance.js +42 -0
- package/dist/cursor-ripgrep-path.js +14 -3
- package/dist/cursor-runtime-state.js +50 -43
- package/dist/cursor-sdk-billed-usage.js +54 -75
- package/dist/cursor-sdk-event-debug-session.js +5 -6
- package/dist/cursor-sdk-event-debug.js +9 -6
- package/dist/cursor-sdk-process-error-guard.js +8 -7
- package/dist/cursor-sdk-runtime.js +13 -0
- package/dist/cursor-session-agent-cleanup.js +2 -2
- package/dist/cursor-session-agent-lifecycle.js +18 -9
- package/dist/cursor-session-agent-lineage.js +28 -12
- package/dist/cursor-session-agent-resume.js +51 -35
- package/dist/cursor-session-agent.js +9 -9
- package/dist/cursor-session-compaction-prep.js +2 -7
- package/dist/cursor-session-scope.js +71 -39
- package/dist/cursor-session-settings.js +61 -0
- package/dist/cursor-skill-tool.js +32 -49
- package/dist/cursor-state.js +72 -62
- package/dist/cursor-usage-accounting.js +13 -70
- package/dist/cursor-usage-command.js +89 -0
- package/dist/cursor-usage-ledger.js +512 -0
- package/dist/index.js +11 -19
- package/dist/model-discovery.js +11 -19
- package/docs/cursor-dogfood-checklist.md +3 -3
- package/docs/cursor-live-smoke-checklist.md +15 -15
- package/docs/cursor-model-ux-spec.md +59 -18
- package/docs/cursor-native-tool-replay.md +5 -3
- package/docs/cursor-native-tool-visual-audit.md +8 -8
- package/docs/cursor-testing-lessons.md +47 -23
- package/docs/cursor-tool-surfaces.md +1 -1
- package/docs/platform-smoke-implementation.md +10 -6
- package/docs/platform-smoke.md +35 -46
- package/package.json +6 -6
- package/scripts/cloud-runtime-smoke.mjs +4 -2
- package/scripts/local-resume-smoke.mjs +1 -1
- package/scripts/platform-smoke/card-detect.mjs +2 -8
- package/scripts/platform-smoke/targets.mjs +8 -15
- package/scripts/platform-smoke/visual-evidence.mjs +7 -2
- package/scripts/tmux-live-smoke.sh +57 -90
- package/src/context-window-cache.ts +0 -6
- package/src/context.ts +8 -0
- package/src/cursor-cloud-lifecycle.ts +124 -98
- package/src/cursor-durable-fs.ts +65 -3
- package/src/cursor-fallback-models.generated.ts +288 -1
- package/src/cursor-fallback-warning.ts +2 -2
- package/src/cursor-http1.ts +8 -8
- package/src/cursor-live-run-coordinator.ts +12 -13
- package/src/cursor-native-replay-routing.ts +2 -1
- package/src/cursor-native-tool-display-registration.ts +48 -24
- package/src/cursor-native-tool-display-state.ts +65 -21
- package/src/cursor-native-tool-display-tools.ts +7 -4
- package/src/cursor-pi-tool-bridge-constants.ts +27 -2
- package/src/cursor-pi-tool-bridge-run.ts +11 -3
- package/src/cursor-pi-tool-bridge-snapshot.ts +1 -1
- package/src/cursor-pi-tool-bridge.ts +26 -9
- package/src/cursor-provider-binding.ts +62 -0
- package/src/cursor-provider-errors.ts +27 -7
- package/src/cursor-provider-lazy.ts +21 -15
- package/src/cursor-provider-live-run-drain.ts +20 -13
- package/src/cursor-provider-run-finalizer.ts +24 -15
- package/src/cursor-provider-turn-coordinator.ts +2 -0
- package/src/cursor-provider-turn-display-router.ts +5 -0
- package/src/cursor-provider-turn-emit.ts +3 -1
- package/src/cursor-provider-turn-finalize.ts +38 -23
- package/src/cursor-provider-turn-prepare.ts +23 -14
- package/src/cursor-provider-turn-runner.ts +40 -13
- package/src/cursor-provider-turn-send.ts +23 -15
- package/src/cursor-provider-turn-summary.ts +94 -0
- package/src/cursor-provider-turn-types.ts +37 -4
- package/src/cursor-provider.ts +25 -3
- package/src/cursor-request-provenance.ts +64 -0
- package/src/cursor-ripgrep-path.ts +15 -5
- package/src/cursor-runtime-state.ts +53 -48
- package/src/cursor-sdk-billed-usage.ts +54 -102
- package/src/cursor-sdk-event-debug-session.ts +5 -5
- package/src/cursor-sdk-event-debug.ts +10 -6
- package/src/cursor-sdk-process-error-guard.ts +7 -7
- package/src/cursor-sdk-runtime.ts +14 -0
- package/src/cursor-session-agent-cleanup.ts +2 -2
- package/src/cursor-session-agent-lifecycle.ts +14 -9
- package/src/cursor-session-agent-lineage.ts +26 -12
- package/src/cursor-session-agent-resume.ts +49 -36
- package/src/cursor-session-agent.ts +13 -10
- package/src/cursor-session-compaction-prep.ts +2 -7
- package/src/cursor-session-scope.ts +87 -39
- package/src/cursor-session-settings.ts +72 -0
- package/src/cursor-skill-tool.ts +37 -61
- package/src/cursor-state.ts +74 -67
- package/src/cursor-usage-accounting.ts +17 -82
- package/src/cursor-usage-command.ts +76 -0
- package/src/cursor-usage-ledger.ts +500 -0
- package/src/index.ts +14 -23
- package/src/model-discovery.ts +14 -22
package/src/index.ts
CHANGED
|
@@ -1,21 +1,23 @@
|
|
|
1
|
-
import type { ExtensionAPI
|
|
1
|
+
import type { ExtensionAPI } from "@earendil-works/pi-coding-agent";
|
|
2
2
|
import { discoverModels, type CursorModelFallbackIssue } from "./model-discovery.js";
|
|
3
3
|
import { registerCursorRuntimeControls } from "./cursor-state.js";
|
|
4
4
|
import { registerCursorNativeToolDisplay } from "./cursor-native-tool-display-registration.js";
|
|
5
5
|
import { registerCursorPiToolBridge } from "./cursor-pi-tool-bridge.js";
|
|
6
6
|
import { registerCursorQuestionTool } from "./cursor-question-tool.js";
|
|
7
7
|
import { registerCursorSkillTool } from "./cursor-skill-tool.js";
|
|
8
|
-
import {
|
|
8
|
+
import { registerCursorProviderBinding } from "./cursor-provider-binding.js";
|
|
9
|
+
import { getCursorSessionScopeSnapshot, registerCursorSessionScope } from "./cursor-session-scope.js";
|
|
9
10
|
import { registerCursorSessionAgentLifecycle } from "./cursor-session-agent-lifecycle.js";
|
|
10
11
|
import { registerCursorSessionAgentLineage } from "./cursor-session-agent-lineage.js";
|
|
11
12
|
import { registerCursorSessionAgentResume } from "./cursor-session-agent-resume.js";
|
|
12
|
-
import {
|
|
13
|
-
import { CURSOR_API_KEY_CONFIG_VALUE, resolveCursorApiKey } from "./cursor-api-key.js";
|
|
13
|
+
import { resolveCursorApiKey } from "./cursor-api-key.js";
|
|
14
14
|
import { registerCursorFallbackIssueWarning } from "./cursor-fallback-warning.js";
|
|
15
15
|
import { registerCursorAgentsContextDedup } from "./cursor-agents-context-registration.js";
|
|
16
16
|
import { registerCursorOverflowNormalization } from "./cursor-provider-overflow.js";
|
|
17
17
|
import { registerCursorSdkSessionProcessErrorGuard } from "./cursor-sdk-process-error-guard.js";
|
|
18
18
|
import { prepareCursorSessionForCompaction } from "./cursor-session-compaction-prep.js";
|
|
19
|
+
import { registerCursorUsageLedger } from "./cursor-usage-ledger.js";
|
|
20
|
+
import { registerCursorUsageCommand } from "./cursor-usage-command.js";
|
|
19
21
|
|
|
20
22
|
type CursorExtensionApi =
|
|
21
23
|
& Pick<ExtensionAPI, "registerProvider" | "registerCommand" | "on">
|
|
@@ -31,31 +33,20 @@ type CursorExtensionApi =
|
|
|
31
33
|
& Parameters<typeof registerCursorFallbackIssueWarning>[0]
|
|
32
34
|
& Parameters<typeof registerCursorAgentsContextDedup>[0]
|
|
33
35
|
& Parameters<typeof registerCursorOverflowNormalization>[0]
|
|
34
|
-
& Parameters<typeof registerCursorSdkSessionProcessErrorGuard>[0]
|
|
35
|
-
|
|
36
|
-
function createCursorProviderConfig(models: ProviderModelConfig[]): ProviderConfig {
|
|
37
|
-
return {
|
|
38
|
-
name: "Cursor",
|
|
39
|
-
baseUrl: "https://cursor.com",
|
|
40
|
-
apiKey: CURSOR_API_KEY_CONFIG_VALUE,
|
|
41
|
-
api: "cursor-sdk",
|
|
42
|
-
models,
|
|
43
|
-
streamSimple: streamCursorLazy,
|
|
44
|
-
};
|
|
45
|
-
}
|
|
46
|
-
|
|
47
|
-
function registerCursorProvider(pi: Pick<ExtensionAPI, "registerProvider">, models: ProviderModelConfig[]): void {
|
|
48
|
-
pi.registerProvider("cursor", createCursorProviderConfig(models));
|
|
49
|
-
}
|
|
36
|
+
& Parameters<typeof registerCursorSdkSessionProcessErrorGuard>[0]
|
|
37
|
+
& Parameters<typeof registerCursorUsageLedger>[0];
|
|
50
38
|
|
|
51
39
|
export default async function (pi: CursorExtensionApi) {
|
|
52
40
|
// Session cwd must register before other session_start listeners that depend on it.
|
|
53
41
|
registerCursorSessionScope(pi);
|
|
42
|
+
registerCursorUsageLedger(pi);
|
|
43
|
+
registerCursorUsageCommand(pi);
|
|
44
|
+
const registerCursorProvider = registerCursorProviderBinding(pi);
|
|
54
45
|
registerCursorSessionAgentLineage(pi);
|
|
55
46
|
registerCursorSessionAgentLifecycle(pi);
|
|
56
47
|
registerCursorSessionAgentResume(pi);
|
|
57
48
|
pi.on("session_before_compact", async () => {
|
|
58
|
-
await prepareCursorSessionForCompaction();
|
|
49
|
+
await prepareCursorSessionForCompaction(getCursorSessionScopeSnapshot(pi).scopeKey);
|
|
59
50
|
});
|
|
60
51
|
registerCursorRuntimeControls(pi);
|
|
61
52
|
registerCursorNativeToolDisplay(pi);
|
|
@@ -87,7 +78,7 @@ export default async function (pi: CursorExtensionApi) {
|
|
|
87
78
|
refreshFallbackIssue = issue;
|
|
88
79
|
},
|
|
89
80
|
});
|
|
90
|
-
registerCursorProvider(
|
|
81
|
+
registerCursorProvider(refreshedModels);
|
|
91
82
|
if (!ctx.hasUI) return;
|
|
92
83
|
if (refreshFallbackIssue) {
|
|
93
84
|
ctx.ui.notify(`Cursor model catalog refresh did not use a live catalog: ${refreshFallbackIssue.message}`, "warning");
|
|
@@ -97,7 +88,7 @@ export default async function (pi: CursorExtensionApi) {
|
|
|
97
88
|
},
|
|
98
89
|
});
|
|
99
90
|
|
|
100
|
-
registerCursorProvider(
|
|
91
|
+
registerCursorProvider(models);
|
|
101
92
|
// Register last so session_shutdown cleanup remains protected until other Cursor handlers finish.
|
|
102
93
|
registerCursorSdkSessionProcessErrorGuard(pi);
|
|
103
94
|
}
|
package/src/model-discovery.ts
CHANGED
|
@@ -4,13 +4,13 @@ import type {
|
|
|
4
4
|
ModelParameterValue,
|
|
5
5
|
ModelSelection,
|
|
6
6
|
} from "@cursor/sdk";
|
|
7
|
-
import type { ProviderModelConfig } from "@earendil-works/pi-coding-agent";
|
|
7
|
+
import type { ProviderModelConfig as PiProviderModelConfig } from "@earendil-works/pi-coding-agent";
|
|
8
8
|
import type { ModelThinkingLevel, ThinkingLevelMap } from "@earendil-works/pi-ai";
|
|
9
9
|
import { getCursorModelSelectionIdentities } from "../shared/cursor-model-selection-identities.mjs";
|
|
10
10
|
import { loadContextWindowCache } from "./context-window-cache.js";
|
|
11
11
|
import { loadCursorSdk } from "./cursor-sdk-runtime.js";
|
|
12
12
|
import { resolveCursorApiKey, resolveCursorRuntimeApiKey } from "./cursor-api-key.js";
|
|
13
|
-
import {
|
|
13
|
+
import { sanitizeCursorProviderError } from "./cursor-provider-errors.js";
|
|
14
14
|
import {
|
|
15
15
|
fingerprintApiKey,
|
|
16
16
|
loadAnyCachedModelCatalog,
|
|
@@ -18,6 +18,8 @@ import {
|
|
|
18
18
|
saveModelListCache,
|
|
19
19
|
} from "./model-list-cache.js";
|
|
20
20
|
|
|
21
|
+
type ProviderModelConfig = Extract<PiProviderModelConfig, { reasoning: boolean }>;
|
|
22
|
+
|
|
21
23
|
const FALLBACK_CONTEXT_WINDOW = 128000;
|
|
22
24
|
const FALLBACK_MAX_TOKENS = 16384;
|
|
23
25
|
const ZERO_COST = { input: 0, output: 0, cacheRead: 0, cacheWrite: 0 };
|
|
@@ -65,6 +67,7 @@ export interface CursorModelMetadata {
|
|
|
65
67
|
reasoning: boolean;
|
|
66
68
|
effort: boolean;
|
|
67
69
|
thinking: boolean;
|
|
70
|
+
reasoning_effort: boolean;
|
|
68
71
|
fast: boolean;
|
|
69
72
|
};
|
|
70
73
|
}
|
|
@@ -114,7 +117,7 @@ function getThinkingLevelMap(item: ModelListItem): ThinkingLevelMap | undefined
|
|
|
114
117
|
const reasoningParameter = getParameter(item, "reasoning");
|
|
115
118
|
const effortParameter = getParameter(item, "effort");
|
|
116
119
|
const thinkingParameter = getParameter(item, "thinking");
|
|
117
|
-
const valueParameter = effortParameter ?? reasoningParameter ?? thinkingParameter;
|
|
120
|
+
const valueParameter = effortParameter ?? reasoningParameter ?? thinkingParameter ?? getParameter(item, "reasoning_effort");
|
|
118
121
|
if (!valueParameter) return undefined;
|
|
119
122
|
|
|
120
123
|
if (valueParameter.id === "thinking" && hasBooleanValues(valueParameter)) {
|
|
@@ -235,6 +238,7 @@ function toMetadata(
|
|
|
235
238
|
reasoning: getParameter(item, "reasoning") !== undefined,
|
|
236
239
|
effort: getParameter(item, "effort") !== undefined,
|
|
237
240
|
thinking: getParameter(item, "thinking") !== undefined,
|
|
241
|
+
reasoning_effort: getParameter(item, "reasoning_effort") !== undefined,
|
|
238
242
|
fast: getParameter(item, "fast") !== undefined,
|
|
239
243
|
},
|
|
240
244
|
};
|
|
@@ -280,15 +284,6 @@ export function getCursorModelMetadata(modelId: string): CursorModelMetadata | u
|
|
|
280
284
|
return metadataByPiModelId.get(modelId);
|
|
281
285
|
}
|
|
282
286
|
|
|
283
|
-
export function getCursorModelMetadataEntries(): CursorModelMetadata[] {
|
|
284
|
-
return [...metadataByPiModelId.values()].map((metadata) => ({
|
|
285
|
-
...metadata,
|
|
286
|
-
defaultParams: cloneParams(metadata.defaultParams),
|
|
287
|
-
...(metadata.thinkingLevelMap ? { thinkingLevelMap: { ...metadata.thinkingLevelMap } } : {}),
|
|
288
|
-
parameterIds: { ...metadata.parameterIds },
|
|
289
|
-
}));
|
|
290
|
-
}
|
|
291
|
-
|
|
292
287
|
function setParam(params: ModelParameterValue[], id: string, value: string): void {
|
|
293
288
|
const existing = params.find((param) => param.id === id);
|
|
294
289
|
if (existing) {
|
|
@@ -336,6 +331,8 @@ function applyThinkingLevel(
|
|
|
336
331
|
|
|
337
332
|
if (metadata.parameterIds.thinking) {
|
|
338
333
|
setParam(params, "thinking", mapped);
|
|
334
|
+
} else if (metadata.parameterIds.reasoning_effort) {
|
|
335
|
+
setParam(params, "reasoning_effort", mapped);
|
|
339
336
|
}
|
|
340
337
|
}
|
|
341
338
|
|
|
@@ -357,11 +354,6 @@ export function buildCursorModelSelection(
|
|
|
357
354
|
return params.length > 0 ? { id: metadata.selectionModelId, params } : { id: metadata.selectionModelId };
|
|
358
355
|
}
|
|
359
356
|
|
|
360
|
-
function sanitizeDiscoveryError(error: unknown, apiKey: string): string | undefined {
|
|
361
|
-
const message = error instanceof Error ? error.message : typeof error === "string" ? error : "";
|
|
362
|
-
return scrubSensitiveText(message, apiKey).trim() || undefined;
|
|
363
|
-
}
|
|
364
|
-
|
|
365
357
|
async function useFallbackModels(options: DiscoverModelsOptions, issue: CursorModelFallbackIssue): Promise<ProviderModelConfig[]> {
|
|
366
358
|
options.onFallback?.(issue);
|
|
367
359
|
const { FALLBACK_MODEL_ITEMS } = await import("./cursor-fallback-models.generated.js");
|
|
@@ -398,7 +390,7 @@ export async function discoverModels(options: DiscoverModelsOptions = {}): Promi
|
|
|
398
390
|
message: `Cursor model discovery returned no models. Using fallback Cursor models; verify ${AUTH_SETUP_HINT}. ${CATALOG_REFRESH_HINT}`,
|
|
399
391
|
});
|
|
400
392
|
} catch (error) {
|
|
401
|
-
const errorMessage =
|
|
393
|
+
const errorMessage = sanitizeCursorProviderError(error, apiKey);
|
|
402
394
|
// Prefer a previously cached catalog over the generic bundled fallback when
|
|
403
395
|
// a live refresh fails (e.g. transient network/auth errors), but keep the
|
|
404
396
|
// provenance visible so refresh commands do not claim a live refresh worked.
|
|
@@ -406,15 +398,15 @@ export async function discoverModels(options: DiscoverModelsOptions = {}): Promi
|
|
|
406
398
|
if (cachedCatalog && cachedCatalog.models.length > 0) {
|
|
407
399
|
options.onFallback?.({
|
|
408
400
|
reason: "cached-after-error",
|
|
409
|
-
message: `Cursor model discovery failed; using cached Cursor model catalog from ${new Date(cachedCatalog.fetchedAt).toISOString()}
|
|
410
|
-
|
|
401
|
+
message: `Cursor model discovery failed; using cached Cursor model catalog from ${new Date(cachedCatalog.fetchedAt).toISOString()}. ${errorMessage}`,
|
|
402
|
+
errorMessage,
|
|
411
403
|
});
|
|
412
404
|
return registerModelItems(cachedCatalog.models);
|
|
413
405
|
}
|
|
414
406
|
return useFallbackModels(options, {
|
|
415
407
|
reason: "discovery-failed",
|
|
416
|
-
message: `Cursor model discovery failed
|
|
417
|
-
|
|
408
|
+
message: `Cursor model discovery failed: ${errorMessage} Using fallback Cursor models; run /cursor-refresh-models to retry discovery.`,
|
|
409
|
+
errorMessage,
|
|
418
410
|
});
|
|
419
411
|
}
|
|
420
412
|
}
|