session-steward 0.1.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/LICENSE +21 -0
- package/README.md +217 -0
- package/bin/session-steward-cli.mjs +71 -0
- package/bin/session-steward.mjs +51 -0
- package/dist/assets/index-DGVNvKX8.js +9 -0
- package/dist/assets/index-DTDZWQb9.css +2 -0
- package/dist/index.html +3 -0
- package/docs/session-steward-overview.jpg +0 -0
- package/lib/cli.mjs +579 -0
- package/lib/providers/codex/index.mjs +35 -0
- package/lib/providers/codex/store.mjs +2300 -0
- package/lib/providers/index.mjs +18 -0
- package/lib/runtime.mjs +27 -0
- package/lib/server.mjs +753 -0
- package/lib/settings.mjs +229 -0
- package/lib/storage/jsonl.mjs +86 -0
- package/lib/storage/sqlite.mjs +66 -0
- package/lib/update-check.mjs +85 -0
- package/lib/version-support.mjs +103 -0
- package/package.json +70 -0
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 Mallik Cheripally
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
package/README.md
ADDED
|
@@ -0,0 +1,217 @@
|
|
|
1
|
+
# Session Steward
|
|
2
|
+
|
|
3
|
+
Safely review, back up, and remove local Codex sessions with a browser UI or terminal CLI.
|
|
4
|
+
|
|
5
|
+
Session Steward is a local-first Codex session manager for macOS and Linux. It shows what will be removed before cleanup, creates a local backup, and verifies the result afterward. Your session data stays on your computer.
|
|
6
|
+
|
|
7
|
+
Use it to clear old Codex session history, reclaim the space used by session artifacts, or remove local session traces without resetting the rest of your Codex setup.
|
|
8
|
+
|
|
9
|
+

|
|
10
|
+
|
|
11
|
+
## Why Session Steward
|
|
12
|
+
|
|
13
|
+
- Review local Codex sessions in a clear browser interface.
|
|
14
|
+
- See linked subagents and affected local records before deletion.
|
|
15
|
+
- Choose between focused session removal and a deeper local cleanup.
|
|
16
|
+
- Keep an automatic backup of every cleanup operation.
|
|
17
|
+
- Pause thorough cleanup when an unfamiliar storage format is found.
|
|
18
|
+
- Verify that selected session artifacts were removed.
|
|
19
|
+
- Use the same saved Codex folder in the browser and terminal interfaces.
|
|
20
|
+
|
|
21
|
+
Session Steward does not delete conversations stored in your ChatGPT account.
|
|
22
|
+
|
|
23
|
+
## Requirements
|
|
24
|
+
|
|
25
|
+
- macOS or Linux
|
|
26
|
+
- [Node.js](https://nodejs.org/) 24.15 or newer
|
|
27
|
+
- Local sessions created by Codex
|
|
28
|
+
|
|
29
|
+
Git and a separate SQLite installation are not required. Session Steward uses the SQLite support included with Node.js.
|
|
30
|
+
|
|
31
|
+
## Install
|
|
32
|
+
|
|
33
|
+
Install Session Steward globally with npm:
|
|
34
|
+
|
|
35
|
+
```bash
|
|
36
|
+
npm install --global session-steward
|
|
37
|
+
```
|
|
38
|
+
|
|
39
|
+
Then launch it:
|
|
40
|
+
|
|
41
|
+
```bash
|
|
42
|
+
session-steward
|
|
43
|
+
```
|
|
44
|
+
|
|
45
|
+
Session Steward opens its browser interface and listens only on `127.0.0.1`. It uses `~/.codex` by default.
|
|
46
|
+
|
|
47
|
+
Keep the terminal open while using Session Steward. Press `Ctrl+C` when you want to stop it.
|
|
48
|
+
|
|
49
|
+
To try it without a global installation:
|
|
50
|
+
|
|
51
|
+
```bash
|
|
52
|
+
npx session-steward@latest
|
|
53
|
+
```
|
|
54
|
+
|
|
55
|
+
## Quick start
|
|
56
|
+
|
|
57
|
+
1. Run `session-steward`.
|
|
58
|
+
2. Review the detected Codex sessions.
|
|
59
|
+
3. Select one or more sessions.
|
|
60
|
+
4. Choose a cleanup option and review the deletion preview.
|
|
61
|
+
5. Close any selected sessions that may still be active.
|
|
62
|
+
6. Confirm the cleanup.
|
|
63
|
+
|
|
64
|
+
Each cleanup creates a backup inside your Codex folder under `session-steward-backups/`.
|
|
65
|
+
|
|
66
|
+
## What you can adjust
|
|
67
|
+
|
|
68
|
+
- Search by session name, workspace, or session ID.
|
|
69
|
+
- Sort by recent activity, creation time, name, or workspace.
|
|
70
|
+
- Show subagent and supporting sessions when you need the additional detail.
|
|
71
|
+
- Choose standard or thorough cleanup for each deletion.
|
|
72
|
+
- Change the Codex session folder and save that choice for later runs.
|
|
73
|
+
|
|
74
|
+
## Safety model
|
|
75
|
+
|
|
76
|
+
Session Steward is intentionally conservative:
|
|
77
|
+
|
|
78
|
+
- All session inspection and cleanup happens on your computer.
|
|
79
|
+
- Only recognized Codex storage is changed.
|
|
80
|
+
- Unrecognized databases and changed storage layouts are reported but left untouched.
|
|
81
|
+
- Thorough cleanup is paused when the local storage layout is not supported.
|
|
82
|
+
- A backup is created before session data is changed.
|
|
83
|
+
- Cleanup is checked afterward for remaining selected artifacts.
|
|
84
|
+
- Authentication, plugins, caches, project files, worktrees, and unrelated sessions are not removed.
|
|
85
|
+
|
|
86
|
+
At startup, Session Steward may contact the public npm registry to check for a newer release. It does not send session contents or other Codex data.
|
|
87
|
+
|
|
88
|
+
Close selected Codex sessions before deleting them. Session Steward cannot currently determine whether a session is still being written to.
|
|
89
|
+
|
|
90
|
+
## Cleanup options
|
|
91
|
+
|
|
92
|
+
### Standard cleanup
|
|
93
|
+
|
|
94
|
+
Recommended for routine session removal. It removes the selected session registry entries, transcripts, history entries, session-index entries, logs, and linked subagents.
|
|
95
|
+
|
|
96
|
+
### Thorough cleanup
|
|
97
|
+
|
|
98
|
+
Choose this when you also want supported local references and generated records removed. It includes everything in standard cleanup, plus recognized ChatGPT Desktop references, memory outputs, and goal records.
|
|
99
|
+
|
|
100
|
+
Thorough cleanup remains unavailable when Session Steward finds storage it does not recognize. Standard cleanup stays available for the supported records it can identify safely.
|
|
101
|
+
|
|
102
|
+
## Backups and recovery
|
|
103
|
+
|
|
104
|
+
Completed cleanups keep their recovery backup on disk. If cleanup encounters a problem after creating its backup, Session Steward offers a guided restore from the cleanup progress screen.
|
|
105
|
+
|
|
106
|
+
Before restoring, Session Steward saves the current versions of the affected files in a separate safety folder. This gives you a second recovery point if the restore itself is interrupted.
|
|
107
|
+
|
|
108
|
+
## Use a custom Codex home folder
|
|
109
|
+
|
|
110
|
+
The browser interface shows the active Codex session folder. Choose **Change folder** to select another existing Codex folder and remember it for future browser and terminal sessions.
|
|
111
|
+
|
|
112
|
+
For a one-time folder override:
|
|
113
|
+
|
|
114
|
+
```bash
|
|
115
|
+
session-steward --codex-home /path/to/.codex
|
|
116
|
+
```
|
|
117
|
+
|
|
118
|
+
The command-line override applies only to that run and does not replace the saved folder.
|
|
119
|
+
|
|
120
|
+
Saved settings are stored at:
|
|
121
|
+
|
|
122
|
+
- macOS: `~/Library/Application Support/session-steward/config.json`
|
|
123
|
+
- Linux: `$XDG_CONFIG_HOME/session-steward/config.json`, or `~/.config/session-steward/config.json` when `XDG_CONFIG_HOME` is not set
|
|
124
|
+
|
|
125
|
+
## Terminal interface
|
|
126
|
+
|
|
127
|
+
For an interactive terminal workflow:
|
|
128
|
+
|
|
129
|
+
```bash
|
|
130
|
+
session-steward-cli
|
|
131
|
+
```
|
|
132
|
+
|
|
133
|
+
To inspect a small JSON result without opening the browser:
|
|
134
|
+
|
|
135
|
+
```bash
|
|
136
|
+
session-steward-cli --json --limit 10
|
|
137
|
+
```
|
|
138
|
+
|
|
139
|
+
Run `session-steward-cli --help` for all available options. The terminal interface uses the same saved Codex folder as the browser interface.
|
|
140
|
+
|
|
141
|
+
## Common commands
|
|
142
|
+
|
|
143
|
+
Start without opening a browser:
|
|
144
|
+
|
|
145
|
+
```bash
|
|
146
|
+
session-steward --no-open
|
|
147
|
+
```
|
|
148
|
+
|
|
149
|
+
Update to the latest release:
|
|
150
|
+
|
|
151
|
+
```bash
|
|
152
|
+
npm install --global session-steward@latest
|
|
153
|
+
```
|
|
154
|
+
|
|
155
|
+
Uninstall Session Steward:
|
|
156
|
+
|
|
157
|
+
```bash
|
|
158
|
+
npm uninstall --global session-steward
|
|
159
|
+
```
|
|
160
|
+
|
|
161
|
+
Uninstalling the package does not remove your Codex sessions, Session Steward backups, or saved folder preference.
|
|
162
|
+
|
|
163
|
+
## Troubleshooting
|
|
164
|
+
|
|
165
|
+
### The browser did not open
|
|
166
|
+
|
|
167
|
+
Run `session-steward --no-open`, then open the local address printed in the terminal.
|
|
168
|
+
|
|
169
|
+
### No sessions were found
|
|
170
|
+
|
|
171
|
+
Confirm that the displayed Codex folder contains your local session data. Use **Change folder** or pass `--codex-home` for a one-time override.
|
|
172
|
+
|
|
173
|
+
### Thorough cleanup is unavailable
|
|
174
|
+
|
|
175
|
+
Open the compatibility details in Session Steward. New or changed local storage is left untouched until that format is supported. You can still use standard cleanup when its recognized records are supported.
|
|
176
|
+
|
|
177
|
+
### Node.js is too old
|
|
178
|
+
|
|
179
|
+
Install Node.js 24.15 or newer, then run `session-steward` again.
|
|
180
|
+
|
|
181
|
+
## Development
|
|
182
|
+
|
|
183
|
+
Clone the repository and install its dependencies:
|
|
184
|
+
|
|
185
|
+
```bash
|
|
186
|
+
git clone https://github.com/mallikcheripally/session-steward.git
|
|
187
|
+
cd session-steward
|
|
188
|
+
npm install
|
|
189
|
+
```
|
|
190
|
+
|
|
191
|
+
Useful commands:
|
|
192
|
+
|
|
193
|
+
```bash
|
|
194
|
+
npm start
|
|
195
|
+
npm test
|
|
196
|
+
npm run benchmark:scale
|
|
197
|
+
npm run benchmark:discovery
|
|
198
|
+
npm run benchmark:transcripts
|
|
199
|
+
npm run build
|
|
200
|
+
npm pack --dry-run --cache .npm-cache
|
|
201
|
+
```
|
|
202
|
+
|
|
203
|
+
Tests use temporary synthetic Codex data. They do not read or change your local Codex sessions.
|
|
204
|
+
|
|
205
|
+
## Roadmap
|
|
206
|
+
|
|
207
|
+
Codex is supported today. Claude Code is planned as the next provider integration.
|
|
208
|
+
|
|
209
|
+
## Support
|
|
210
|
+
|
|
211
|
+
Use [GitHub Issues](https://github.com/mallikcheripally/session-steward/issues) to report a bug, request a provider, or share a storage format that Session Steward does not yet recognize.
|
|
212
|
+
|
|
213
|
+
Session Steward is an independent project and is not affiliated with or endorsed by OpenAI.
|
|
214
|
+
|
|
215
|
+
## License
|
|
216
|
+
|
|
217
|
+
[MIT](LICENSE)
|
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
|
|
3
|
+
import { parseArgs } from "node:util";
|
|
4
|
+
|
|
5
|
+
import { assertSupportedNode } from "../lib/runtime.mjs";
|
|
6
|
+
|
|
7
|
+
assertSupportedNode();
|
|
8
|
+
|
|
9
|
+
const { runCli } = await import("../lib/cli.mjs");
|
|
10
|
+
|
|
11
|
+
const { values } = parseArgs({
|
|
12
|
+
allowPositionals: false,
|
|
13
|
+
options: {
|
|
14
|
+
"codex-home": {
|
|
15
|
+
type: "string",
|
|
16
|
+
},
|
|
17
|
+
help: {
|
|
18
|
+
short: "h",
|
|
19
|
+
type: "boolean",
|
|
20
|
+
},
|
|
21
|
+
"include-internals": {
|
|
22
|
+
type: "boolean",
|
|
23
|
+
},
|
|
24
|
+
json: {
|
|
25
|
+
type: "boolean",
|
|
26
|
+
},
|
|
27
|
+
limit: {
|
|
28
|
+
type: "string",
|
|
29
|
+
},
|
|
30
|
+
search: {
|
|
31
|
+
type: "string",
|
|
32
|
+
},
|
|
33
|
+
sort: {
|
|
34
|
+
type: "string",
|
|
35
|
+
},
|
|
36
|
+
},
|
|
37
|
+
});
|
|
38
|
+
|
|
39
|
+
const numericLimit =
|
|
40
|
+
values.limit && Number.isFinite(Number.parseInt(values.limit, 10))
|
|
41
|
+
? Number.parseInt(values.limit, 10)
|
|
42
|
+
: null;
|
|
43
|
+
|
|
44
|
+
async function main() {
|
|
45
|
+
const help = values.help ?? false;
|
|
46
|
+
let codexHome = values["codex-home"];
|
|
47
|
+
|
|
48
|
+
if (!help) {
|
|
49
|
+
const { createProviderSettings } = await import("../lib/settings.mjs");
|
|
50
|
+
const settings = await createProviderSettings({
|
|
51
|
+
providerHomeOverrides: codexHome === undefined ? {} : { codex: codexHome },
|
|
52
|
+
});
|
|
53
|
+
codexHome = settings.getHome("codex");
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
await runCli({
|
|
57
|
+
codexHome,
|
|
58
|
+
help,
|
|
59
|
+
includeInternals: values["include-internals"] ?? false,
|
|
60
|
+
json: values.json ?? false,
|
|
61
|
+
limit: numericLimit,
|
|
62
|
+
search: values.search ?? "",
|
|
63
|
+
sort: values.sort ?? "updated",
|
|
64
|
+
});
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
main().catch((error) => {
|
|
68
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
69
|
+
process.stderr.write(`${message}\n`);
|
|
70
|
+
process.exitCode = 1;
|
|
71
|
+
});
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
|
|
3
|
+
import { parseArgs } from "node:util";
|
|
4
|
+
import { spawn } from "node:child_process";
|
|
5
|
+
|
|
6
|
+
import packageMetadata from "../package.json" with { type: "json" };
|
|
7
|
+
import { assertSupportedNode } from "../lib/runtime.mjs";
|
|
8
|
+
import { findAvailableUpdate, formatUpdateNotice } from "../lib/update-check.mjs";
|
|
9
|
+
|
|
10
|
+
assertSupportedNode();
|
|
11
|
+
|
|
12
|
+
const { startLocalServer } = await import("../lib/server.mjs");
|
|
13
|
+
|
|
14
|
+
const { values } = parseArgs({
|
|
15
|
+
options: {
|
|
16
|
+
"codex-home": { type: "string" },
|
|
17
|
+
"no-open": { type: "boolean", default: false },
|
|
18
|
+
port: { type: "string" },
|
|
19
|
+
},
|
|
20
|
+
});
|
|
21
|
+
const port = values.port === undefined ? 0 : Number.parseInt(values.port, 10);
|
|
22
|
+
const availableUpdate = await findAvailableUpdate({ packageMetadata });
|
|
23
|
+
|
|
24
|
+
if (availableUpdate) {
|
|
25
|
+
process.stdout.write(`${formatUpdateNotice(availableUpdate)}\n`);
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
const server = await startLocalServer({
|
|
29
|
+
codexHome: values["codex-home"],
|
|
30
|
+
port,
|
|
31
|
+
});
|
|
32
|
+
|
|
33
|
+
process.stdout.write(`Session Steward is running at http://127.0.0.1:${server.port}\n`);
|
|
34
|
+
|
|
35
|
+
if (!values["no-open"]) {
|
|
36
|
+
const url = `http://127.0.0.1:${server.port}`;
|
|
37
|
+
const openerCommand = process.platform === "darwin"
|
|
38
|
+
? "open"
|
|
39
|
+
: process.platform === "linux"
|
|
40
|
+
? "xdg-open"
|
|
41
|
+
: null;
|
|
42
|
+
|
|
43
|
+
if (openerCommand) {
|
|
44
|
+
const opener = spawn(openerCommand, [url], { detached: true, stdio: "ignore" });
|
|
45
|
+
opener.unref();
|
|
46
|
+
} else {
|
|
47
|
+
process.stdout.write(`Open ${url} in a browser.\n`);
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
process.stdout.write("Press Ctrl+C to stop.\n");
|