pi-auto-save-to-markdown 0.7.3 → 0.7.4
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 +4 -4
- package/README.zh.md +4 -4
- package/index.ts +36 -14
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -92,10 +92,10 @@ changes never touch the filename, and manually renamed files are left alone.
|
|
|
92
92
|
---
|
|
93
93
|
title: "Fix login redirect loop"
|
|
94
94
|
agent: "pi"
|
|
95
|
-
format_version: "1.
|
|
95
|
+
format_version: "1.3"
|
|
96
96
|
session_id: "d0a4f541-976d-4d1b-8e1c-30a1f2b3c4d5"
|
|
97
97
|
session_key: "c2088d77"
|
|
98
|
-
|
|
98
|
+
branch_last_entry_id: "019be3a2-1f4d-7c8a-9b01-d23e45f6a7b8"
|
|
99
99
|
model: "z-ai/glm-5.3"
|
|
100
100
|
provider: "openrouter"
|
|
101
101
|
cost: 0.023401
|
|
@@ -105,8 +105,8 @@ tokens_output: 3515
|
|
|
105
105
|
tokens_cache_read: 0
|
|
106
106
|
tokens_cache_write: 0
|
|
107
107
|
messages: 8
|
|
108
|
-
created: "2026-08-
|
|
109
|
-
updated: "2026-08-
|
|
108
|
+
created: "2026-08-29T13:05:12+08:00"
|
|
109
|
+
updated: "2026-08-29T13:42:10+08:00"
|
|
110
110
|
project_root: "/Users/me/project"
|
|
111
111
|
session_file: "~/.pi/agent/sessions/--Users-me-project-20260829-050500_ab12.jsonl"
|
|
112
112
|
---
|
package/README.zh.md
CHANGED
|
@@ -66,10 +66,10 @@ PI_SAVE_CONVERSATION_DIR=notes/ai pi
|
|
|
66
66
|
---
|
|
67
67
|
title: "修复登录重定向死循环"
|
|
68
68
|
agent: "pi"
|
|
69
|
-
format_version: "1.
|
|
69
|
+
format_version: "1.3"
|
|
70
70
|
session_id: "d0a4f541-976d-4d1b-8e1c-30a1f2b3c4d5"
|
|
71
71
|
session_key: "c2088d77"
|
|
72
|
-
|
|
72
|
+
branch_last_entry_id: "019be3a2-1f4d-7c8a-9b01-d23e45f6a7b8"
|
|
73
73
|
model: "z-ai/glm-5.3"
|
|
74
74
|
provider: "openrouter"
|
|
75
75
|
cost: 0.023401
|
|
@@ -79,8 +79,8 @@ tokens_output: 3515
|
|
|
79
79
|
tokens_cache_read: 0
|
|
80
80
|
tokens_cache_write: 0
|
|
81
81
|
messages: 8
|
|
82
|
-
created: "2026-08-
|
|
83
|
-
updated: "2026-08-
|
|
82
|
+
created: "2026-08-29T13:05:12+08:00"
|
|
83
|
+
updated: "2026-08-29T13:42:10+08:00"
|
|
84
84
|
project_root: "/Users/me/project"
|
|
85
85
|
session_file: "~/.pi/agent/sessions/--Users-me-project-20260829-050500_ab12.jsonl"
|
|
86
86
|
---
|
package/index.ts
CHANGED
|
@@ -25,11 +25,14 @@
|
|
|
25
25
|
* plugins for other runtimes would write their own value), format_version
|
|
26
26
|
* (the document format of the last write — additive frontmatter fields
|
|
27
27
|
* never bump it; see FORMAT_VERSION), session id, session key (the
|
|
28
|
-
* filename key), last entry id (
|
|
29
|
-
*
|
|
30
|
-
*
|
|
31
|
-
*
|
|
32
|
-
*
|
|
28
|
+
* filename key), branch last entry id (field `branch_last_entry_id` — the
|
|
29
|
+
* id of the deepest message entry on the saved branch: the file's position
|
|
30
|
+
* in the session jsonl tree at the last write, scoped to this file's
|
|
31
|
+
* branch, not the session-wide last entry), model, provider, cumulative
|
|
32
|
+
* cost and tokens (input, output,
|
|
33
|
+
* cache read/write), message count, created/updated timestamps (tz-aware
|
|
34
|
+
* ISO 8601 in the local timezone with its numeric UTC offset, e.g.
|
|
35
|
+
* "2026-08-29T13:05:12+08:00"), project root and session file.
|
|
33
36
|
* - Body format: every message block opens with a setext-H1 info header
|
|
34
37
|
* (`User <span …>YYYY-MM-DD HH:MM:SS</span>` /
|
|
35
38
|
* `Assistant <span …>YYYY-MM-DD HH:MM:SS · model</span>`, where the span
|
|
@@ -196,7 +199,7 @@ const SAVE_STATE_SCHEMA = "1.2";
|
|
|
196
199
|
* the frontmatter and the document heading); additive frontmatter fields do
|
|
197
200
|
* NOT bump it — they are invisible to any within-major parser.
|
|
198
201
|
*/
|
|
199
|
-
const FORMAT_VERSION = "1.
|
|
202
|
+
const FORMAT_VERSION = "1.3";
|
|
200
203
|
|
|
201
204
|
/**
|
|
202
205
|
* Package version of this extension, read best-effort from the adjacent
|
|
@@ -248,8 +251,8 @@ interface SaveState {
|
|
|
248
251
|
/**
|
|
249
252
|
* Id of the session tree leaf at save time (getLeafId()) — may be a custom
|
|
250
253
|
* state entry rather than a message; used to rank continuation candidates
|
|
251
|
-
* on the current path. Distinct from frontmatter `
|
|
252
|
-
* the deepest message entry (an id actually present in the file).
|
|
254
|
+
* on the current path. Distinct from frontmatter `branch_last_entry_id`,
|
|
255
|
+
* which is the deepest message entry (an id actually present in the file).
|
|
253
256
|
*/
|
|
254
257
|
lastSavedEntryId: string | null;
|
|
255
258
|
file: string;
|
|
@@ -388,10 +391,11 @@ interface BranchMeta {
|
|
|
388
391
|
sessionKey: string;
|
|
389
392
|
/**
|
|
390
393
|
* Id of the deepest message entry on the saved branch at the last write
|
|
391
|
-
* (field name `
|
|
392
|
-
* session jsonl tree
|
|
394
|
+
* (field name `branch_last_entry_id`) — the file's exact position in the
|
|
395
|
+
* session jsonl tree, scoped to this file's branch rather than the
|
|
396
|
+
* session-wide last entry. Updated on every append, like `updated`.
|
|
393
397
|
*/
|
|
394
|
-
|
|
398
|
+
branchLastEntryId: string;
|
|
395
399
|
model: string | null;
|
|
396
400
|
provider: string | null;
|
|
397
401
|
cost: number;
|
|
@@ -1097,6 +1101,24 @@ export default function (pi: ExtensionAPI) {
|
|
|
1097
1101
|
return `"${safe.replace(/\\/g, "\\\\").replace(/"/g, '\\"')}"`;
|
|
1098
1102
|
}
|
|
1099
1103
|
|
|
1104
|
+
/**
|
|
1105
|
+
* ISO 8601 timestamp in the machine's local timezone, with the numeric
|
|
1106
|
+
* UTC offset appended (e.g. "2026-08-29T13:05:12+08:00"): tz-aware, so the
|
|
1107
|
+
* value reads as local wall-clock time without assuming the reader's
|
|
1108
|
+
* timezone. Legacy files written with UTC "Z" values parse identically.
|
|
1109
|
+
*/
|
|
1110
|
+
function localIsoTimestamp(date: Date): string {
|
|
1111
|
+
const pad = (n: number) => String(n).padStart(2, "0");
|
|
1112
|
+
const offsetMin = -date.getTimezoneOffset();
|
|
1113
|
+
const sign = offsetMin >= 0 ? "+" : "-";
|
|
1114
|
+
const abs = Math.abs(offsetMin);
|
|
1115
|
+
return (
|
|
1116
|
+
`${date.getFullYear()}-${pad(date.getMonth() + 1)}-${pad(date.getDate())}` +
|
|
1117
|
+
`T${pad(date.getHours())}:${pad(date.getMinutes())}:${pad(date.getSeconds())}` +
|
|
1118
|
+
`${sign}${pad(Math.floor(abs / 60))}:${pad(abs % 60)}`
|
|
1119
|
+
);
|
|
1120
|
+
}
|
|
1121
|
+
|
|
1100
1122
|
function frontmatter(meta: BranchMeta): string {
|
|
1101
1123
|
const lines: string[] = ["---"];
|
|
1102
1124
|
lines.push(`title: ${yamlQuote(meta.title)}`);
|
|
@@ -1104,7 +1126,7 @@ export default function (pi: ExtensionAPI) {
|
|
|
1104
1126
|
lines.push(`format_version: ${yamlQuote(FORMAT_VERSION)}`);
|
|
1105
1127
|
if (meta.sessionId) lines.push(`session_id: ${yamlQuote(meta.sessionId)}`);
|
|
1106
1128
|
lines.push(`session_key: ${yamlQuote(meta.sessionKey)}`);
|
|
1107
|
-
lines.push(`
|
|
1129
|
+
lines.push(`branch_last_entry_id: ${yamlQuote(meta.branchLastEntryId)}`);
|
|
1108
1130
|
if (meta.model) lines.push(`model: ${yamlQuote(meta.model)}`);
|
|
1109
1131
|
if (meta.provider) lines.push(`provider: ${yamlQuote(meta.provider)}`);
|
|
1110
1132
|
lines.push(`cost: ${meta.cost.toFixed(6)}`);
|
|
@@ -1177,14 +1199,14 @@ export default function (pi: ExtensionAPI) {
|
|
|
1177
1199
|
tokensCacheWrite += usage.cacheWrite ?? 0;
|
|
1178
1200
|
}
|
|
1179
1201
|
}
|
|
1180
|
-
const now = new Date()
|
|
1202
|
+
const now = localIsoTimestamp(new Date());
|
|
1181
1203
|
return {
|
|
1182
1204
|
title: displayTitle(ctx, firstUserText(pathMessages)),
|
|
1183
1205
|
agent: agent ?? AGENT,
|
|
1184
1206
|
sessionId: ctx.session.getSessionId(),
|
|
1185
1207
|
sessionFile: ctx.session.getSessionFile() ?? null,
|
|
1186
1208
|
sessionKey,
|
|
1187
|
-
|
|
1209
|
+
branchLastEntryId: pathMessages[pathMessages.length - 1].id,
|
|
1188
1210
|
model,
|
|
1189
1211
|
provider,
|
|
1190
1212
|
cost,
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "pi-auto-save-to-markdown",
|
|
3
|
-
"version": "0.7.
|
|
3
|
+
"version": "0.7.4",
|
|
4
4
|
"description": "Pi extension that automatically saves each completed conversation turn as a markdown file with YAML frontmatter, one file per session-tree branch.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "MIT",
|