droid-patch 0.7.1 → 0.8.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/README.md +61 -0
- package/README.zh-CN.md +61 -0
- package/dist/alias-Bhigcbue.mjs.map +1 -1
- package/dist/cli.mjs +302 -7
- package/dist/cli.mjs.map +1 -1
- package/package.json +1 -1
package/dist/cli.mjs
CHANGED
|
@@ -1418,7 +1418,7 @@ async function main() {
|
|
|
1418
1418
|
main().catch(() => {});
|
|
1419
1419
|
`;
|
|
1420
1420
|
}
|
|
1421
|
-
function generateStatuslineWrapperScript(execTargetPath, monitorScriptPath) {
|
|
1421
|
+
function generateStatuslineWrapperScript(execTargetPath, monitorScriptPath, sessionsScriptPath) {
|
|
1422
1422
|
return `#!/usr/bin/env python3
|
|
1423
1423
|
# Droid with Statusline (PTY proxy)
|
|
1424
1424
|
# Auto-generated by droid-patch --statusline
|
|
@@ -1444,6 +1444,7 @@ import fcntl
|
|
|
1444
1444
|
|
|
1445
1445
|
EXEC_TARGET = ${JSON.stringify(execTargetPath)}
|
|
1446
1446
|
STATUSLINE_MONITOR = ${JSON.stringify(monitorScriptPath)}
|
|
1447
|
+
SESSIONS_SCRIPT = ${sessionsScriptPath ? JSON.stringify(sessionsScriptPath) : "None"}
|
|
1447
1448
|
|
|
1448
1449
|
IS_APPLE_TERMINAL = os.environ.get("TERM_PROGRAM") == "Apple_Terminal"
|
|
1449
1450
|
MIN_RENDER_INTERVAL_MS = 800 if IS_APPLE_TERMINAL else 400
|
|
@@ -1483,6 +1484,25 @@ def _exec_passthrough():
|
|
|
1483
1484
|
sys.stderr.write(f"[statusline] passthrough failed: {e}\\n")
|
|
1484
1485
|
sys.exit(1)
|
|
1485
1486
|
|
|
1487
|
+
def _is_sessions_command(argv):
|
|
1488
|
+
for a in argv:
|
|
1489
|
+
if a == "--":
|
|
1490
|
+
return False
|
|
1491
|
+
if a == "--sessions":
|
|
1492
|
+
return True
|
|
1493
|
+
return False
|
|
1494
|
+
|
|
1495
|
+
def _run_sessions():
|
|
1496
|
+
if SESSIONS_SCRIPT and os.path.exists(SESSIONS_SCRIPT):
|
|
1497
|
+
os.execvp("node", ["node", SESSIONS_SCRIPT])
|
|
1498
|
+
else:
|
|
1499
|
+
sys.stderr.write("[statusline] sessions script not found\\n")
|
|
1500
|
+
sys.exit(1)
|
|
1501
|
+
|
|
1502
|
+
# Handle --sessions command
|
|
1503
|
+
if _is_sessions_command(sys.argv[1:]):
|
|
1504
|
+
_run_sessions()
|
|
1505
|
+
|
|
1486
1506
|
# Passthrough for non-interactive/meta commands (avoid clearing screen / PTY proxy)
|
|
1487
1507
|
if (not sys.stdin.isatty()) or (not sys.stdout.isatty()) or _should_passthrough(sys.argv[1:]):
|
|
1488
1508
|
_exec_passthrough()
|
|
@@ -2381,13 +2401,13 @@ if __name__ == "__main__":
|
|
|
2381
2401
|
main()
|
|
2382
2402
|
`;
|
|
2383
2403
|
}
|
|
2384
|
-
async function createStatuslineFiles(outputDir, execTargetPath, aliasName) {
|
|
2404
|
+
async function createStatuslineFiles(outputDir, execTargetPath, aliasName, sessionsScriptPath) {
|
|
2385
2405
|
if (!existsSync(outputDir)) await mkdir(outputDir, { recursive: true });
|
|
2386
2406
|
const monitorScriptPath = join(outputDir, `${aliasName}-statusline.js`);
|
|
2387
2407
|
const wrapperScriptPath = join(outputDir, aliasName);
|
|
2388
2408
|
await writeFile(monitorScriptPath, generateStatuslineMonitorScript());
|
|
2389
2409
|
await chmod(monitorScriptPath, 493);
|
|
2390
|
-
await writeFile(wrapperScriptPath, generateStatuslineWrapperScript(execTargetPath, monitorScriptPath));
|
|
2410
|
+
await writeFile(wrapperScriptPath, generateStatuslineWrapperScript(execTargetPath, monitorScriptPath, sessionsScriptPath));
|
|
2391
2411
|
await chmod(wrapperScriptPath, 493);
|
|
2392
2412
|
return {
|
|
2393
2413
|
wrapperScript: wrapperScriptPath,
|
|
@@ -2395,6 +2415,269 @@ async function createStatuslineFiles(outputDir, execTargetPath, aliasName) {
|
|
|
2395
2415
|
};
|
|
2396
2416
|
}
|
|
2397
2417
|
|
|
2418
|
+
//#endregion
|
|
2419
|
+
//#region src/sessions-patch.ts
|
|
2420
|
+
/**
|
|
2421
|
+
* Generate sessions browser script (Node.js)
|
|
2422
|
+
*/
|
|
2423
|
+
function generateSessionsBrowserScript(aliasName) {
|
|
2424
|
+
return `#!/usr/bin/env node
|
|
2425
|
+
// Droid Sessions Browser - Interactive selector
|
|
2426
|
+
// Auto-generated by droid-patch
|
|
2427
|
+
|
|
2428
|
+
const fs = require('fs');
|
|
2429
|
+
const path = require('path');
|
|
2430
|
+
const readline = require('readline');
|
|
2431
|
+
const { execSync, spawn } = require('child_process');
|
|
2432
|
+
|
|
2433
|
+
const FACTORY_HOME = path.join(require('os').homedir(), '.factory');
|
|
2434
|
+
const SESSIONS_ROOT = path.join(FACTORY_HOME, 'sessions');
|
|
2435
|
+
const ALIAS_NAME = ${JSON.stringify(aliasName)};
|
|
2436
|
+
|
|
2437
|
+
// ANSI
|
|
2438
|
+
const CYAN = '\\x1b[36m';
|
|
2439
|
+
const GREEN = '\\x1b[32m';
|
|
2440
|
+
const YELLOW = '\\x1b[33m';
|
|
2441
|
+
const RED = '\\x1b[31m';
|
|
2442
|
+
const DIM = '\\x1b[2m';
|
|
2443
|
+
const RESET = '\\x1b[0m';
|
|
2444
|
+
const BOLD = '\\x1b[1m';
|
|
2445
|
+
const CLEAR = '\\x1b[2J\\x1b[H';
|
|
2446
|
+
const HIDE_CURSOR = '\\x1b[?25l';
|
|
2447
|
+
const SHOW_CURSOR = '\\x1b[?25h';
|
|
2448
|
+
|
|
2449
|
+
function sanitizePath(p) {
|
|
2450
|
+
return p.replace(/:/g, '').replace(/[\\\\/]/g, '-');
|
|
2451
|
+
}
|
|
2452
|
+
|
|
2453
|
+
function parseSessionFile(jsonlPath, settingsPath) {
|
|
2454
|
+
const sessionId = path.basename(jsonlPath, '.jsonl');
|
|
2455
|
+
const stats = fs.statSync(jsonlPath);
|
|
2456
|
+
|
|
2457
|
+
const result = {
|
|
2458
|
+
id: sessionId,
|
|
2459
|
+
title: '',
|
|
2460
|
+
mtime: stats.mtimeMs,
|
|
2461
|
+
model: '',
|
|
2462
|
+
firstUserMsg: '',
|
|
2463
|
+
lastUserMsg: '',
|
|
2464
|
+
messageCount: 0,
|
|
2465
|
+
lastTimestamp: '',
|
|
2466
|
+
};
|
|
2467
|
+
|
|
2468
|
+
try {
|
|
2469
|
+
const content = fs.readFileSync(jsonlPath, 'utf-8');
|
|
2470
|
+
const lines = content.split('\\n').filter(l => l.trim());
|
|
2471
|
+
const userMessages = [];
|
|
2472
|
+
|
|
2473
|
+
for (const line of lines) {
|
|
2474
|
+
try {
|
|
2475
|
+
const obj = JSON.parse(line);
|
|
2476
|
+
if (obj.type === 'session_start') {
|
|
2477
|
+
result.title = obj.title || '';
|
|
2478
|
+
} else if (obj.type === 'message') {
|
|
2479
|
+
result.messageCount++;
|
|
2480
|
+
if (obj.timestamp) result.lastTimestamp = obj.timestamp;
|
|
2481
|
+
|
|
2482
|
+
const msg = obj.message || {};
|
|
2483
|
+
if (msg.role === 'user' && Array.isArray(msg.content)) {
|
|
2484
|
+
for (const c of msg.content) {
|
|
2485
|
+
if (c && c.type === 'text' && c.text && !c.text.startsWith('<system-reminder>')) {
|
|
2486
|
+
userMessages.push(c.text.slice(0, 150).replace(/\\n/g, ' ').trim());
|
|
2487
|
+
break;
|
|
2488
|
+
}
|
|
2489
|
+
}
|
|
2490
|
+
}
|
|
2491
|
+
}
|
|
2492
|
+
} catch {}
|
|
2493
|
+
}
|
|
2494
|
+
|
|
2495
|
+
if (userMessages.length > 0) {
|
|
2496
|
+
result.firstUserMsg = userMessages[0];
|
|
2497
|
+
result.lastUserMsg = userMessages.length > 1 ? userMessages[userMessages.length - 1] : '';
|
|
2498
|
+
}
|
|
2499
|
+
} catch {}
|
|
2500
|
+
|
|
2501
|
+
if (fs.existsSync(settingsPath)) {
|
|
2502
|
+
try {
|
|
2503
|
+
const settings = JSON.parse(fs.readFileSync(settingsPath, 'utf-8'));
|
|
2504
|
+
result.model = settings.model || '';
|
|
2505
|
+
} catch {}
|
|
2506
|
+
}
|
|
2507
|
+
|
|
2508
|
+
return result;
|
|
2509
|
+
}
|
|
2510
|
+
|
|
2511
|
+
function collectSessions() {
|
|
2512
|
+
const cwd = process.cwd();
|
|
2513
|
+
const cwdSanitized = sanitizePath(cwd);
|
|
2514
|
+
const sessions = [];
|
|
2515
|
+
|
|
2516
|
+
if (!fs.existsSync(SESSIONS_ROOT)) return sessions;
|
|
2517
|
+
|
|
2518
|
+
for (const wsDir of fs.readdirSync(SESSIONS_ROOT)) {
|
|
2519
|
+
if (wsDir !== cwdSanitized) continue;
|
|
2520
|
+
|
|
2521
|
+
const wsPath = path.join(SESSIONS_ROOT, wsDir);
|
|
2522
|
+
if (!fs.statSync(wsPath).isDirectory()) continue;
|
|
2523
|
+
|
|
2524
|
+
for (const file of fs.readdirSync(wsPath)) {
|
|
2525
|
+
if (!file.endsWith('.jsonl')) continue;
|
|
2526
|
+
|
|
2527
|
+
const sessionId = file.slice(0, -6);
|
|
2528
|
+
const jsonlPath = path.join(wsPath, file);
|
|
2529
|
+
const settingsPath = path.join(wsPath, sessionId + '.settings.json');
|
|
2530
|
+
|
|
2531
|
+
try {
|
|
2532
|
+
const session = parseSessionFile(jsonlPath, settingsPath);
|
|
2533
|
+
if (session.messageCount === 0 || !session.firstUserMsg) continue;
|
|
2534
|
+
sessions.push(session);
|
|
2535
|
+
} catch {}
|
|
2536
|
+
}
|
|
2537
|
+
}
|
|
2538
|
+
|
|
2539
|
+
sessions.sort((a, b) => b.mtime - a.mtime);
|
|
2540
|
+
return sessions.slice(0, 50);
|
|
2541
|
+
}
|
|
2542
|
+
|
|
2543
|
+
function formatTime(ts) {
|
|
2544
|
+
if (!ts) return '';
|
|
2545
|
+
try {
|
|
2546
|
+
const d = new Date(ts);
|
|
2547
|
+
return d.toLocaleString('zh-CN', { month: '2-digit', day: '2-digit', hour: '2-digit', minute: '2-digit' });
|
|
2548
|
+
} catch {
|
|
2549
|
+
return ts.slice(0, 16);
|
|
2550
|
+
}
|
|
2551
|
+
}
|
|
2552
|
+
|
|
2553
|
+
function truncate(s, len) {
|
|
2554
|
+
if (!s) return '';
|
|
2555
|
+
s = s.replace(/\\n/g, ' ');
|
|
2556
|
+
return s.length > len ? s.slice(0, len - 3) + '...' : s;
|
|
2557
|
+
}
|
|
2558
|
+
|
|
2559
|
+
function render(sessions, selected, offset, rows) {
|
|
2560
|
+
const cwd = process.cwd();
|
|
2561
|
+
const pageSize = rows - 6;
|
|
2562
|
+
const visible = sessions.slice(offset, offset + pageSize);
|
|
2563
|
+
|
|
2564
|
+
let out = CLEAR;
|
|
2565
|
+
out += BOLD + 'Sessions: ' + RESET + DIM + cwd + RESET + '\\n';
|
|
2566
|
+
out += DIM + '[↑/↓] Select [Enter] Resume [q] Quit' + RESET + '\\n\\n';
|
|
2567
|
+
|
|
2568
|
+
for (let i = 0; i < visible.length; i++) {
|
|
2569
|
+
const s = visible[i];
|
|
2570
|
+
const idx = offset + i;
|
|
2571
|
+
const isSelected = idx === selected;
|
|
2572
|
+
const prefix = isSelected ? GREEN + '▶ ' + RESET : ' ';
|
|
2573
|
+
|
|
2574
|
+
const title = truncate(s.title || '(no title)', 35);
|
|
2575
|
+
const time = formatTime(s.lastTimestamp);
|
|
2576
|
+
const model = truncate(s.model, 20);
|
|
2577
|
+
|
|
2578
|
+
if (isSelected) {
|
|
2579
|
+
out += prefix + YELLOW + title + RESET + '\\n';
|
|
2580
|
+
out += ' ' + DIM + 'ID: ' + RESET + CYAN + s.id + RESET + '\\n';
|
|
2581
|
+
out += ' ' + DIM + 'Last: ' + time + ' | Model: ' + model + ' | ' + s.messageCount + ' msgs' + RESET + '\\n';
|
|
2582
|
+
out += ' ' + DIM + 'First input: ' + RESET + truncate(s.firstUserMsg, 60) + '\\n';
|
|
2583
|
+
if (s.lastUserMsg && s.lastUserMsg !== s.firstUserMsg) {
|
|
2584
|
+
out += ' ' + DIM + 'Last input: ' + RESET + truncate(s.lastUserMsg, 60) + '\\n';
|
|
2585
|
+
}
|
|
2586
|
+
} else {
|
|
2587
|
+
out += prefix + title + DIM + ' (' + time + ')' + RESET + '\\n';
|
|
2588
|
+
}
|
|
2589
|
+
}
|
|
2590
|
+
|
|
2591
|
+
out += '\\n' + DIM + 'Page ' + (Math.floor(offset / pageSize) + 1) + '/' + Math.ceil(sessions.length / pageSize) + ' (' + sessions.length + ' sessions)' + RESET;
|
|
2592
|
+
|
|
2593
|
+
process.stdout.write(out);
|
|
2594
|
+
}
|
|
2595
|
+
|
|
2596
|
+
async function main() {
|
|
2597
|
+
const sessions = collectSessions();
|
|
2598
|
+
|
|
2599
|
+
if (sessions.length === 0) {
|
|
2600
|
+
console.log(RED + 'No sessions with interactions found in current directory' + RESET);
|
|
2601
|
+
process.exit(0);
|
|
2602
|
+
}
|
|
2603
|
+
|
|
2604
|
+
if (!process.stdin.isTTY) {
|
|
2605
|
+
for (const s of sessions) {
|
|
2606
|
+
console.log(s.id + ' ' + (s.title || '') + ' ' + formatTime(s.lastTimestamp));
|
|
2607
|
+
}
|
|
2608
|
+
process.exit(0);
|
|
2609
|
+
}
|
|
2610
|
+
|
|
2611
|
+
const rows = process.stdout.rows || 24;
|
|
2612
|
+
const pageSize = rows - 6;
|
|
2613
|
+
let selected = 0;
|
|
2614
|
+
let offset = 0;
|
|
2615
|
+
|
|
2616
|
+
process.stdin.setRawMode(true);
|
|
2617
|
+
process.stdin.resume();
|
|
2618
|
+
process.stdout.write(HIDE_CURSOR);
|
|
2619
|
+
|
|
2620
|
+
render(sessions, selected, offset, rows);
|
|
2621
|
+
|
|
2622
|
+
process.stdin.on('data', (key) => {
|
|
2623
|
+
const k = key.toString();
|
|
2624
|
+
|
|
2625
|
+
if (k === 'q' || k === '\\x03') { // q or Ctrl+C
|
|
2626
|
+
process.stdout.write(SHOW_CURSOR + CLEAR);
|
|
2627
|
+
process.exit(0);
|
|
2628
|
+
}
|
|
2629
|
+
|
|
2630
|
+
if (k === '\\r' || k === '\\n') { // Enter
|
|
2631
|
+
process.stdout.write(SHOW_CURSOR + CLEAR);
|
|
2632
|
+
const session = sessions[selected];
|
|
2633
|
+
console.log(GREEN + 'Resuming session: ' + session.id + RESET);
|
|
2634
|
+
console.log(DIM + 'Using: ' + ALIAS_NAME + ' --resume ' + session.id + RESET + '\\n');
|
|
2635
|
+
const child = spawn(ALIAS_NAME, ['--resume', session.id], { stdio: 'inherit' });
|
|
2636
|
+
child.on('exit', (code) => process.exit(code || 0));
|
|
2637
|
+
return;
|
|
2638
|
+
}
|
|
2639
|
+
|
|
2640
|
+
if (k === '\\x1b[A' || k === 'k') { // Up
|
|
2641
|
+
if (selected > 0) {
|
|
2642
|
+
selected--;
|
|
2643
|
+
if (selected < offset) offset = Math.max(0, offset - 1);
|
|
2644
|
+
}
|
|
2645
|
+
} else if (k === '\\x1b[B' || k === 'j') { // Down
|
|
2646
|
+
if (selected < sessions.length - 1) {
|
|
2647
|
+
selected++;
|
|
2648
|
+
if (selected >= offset + pageSize) offset++;
|
|
2649
|
+
}
|
|
2650
|
+
} else if (k === '\\x1b[5~') { // Page Up
|
|
2651
|
+
selected = Math.max(0, selected - pageSize);
|
|
2652
|
+
offset = Math.max(0, offset - pageSize);
|
|
2653
|
+
} else if (k === '\\x1b[6~') { // Page Down
|
|
2654
|
+
selected = Math.min(sessions.length - 1, selected + pageSize);
|
|
2655
|
+
offset = Math.min(Math.max(0, sessions.length - pageSize), offset + pageSize);
|
|
2656
|
+
}
|
|
2657
|
+
|
|
2658
|
+
render(sessions, selected, offset, rows);
|
|
2659
|
+
});
|
|
2660
|
+
|
|
2661
|
+
process.on('SIGINT', () => {
|
|
2662
|
+
process.stdout.write(SHOW_CURSOR + CLEAR);
|
|
2663
|
+
process.exit(0);
|
|
2664
|
+
});
|
|
2665
|
+
}
|
|
2666
|
+
|
|
2667
|
+
main();
|
|
2668
|
+
`;
|
|
2669
|
+
}
|
|
2670
|
+
/**
|
|
2671
|
+
* Create sessions browser script file
|
|
2672
|
+
*/
|
|
2673
|
+
async function createSessionsScript(outputDir, aliasName) {
|
|
2674
|
+
if (!existsSync(outputDir)) await mkdir(outputDir, { recursive: true });
|
|
2675
|
+
const sessionsScriptPath = join(outputDir, `${aliasName}-sessions.js`);
|
|
2676
|
+
await writeFile(sessionsScriptPath, generateSessionsBrowserScript(aliasName));
|
|
2677
|
+
await chmod(sessionsScriptPath, 493);
|
|
2678
|
+
return { sessionsScript: sessionsScriptPath };
|
|
2679
|
+
}
|
|
2680
|
+
|
|
2398
2681
|
//#endregion
|
|
2399
2682
|
//#region src/cli.ts
|
|
2400
2683
|
const __dirname = dirname(fileURLToPath(import.meta.url));
|
|
@@ -2447,13 +2730,14 @@ function findDefaultDroidPath() {
|
|
|
2447
2730
|
for (const p of paths) if (existsSync(p)) return p;
|
|
2448
2731
|
return join(home, ".droid", "bin", "droid");
|
|
2449
2732
|
}
|
|
2450
|
-
bin("droid-patch", "CLI tool to patch droid binary with various modifications").package("droid-patch", version).option("--is-custom", "Patch isCustom:!0 to isCustom:!1 (enable context compression for custom models)").option("--skip-login", "Inject a fake FACTORY_API_KEY to bypass login requirement (no real key needed)").option("--api-base <url>", "Replace API URL (standalone: binary patch, max 22 chars; with --websearch: proxy forward target, no limit)").option("--websearch", "Enable local WebSearch proxy (each instance runs own proxy, auto-cleanup on exit)").option("--statusline", "Enable a Claude-style statusline (terminal UI)").option("--standalone", "Standalone mode: mock non-LLM Factory APIs (use with --websearch)").option("--reasoning-effort", "Enable reasoning effort for custom models (set to high, enable UI selector)").option("--disable-telemetry", "Disable telemetry and Sentry error reporting (block data uploads)").option("--dry-run", "Verify patches without actually modifying the binary").option("-p, --path <path>", "Path to the droid binary").option("-o, --output <dir>", "Output directory for patched binary").option("--no-backup", "Do not create backup of original binary").option("-v, --verbose", "Enable verbose output").argument("[alias]", "Alias name for the patched binary").action(async (options, args) => {
|
|
2733
|
+
bin("droid-patch", "CLI tool to patch droid binary with various modifications").package("droid-patch", version).option("--is-custom", "Patch isCustom:!0 to isCustom:!1 (enable context compression for custom models)").option("--skip-login", "Inject a fake FACTORY_API_KEY to bypass login requirement (no real key needed)").option("--api-base <url>", "Replace API URL (standalone: binary patch, max 22 chars; with --websearch: proxy forward target, no limit)").option("--websearch", "Enable local WebSearch proxy (each instance runs own proxy, auto-cleanup on exit)").option("--statusline", "Enable a Claude-style statusline (terminal UI)").option("--sessions", "Enable sessions browser (--sessions flag in alias)").option("--standalone", "Standalone mode: mock non-LLM Factory APIs (use with --websearch)").option("--reasoning-effort", "Enable reasoning effort for custom models (set to high, enable UI selector)").option("--disable-telemetry", "Disable telemetry and Sentry error reporting (block data uploads)").option("--dry-run", "Verify patches without actually modifying the binary").option("-p, --path <path>", "Path to the droid binary").option("-o, --output <dir>", "Output directory for patched binary").option("--no-backup", "Do not create backup of original binary").option("-v, --verbose", "Enable verbose output").argument("[alias]", "Alias name for the patched binary").action(async (options, args) => {
|
|
2451
2734
|
const alias = args?.[0];
|
|
2452
2735
|
const isCustom = options["is-custom"];
|
|
2453
2736
|
const skipLogin = options["skip-login"];
|
|
2454
2737
|
const apiBase = options["api-base"];
|
|
2455
2738
|
const websearch = options["websearch"];
|
|
2456
2739
|
const statusline = options["statusline"];
|
|
2740
|
+
const sessions = options["sessions"];
|
|
2457
2741
|
const standalone = options["standalone"];
|
|
2458
2742
|
const websearchTarget = websearch ? apiBase || "https://api.factory.ai" : void 0;
|
|
2459
2743
|
const reasoningEffort = options["reasoning-effort"];
|
|
@@ -2488,7 +2772,10 @@ bin("droid-patch", "CLI tool to patch droid binary with various modifications").
|
|
|
2488
2772
|
execTargetPath = wrapperScript;
|
|
2489
2773
|
}
|
|
2490
2774
|
if (statusline) {
|
|
2491
|
-
const
|
|
2775
|
+
const statuslineDir = join(homedir(), ".droid-patch", "statusline");
|
|
2776
|
+
let sessionsScript;
|
|
2777
|
+
if (sessions) sessionsScript = (await createSessionsScript(statuslineDir, alias)).sessionsScript;
|
|
2778
|
+
const { wrapperScript } = await createStatuslineFiles(statuslineDir, execTargetPath, alias, sessionsScript);
|
|
2492
2779
|
execTargetPath = wrapperScript;
|
|
2493
2780
|
}
|
|
2494
2781
|
const aliasResult = await createAliasForWrapper(execTargetPath, alias, verbose);
|
|
@@ -2499,6 +2786,7 @@ bin("droid-patch", "CLI tool to patch droid binary with various modifications").
|
|
|
2499
2786
|
apiBase: apiBase || null,
|
|
2500
2787
|
websearch: !!websearch,
|
|
2501
2788
|
statusline: !!statusline,
|
|
2789
|
+
sessions: !!sessions,
|
|
2502
2790
|
reasoningEffort: false,
|
|
2503
2791
|
noTelemetry: false,
|
|
2504
2792
|
standalone
|
|
@@ -2694,7 +2982,10 @@ bin("droid-patch", "CLI tool to patch droid binary with various modifications").
|
|
|
2694
2982
|
if (standalone) console.log(styleText("white", ` Standalone mode: enabled`));
|
|
2695
2983
|
}
|
|
2696
2984
|
if (statusline) {
|
|
2697
|
-
const
|
|
2985
|
+
const statuslineDir = join(homedir(), ".droid-patch", "statusline");
|
|
2986
|
+
let sessionsScript;
|
|
2987
|
+
if (sessions) sessionsScript = (await createSessionsScript(statuslineDir, alias)).sessionsScript;
|
|
2988
|
+
const { wrapperScript } = await createStatuslineFiles(statuslineDir, execTargetPath, alias, sessionsScript);
|
|
2698
2989
|
execTargetPath = wrapperScript;
|
|
2699
2990
|
console.log();
|
|
2700
2991
|
console.log(styleText("cyan", "Statusline enabled"));
|
|
@@ -2709,6 +3000,7 @@ bin("droid-patch", "CLI tool to patch droid binary with various modifications").
|
|
|
2709
3000
|
apiBase: apiBase || null,
|
|
2710
3001
|
websearch: !!websearch,
|
|
2711
3002
|
statusline: !!statusline,
|
|
3003
|
+
sessions: !!sessions,
|
|
2712
3004
|
reasoningEffort: !!reasoningEffort,
|
|
2713
3005
|
noTelemetry: !!noTelemetry,
|
|
2714
3006
|
standalone: !!standalone
|
|
@@ -2925,7 +3217,10 @@ bin("droid-patch", "CLI tool to patch droid binary with various modifications").
|
|
|
2925
3217
|
}
|
|
2926
3218
|
}
|
|
2927
3219
|
if (meta.patches.statusline) {
|
|
2928
|
-
const
|
|
3220
|
+
const statuslineDir = join(homedir(), ".droid-patch", "statusline");
|
|
3221
|
+
let sessionsScript;
|
|
3222
|
+
if (meta.patches.sessions) sessionsScript = (await createSessionsScript(statuslineDir, meta.name)).sessionsScript;
|
|
3223
|
+
const { wrapperScript } = await createStatuslineFiles(statuslineDir, execTargetPath, meta.name, sessionsScript);
|
|
2929
3224
|
execTargetPath = wrapperScript;
|
|
2930
3225
|
if (verbose) console.log(styleText("gray", ` Regenerated statusline wrapper`));
|
|
2931
3226
|
}
|