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/dist/index.js
CHANGED
|
@@ -4,38 +4,30 @@ import { registerCursorNativeToolDisplay } from "./cursor-native-tool-display-re
|
|
|
4
4
|
import { registerCursorPiToolBridge } from "./cursor-pi-tool-bridge.js";
|
|
5
5
|
import { registerCursorQuestionTool } from "./cursor-question-tool.js";
|
|
6
6
|
import { registerCursorSkillTool } from "./cursor-skill-tool.js";
|
|
7
|
-
import {
|
|
7
|
+
import { registerCursorProviderBinding } from "./cursor-provider-binding.js";
|
|
8
|
+
import { getCursorSessionScopeSnapshot, registerCursorSessionScope } from "./cursor-session-scope.js";
|
|
8
9
|
import { registerCursorSessionAgentLifecycle } from "./cursor-session-agent-lifecycle.js";
|
|
9
10
|
import { registerCursorSessionAgentLineage } from "./cursor-session-agent-lineage.js";
|
|
10
11
|
import { registerCursorSessionAgentResume } from "./cursor-session-agent-resume.js";
|
|
11
|
-
import {
|
|
12
|
-
import { CURSOR_API_KEY_CONFIG_VALUE, resolveCursorApiKey } from "./cursor-api-key.js";
|
|
12
|
+
import { resolveCursorApiKey } from "./cursor-api-key.js";
|
|
13
13
|
import { registerCursorFallbackIssueWarning } from "./cursor-fallback-warning.js";
|
|
14
14
|
import { registerCursorAgentsContextDedup } from "./cursor-agents-context-registration.js";
|
|
15
15
|
import { registerCursorOverflowNormalization } from "./cursor-provider-overflow.js";
|
|
16
16
|
import { registerCursorSdkSessionProcessErrorGuard } from "./cursor-sdk-process-error-guard.js";
|
|
17
17
|
import { prepareCursorSessionForCompaction } from "./cursor-session-compaction-prep.js";
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
name: "Cursor",
|
|
21
|
-
baseUrl: "https://cursor.com",
|
|
22
|
-
apiKey: CURSOR_API_KEY_CONFIG_VALUE,
|
|
23
|
-
api: "cursor-sdk",
|
|
24
|
-
models,
|
|
25
|
-
streamSimple: streamCursorLazy,
|
|
26
|
-
};
|
|
27
|
-
}
|
|
28
|
-
function registerCursorProvider(pi, models) {
|
|
29
|
-
pi.registerProvider("cursor", createCursorProviderConfig(models));
|
|
30
|
-
}
|
|
18
|
+
import { registerCursorUsageLedger } from "./cursor-usage-ledger.js";
|
|
19
|
+
import { registerCursorUsageCommand } from "./cursor-usage-command.js";
|
|
31
20
|
export default async function (pi) {
|
|
32
21
|
// Session cwd must register before other session_start listeners that depend on it.
|
|
33
22
|
registerCursorSessionScope(pi);
|
|
23
|
+
registerCursorUsageLedger(pi);
|
|
24
|
+
registerCursorUsageCommand(pi);
|
|
25
|
+
const registerCursorProvider = registerCursorProviderBinding(pi);
|
|
34
26
|
registerCursorSessionAgentLineage(pi);
|
|
35
27
|
registerCursorSessionAgentLifecycle(pi);
|
|
36
28
|
registerCursorSessionAgentResume(pi);
|
|
37
29
|
pi.on("session_before_compact", async () => {
|
|
38
|
-
await prepareCursorSessionForCompaction();
|
|
30
|
+
await prepareCursorSessionForCompaction(getCursorSessionScopeSnapshot(pi).scopeKey);
|
|
39
31
|
});
|
|
40
32
|
registerCursorRuntimeControls(pi);
|
|
41
33
|
registerCursorNativeToolDisplay(pi);
|
|
@@ -65,7 +57,7 @@ export default async function (pi) {
|
|
|
65
57
|
refreshFallbackIssue = issue;
|
|
66
58
|
},
|
|
67
59
|
});
|
|
68
|
-
registerCursorProvider(
|
|
60
|
+
registerCursorProvider(refreshedModels);
|
|
69
61
|
if (!ctx.hasUI)
|
|
70
62
|
return;
|
|
71
63
|
if (refreshFallbackIssue) {
|
|
@@ -76,7 +68,7 @@ export default async function (pi) {
|
|
|
76
68
|
}
|
|
77
69
|
},
|
|
78
70
|
});
|
|
79
|
-
registerCursorProvider(
|
|
71
|
+
registerCursorProvider(models);
|
|
80
72
|
// Register last so session_shutdown cleanup remains protected until other Cursor handlers finish.
|
|
81
73
|
registerCursorSdkSessionProcessErrorGuard(pi);
|
|
82
74
|
}
|
package/dist/model-discovery.js
CHANGED
|
@@ -2,7 +2,7 @@ import { getCursorModelSelectionIdentities } from "../shared/cursor-model-select
|
|
|
2
2
|
import { loadContextWindowCache } from "./context-window-cache.js";
|
|
3
3
|
import { loadCursorSdk } from "./cursor-sdk-runtime.js";
|
|
4
4
|
import { resolveCursorApiKey, resolveCursorRuntimeApiKey } from "./cursor-api-key.js";
|
|
5
|
-
import {
|
|
5
|
+
import { sanitizeCursorProviderError } from "./cursor-provider-errors.js";
|
|
6
6
|
import { fingerprintApiKey, loadAnyCachedModelCatalog, loadFreshCachedModels, saveModelListCache, } from "./model-list-cache.js";
|
|
7
7
|
const FALLBACK_CONTEXT_WINDOW = 128000;
|
|
8
8
|
const FALLBACK_MAX_TOKENS = 16384;
|
|
@@ -46,7 +46,7 @@ function getThinkingLevelMap(item) {
|
|
|
46
46
|
const reasoningParameter = getParameter(item, "reasoning");
|
|
47
47
|
const effortParameter = getParameter(item, "effort");
|
|
48
48
|
const thinkingParameter = getParameter(item, "thinking");
|
|
49
|
-
const valueParameter = effortParameter ?? reasoningParameter ?? thinkingParameter;
|
|
49
|
+
const valueParameter = effortParameter ?? reasoningParameter ?? thinkingParameter ?? getParameter(item, "reasoning_effort");
|
|
50
50
|
if (!valueParameter)
|
|
51
51
|
return undefined;
|
|
52
52
|
if (valueParameter.id === "thinking" && hasBooleanValues(valueParameter)) {
|
|
@@ -147,6 +147,7 @@ function toMetadata(item, piModelId, selectionModelId, defaultParams, context, c
|
|
|
147
147
|
reasoning: getParameter(item, "reasoning") !== undefined,
|
|
148
148
|
effort: getParameter(item, "effort") !== undefined,
|
|
149
149
|
thinking: getParameter(item, "thinking") !== undefined,
|
|
150
|
+
reasoning_effort: getParameter(item, "reasoning_effort") !== undefined,
|
|
150
151
|
fast: getParameter(item, "fast") !== undefined,
|
|
151
152
|
},
|
|
152
153
|
};
|
|
@@ -179,14 +180,6 @@ function registerModelItems(items) {
|
|
|
179
180
|
export function getCursorModelMetadata(modelId) {
|
|
180
181
|
return metadataByPiModelId.get(modelId);
|
|
181
182
|
}
|
|
182
|
-
export function getCursorModelMetadataEntries() {
|
|
183
|
-
return [...metadataByPiModelId.values()].map((metadata) => ({
|
|
184
|
-
...metadata,
|
|
185
|
-
defaultParams: cloneParams(metadata.defaultParams),
|
|
186
|
-
...(metadata.thinkingLevelMap ? { thinkingLevelMap: { ...metadata.thinkingLevelMap } } : {}),
|
|
187
|
-
parameterIds: { ...metadata.parameterIds },
|
|
188
|
-
}));
|
|
189
|
-
}
|
|
190
183
|
function setParam(params, id, value) {
|
|
191
184
|
const existing = params.find((param) => param.id === id);
|
|
192
185
|
if (existing) {
|
|
@@ -229,6 +222,9 @@ function applyThinkingLevel(metadata, params, level) {
|
|
|
229
222
|
if (metadata.parameterIds.thinking) {
|
|
230
223
|
setParam(params, "thinking", mapped);
|
|
231
224
|
}
|
|
225
|
+
else if (metadata.parameterIds.reasoning_effort) {
|
|
226
|
+
setParam(params, "reasoning_effort", mapped);
|
|
227
|
+
}
|
|
232
228
|
}
|
|
233
229
|
export function buildCursorModelSelection(modelId, thinkingLevel, fastEnabled) {
|
|
234
230
|
const metadata = getCursorModelMetadata(modelId);
|
|
@@ -241,10 +237,6 @@ export function buildCursorModelSelection(modelId, thinkingLevel, fastEnabled) {
|
|
|
241
237
|
}
|
|
242
238
|
return params.length > 0 ? { id: metadata.selectionModelId, params } : { id: metadata.selectionModelId };
|
|
243
239
|
}
|
|
244
|
-
function sanitizeDiscoveryError(error, apiKey) {
|
|
245
|
-
const message = error instanceof Error ? error.message : typeof error === "string" ? error : "";
|
|
246
|
-
return scrubSensitiveText(message, apiKey).trim() || undefined;
|
|
247
|
-
}
|
|
248
240
|
async function useFallbackModels(options, issue) {
|
|
249
241
|
options.onFallback?.(issue);
|
|
250
242
|
const { FALLBACK_MODEL_ITEMS } = await import("./cursor-fallback-models.generated.js");
|
|
@@ -278,7 +270,7 @@ export async function discoverModels(options = {}) {
|
|
|
278
270
|
});
|
|
279
271
|
}
|
|
280
272
|
catch (error) {
|
|
281
|
-
const errorMessage =
|
|
273
|
+
const errorMessage = sanitizeCursorProviderError(error, apiKey);
|
|
282
274
|
// Prefer a previously cached catalog over the generic bundled fallback when
|
|
283
275
|
// a live refresh fails (e.g. transient network/auth errors), but keep the
|
|
284
276
|
// provenance visible so refresh commands do not claim a live refresh worked.
|
|
@@ -286,15 +278,15 @@ export async function discoverModels(options = {}) {
|
|
|
286
278
|
if (cachedCatalog && cachedCatalog.models.length > 0) {
|
|
287
279
|
options.onFallback?.({
|
|
288
280
|
reason: "cached-after-error",
|
|
289
|
-
message: `Cursor model discovery failed; using cached Cursor model catalog from ${new Date(cachedCatalog.fetchedAt).toISOString()}
|
|
290
|
-
|
|
281
|
+
message: `Cursor model discovery failed; using cached Cursor model catalog from ${new Date(cachedCatalog.fetchedAt).toISOString()}. ${errorMessage}`,
|
|
282
|
+
errorMessage,
|
|
291
283
|
});
|
|
292
284
|
return registerModelItems(cachedCatalog.models);
|
|
293
285
|
}
|
|
294
286
|
return useFallbackModels(options, {
|
|
295
287
|
reason: "discovery-failed",
|
|
296
|
-
message: `Cursor model discovery failed
|
|
297
|
-
|
|
288
|
+
message: `Cursor model discovery failed: ${errorMessage} Using fallback Cursor models; run /cursor-refresh-models to retry discovery.`,
|
|
289
|
+
errorMessage,
|
|
298
290
|
});
|
|
299
291
|
}
|
|
300
292
|
}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# Cursor dogfood checklist
|
|
2
2
|
|
|
3
|
-
Short maintainer
|
|
3
|
+
Short maintainer menu for **minimal-surface** validation after prompt, bridge, replay, or manifest changes. Start with offline/faux checks and reuse exact-input retained evidence. Only changed behavior needing new real-service proof warrants a selected exercise on one representative environment; docs/metadata-only changes need no paid runs. The [platform smoke matrix](./platform-smoke.md) is optional, not a routine ship step. No full paid campaign replay or automatic paid retries. No paid Cloud testing for generic PRs/releases; only explicitly Cursor Cloud-focused PRs/issues may select necessary focused Cloud proof. Automated Cursor PR reviews continue unchanged.
|
|
4
4
|
|
|
5
5
|
## Minimal environment
|
|
6
6
|
|
|
@@ -33,7 +33,7 @@ Inspect the session JSONL under the temp `--session-dir`:
|
|
|
33
33
|
| Pattern | Meaning |
|
|
34
34
|
| --- | --- |
|
|
35
35
|
| `cursor-replay-*` | Display-only replay of Cursor SDK activity—not callable |
|
|
36
|
-
| `cursor-pi-bridge-run-*` | Live pi execution via bridge |
|
|
36
|
+
| `cursor-pi-bridge-run-*` (run) / `cursor-pi-bridge-<32 hex>-t<counter>` (tool) | Live pi execution via bridge |
|
|
37
37
|
| Callable tools | Cursor SDK host + MCP `listTools` + exposed `pi__*` only |
|
|
38
38
|
|
|
39
39
|
Common mistake: treating `cursor-replay-*` IDs or pi transcript tool labels as tools to invoke.
|
|
@@ -60,6 +60,6 @@ Canonical visual evidence: `npm run smoke:visual` (see [Cursor native tool visua
|
|
|
60
60
|
## Related docs
|
|
61
61
|
|
|
62
62
|
- [Cursor tool surfaces in pi](./cursor-tool-surfaces.md) — three namespaces and discoverability
|
|
63
|
-
- [Platform smoke
|
|
63
|
+
- [Platform smoke](./platform-smoke.md) — focused selection and optional comprehensive matrix
|
|
64
64
|
- [Cursor live smoke checklist](./cursor-live-smoke-checklist.md) — inner-loop/manual debug checks
|
|
65
65
|
- [Cursor testing lessons](./cursor-testing-lessons.md) — auth, JSONL scans, plan-mode traps
|
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
# Cursor Live Smoke Checklist
|
|
2
2
|
|
|
3
|
-
> **
|
|
3
|
+
> **Cost-conscious verification:** Offline/faux checks first; reuse exact-input retained evidence. Use only the smallest meaningful changed-behavior live check on one representative environment when real-service proof is necessary. Docs/metadata-only changes need no paid runs. The full `smoke:platform:all` matrix is optional. No paid Cloud testing for generic PRs/releases; only explicitly Cursor Cloud-focused PRs/issues may select necessary focused Cloud proof. Automated Cursor PR reviews continue unchanged. See [docs/platform-smoke.md](./platform-smoke.md).
|
|
4
4
|
|
|
5
5
|
## Purpose
|
|
6
6
|
|
|
7
|
-
Use this
|
|
7
|
+
Use this checklist as a menu, not a mandatory campaign. Select only behavior that changed and needs new real-service evidence after offline/faux checks and retained-proof reuse. Do not run host matrices merely for matrix coverage or automatically retry paid failures. See [Cursor testing lessons](./cursor-testing-lessons.md) for isolated-harness and replay pitfalls. Selected checks keep their distinct assertions, persisted evidence, visual proof, and cleanup requirements; do not claim unobserved coverage.
|
|
8
8
|
|
|
9
9
|
## Inner-loop rule
|
|
10
10
|
|
|
@@ -13,8 +13,8 @@ Use this manual checklist during development and debugging of Cursor provider/ru
|
|
|
13
13
|
- Use the local extension under test: `pi --approve -e . --cursor-no-fast --model cursor/grok-4.6`.
|
|
14
14
|
- Use a temporary `--session-dir` for every run.
|
|
15
15
|
- Do not paste or commit Cursor API keys, raw session contents with secrets, endpoint URLs, or local private paths.
|
|
16
|
-
- If
|
|
17
|
-
-
|
|
16
|
+
- If a selected check fails, retain evidence and diagnose offline before choosing a repair or a necessary follow-up call. No automatic paid retries.
|
|
17
|
+
- Scope new live calls to changed behavior that needs real-service proof; retain valid proof for unchanged behavior. Do not run every checklist section or the full matrix as a routine commit/release step.
|
|
18
18
|
- A check is passed only when the visible TUI/output, stderr diagnostics, and persisted JSONL agree with the expected behavior.
|
|
19
19
|
|
|
20
20
|
## Prerequisites
|
|
@@ -65,13 +65,13 @@ node scripts/validate-smoke-jsonl.mjs --replay-errors-only "$SMOKE_DIR/session-s
|
|
|
65
65
|
|
|
66
66
|
The replay scan flags only error `toolResult` / error assistant messages with `Tool grep/cursor/find/ls not found`, not successful reads of docs that mention those strings. See [Cursor testing lessons](./cursor-testing-lessons.md#what-counts-as-a-replay-failure).
|
|
67
67
|
|
|
68
|
-
`npm run smoke:live` is a helper only; it polls the section 3 TUI for answer/footer evidence and then cleans up the tmux session, but it does not replace the canonical rendered-PNG visual review in section 4. Run the relevant helper `--self-test` (`smoke:live`, `smoke:visual`, `smoke:steering`, or `smoke:isolated`) when changing sealed PATH or env wrappers.
|
|
68
|
+
`npm run smoke:live` is a helper only; it polls the section 3 TUI for answer/footer evidence and then cleans up the tmux session, but it does not replace the canonical rendered-PNG visual review in section 4. Run the relevant helper `--self-test` (`smoke:live`, `smoke:visual`, `smoke:steering`, or `smoke:isolated`) when changing sealed PATH or env wrappers. For changed behavior needing new live evidence, select the relevant manual check or existing single-suite/single-target platform run, not both by default. The comprehensive matrix is optional.
|
|
69
69
|
|
|
70
70
|
Pass criteria:
|
|
71
71
|
|
|
72
72
|
- `node --version` reports Node 24+.
|
|
73
73
|
- `pi --version` reports official Pi 0.87.1 or the selected official-latest/current-`fitchmultz/pi` compatibility target.
|
|
74
|
-
- `npm ls` shows exact `@cursor/sdk@1.0.32`;
|
|
74
|
+
- `npm ls` shows exact `@cursor/sdk@1.0.32`; development `@earendil-works/pi-ai`, `@earendil-works/pi-coding-agent`, and `@earendil-works/pi-tui` 0.99.1 and host TypeBox 1.3.27; and the bundled bridge runtime closure `@modelcontextprotocol/server@2.1.0`, `@modelcontextprotocol/hono@2.0.1`, `hono@4.13.9`, and `@hono/node-server@2.1.1`.
|
|
75
75
|
- `cursor/grok-4.6` appears in the model list.
|
|
76
76
|
- No Cursor key or auth token is printed.
|
|
77
77
|
- If neither `~/.pi/agent/auth.json` cursor auth nor `CURSOR_API_KEY` is available, stop and report the live smoke as blocked.
|
|
@@ -136,7 +136,7 @@ Pass criteria:
|
|
|
136
136
|
|
|
137
137
|
## 4. Focused visual card/color rendering check
|
|
138
138
|
|
|
139
|
-
This is
|
|
139
|
+
This is a visual debug menu for changed card/color behavior requiring new live evidence. Select only the relevant category below, or reuse a batched existing platform suite; do not execute the entire list by default. It requires offscreen TUI visual inspection, not only JSONL or code review. Use Node 24+, official Pi 0.87.1 or another current compatibility target, exact `@cursor/sdk@1.0.32`, a fresh temporary session dir, Cursor SDK `plan` mode, native replay enabled, and the checked-in visual runner. The runner resolves `pi` by directly walking the parent `PATH`, uses `process.execPath` for Node, and prepends that Node directory for both prereq checks and tmux launches so `#!/usr/bin/env node` shims use the validated Node. The default matrix is native replay only: native replay registration is forced on, settings sources are `none`, the pi bridge is off, overlapping built-in pi tools are not exposed, and inherited Cursor SDK event-debug artifact env is cleared. With `--event-debug`, debug capture writes to a deterministic directory under `VISUAL_DIR`.
|
|
140
140
|
|
|
141
141
|
```bash
|
|
142
142
|
VISUAL_DIR="$(mktemp -d /tmp/pi-cursor-sdk-1016-visual.XXXXXX)"
|
|
@@ -185,7 +185,7 @@ npm run smoke:visual -- "${VISUAL_ARGS[@]}" \
|
|
|
185
185
|
--prompt 'Stay in Cursor plan mode. If Cursor exposes plan, todo, task, or mode activity for this request, use that capability to outline a tiny unit test without editing files. Otherwise answer with a concise numbered plan. Do not use shell or file mutation tools.'
|
|
186
186
|
```
|
|
187
187
|
|
|
188
|
-
By default, `npm run smoke:visual` writes `.ansi`, `.txt`, `.html`, `.png`, and `.jsonl.path` artifacts. If
|
|
188
|
+
By default, `npm run smoke:visual` writes `.ansi`, `.txt`, `.html`, `.png`, and `.jsonl.path` artifacts. Check browser availability before a paid run. If PNG rendering fails but ANSI/HTML evidence was retained, render that retained evidence with the canonical browser/xterm path and save a PNG; do not repeat the model call merely to produce a screenshot. To visually audit bridge behavior or ambient Cursor settings, opt in with `--bridge`, `--bridge --expose-builtin-tools`, or `--setting-sources <value>` and label that evidence separately; do not count those opt-in runs as default native replay matrix proof.
|
|
189
189
|
|
|
190
190
|
Expected proof for each category is defined in [Cursor Native Tool Visual Audit Workflow](./cursor-native-tool-visual-audit.md). Do not mark a category passed because the prompt was sent. A category passes only when the PNG shows the expected card and the JSONL shows the expected completed `toolCall` / `toolResult` pair with the expected `isError` state.
|
|
191
191
|
|
|
@@ -193,7 +193,7 @@ Pass criteria:
|
|
|
193
193
|
|
|
194
194
|
- PNG screenshots exist for every claimed card category, not only text/JSONL logs.
|
|
195
195
|
- JSONL paths exist for every claimed card category.
|
|
196
|
-
-
|
|
196
|
+
- Each selected changed category has matching PNG + JSONL proof; retained exact-input proof covers unchanged categories. Do not claim unobserved categories.
|
|
197
197
|
- Native-looking read/search/find/list/shell/write/edit cards use intended pi card styling.
|
|
198
198
|
- Shell success is not red/error-styled; stdout is readable.
|
|
199
199
|
- Edit/diff previews show red/green added/removed colors and readable paths.
|
|
@@ -271,7 +271,7 @@ Allowed fields:
|
|
|
271
271
|
|
|
272
272
|
- event name
|
|
273
273
|
- run-safe correlation IDs that are not endpoint path components
|
|
274
|
-
- bridge/pi tool call IDs
|
|
274
|
+
- bridge run IDs remain `cursor-pi-bridge-run-*`; provider-facing bridge/pi tool call IDs encode the same run UUID as 32 hex characters, use the `cursor-pi-bridge-<32 hex>-t<counter>` shape, and stay within the 64-character limit
|
|
275
275
|
- hashed Cursor MCP call correlation IDs of the form `cursor-mcp-call-<8 hex chars>`
|
|
276
276
|
- exposed pi/MCP tool name pairs
|
|
277
277
|
- pending/queued/cancelled counts
|
|
@@ -316,7 +316,7 @@ Pass criteria:
|
|
|
316
316
|
|
|
317
317
|
## 9. Long-running bridge and abort/cancel
|
|
318
318
|
|
|
319
|
-
|
|
319
|
+
Select this check only when changed abort cleanup needs new real-service evidence; otherwise reuse valid retained proof. Keep process, bridge, and persisted-session cleanup assertions intact.
|
|
320
320
|
|
|
321
321
|
Use a harmless long-running command and interrupt it after the bridge request is queued:
|
|
322
322
|
|
|
@@ -353,8 +353,8 @@ Script-enforced pass criteria:
|
|
|
353
353
|
|
|
354
354
|
Additional manual usage checks for provider/accounting changes:
|
|
355
355
|
|
|
356
|
-
-
|
|
357
|
-
-
|
|
356
|
+
- Each assistant message's disjoint input/cache/output components should sum to `totalTokens` and describe one coherent current context, not cumulative billed spend.
|
|
357
|
+
- In split runs, earlier tool results can remain in later current-context estimates. Fresh, attributable LOCAL SDK usage takes precedence; late raw and billed facts remain in the separate ledger without rewriting emitted messages. See [context, compaction, and Cursor usage](../README.md#context-compaction-and-cursor-usage).
|
|
358
358
|
|
|
359
359
|
## 11. Standard local gates
|
|
360
360
|
|
|
@@ -385,7 +385,7 @@ Pass criteria:
|
|
|
385
385
|
|
|
386
386
|
## Coverage gaps this checklist makes explicit
|
|
387
387
|
|
|
388
|
-
|
|
388
|
+
Use this list to choose meaningful changed-behavior coverage, not to trigger a full paid replay. Prefer offline contracts and valid retained evidence:
|
|
389
389
|
|
|
390
390
|
- Long-running bridged tool abort/cancel cleanup.
|
|
391
391
|
- Native replay cards beyond read, especially shell/edit/write cards, when those renderers change.
|
|
@@ -395,4 +395,4 @@ Everything in this section is in scope when using this checklist for Cursor prov
|
|
|
395
395
|
- Ambient Cursor setting-source behavior when startup filtering or local Cursor settings handling changes.
|
|
396
396
|
- Model discovery aliases/context variants when model-discovery code or Cursor SDK versions change.
|
|
397
397
|
|
|
398
|
-
If
|
|
398
|
+
If changed behavior needs real-service proof and neither retained evidence nor an existing focused check covers it, report the specific gap and choose the smallest meaningful check. Do not assume mocks prove service behavior or make unrelated optional lanes a release requirement.
|