threadnote 0.7.2 → 0.7.3
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/dist/threadnote.cjs +100 -50
- package/package.json +1 -1
package/dist/threadnote.cjs
CHANGED
|
@@ -3472,7 +3472,7 @@ var {
|
|
|
3472
3472
|
// src/constants.ts
|
|
3473
3473
|
var DEFAULT_HOST = "127.0.0.1";
|
|
3474
3474
|
var DEFAULT_PORT = 1933;
|
|
3475
|
-
var DEFAULT_OPENVIKING_VERSION = "0.3.
|
|
3475
|
+
var DEFAULT_OPENVIKING_VERSION = "0.3.21";
|
|
3476
3476
|
var DEFAULT_ACCOUNT = "local";
|
|
3477
3477
|
var DEFAULT_AGENT_ID = "threadnote";
|
|
3478
3478
|
var OPENVIKING_PACKAGE_NAME = "openviking[local-embed]";
|
|
@@ -3747,6 +3747,38 @@ async function sleep(ms) {
|
|
|
3747
3747
|
setTimeout(resolvePromise, ms);
|
|
3748
3748
|
});
|
|
3749
3749
|
}
|
|
3750
|
+
function compareVersions(a, b) {
|
|
3751
|
+
const left = parseVersion(a);
|
|
3752
|
+
const right = parseVersion(b);
|
|
3753
|
+
for (let index = 0; index < 3; index += 1) {
|
|
3754
|
+
const difference = left.numbers[index] - right.numbers[index];
|
|
3755
|
+
if (difference !== 0) {
|
|
3756
|
+
return difference;
|
|
3757
|
+
}
|
|
3758
|
+
}
|
|
3759
|
+
if (left.prerelease === right.prerelease) {
|
|
3760
|
+
return 0;
|
|
3761
|
+
}
|
|
3762
|
+
if (left.prerelease === void 0) {
|
|
3763
|
+
return 1;
|
|
3764
|
+
}
|
|
3765
|
+
if (right.prerelease === void 0) {
|
|
3766
|
+
return -1;
|
|
3767
|
+
}
|
|
3768
|
+
return left.prerelease.localeCompare(right.prerelease);
|
|
3769
|
+
}
|
|
3770
|
+
function parseVersion(version) {
|
|
3771
|
+
const normalized = version.trim().replace(/^v/, "");
|
|
3772
|
+
const [core2, prerelease] = normalized.split("-", 2);
|
|
3773
|
+
const parts = core2.split(".").map((part) => Number(part));
|
|
3774
|
+
return {
|
|
3775
|
+
numbers: [safeVersionNumber(parts[0]), safeVersionNumber(parts[1]), safeVersionNumber(parts[2])],
|
|
3776
|
+
prerelease
|
|
3777
|
+
};
|
|
3778
|
+
}
|
|
3779
|
+
function safeVersionNumber(value) {
|
|
3780
|
+
return typeof value === "number" && Number.isInteger(value) && value >= 0 ? value : 0;
|
|
3781
|
+
}
|
|
3750
3782
|
async function readHttpStatus(url, timeoutMs) {
|
|
3751
3783
|
return new Promise((resolvePromise) => {
|
|
3752
3784
|
const request = (0, import_node_http.get)(url, (response) => {
|
|
@@ -9279,7 +9311,7 @@ async function checkForThreadnoteUpdate(args) {
|
|
|
9279
9311
|
}
|
|
9280
9312
|
const cached = await readUpdateCache(args.cachePath);
|
|
9281
9313
|
if (cached && isCacheFresh(cached)) {
|
|
9282
|
-
return
|
|
9314
|
+
return compareVersions2(args.currentVersion, cached.latestVersion);
|
|
9283
9315
|
}
|
|
9284
9316
|
const fresh = await fetchLatestVersion();
|
|
9285
9317
|
if (fresh) {
|
|
@@ -9288,10 +9320,10 @@ async function checkForThreadnoteUpdate(args) {
|
|
|
9288
9320
|
latestVersion: fresh,
|
|
9289
9321
|
version: 1
|
|
9290
9322
|
});
|
|
9291
|
-
return
|
|
9323
|
+
return compareVersions2(args.currentVersion, fresh);
|
|
9292
9324
|
}
|
|
9293
9325
|
if (cached) {
|
|
9294
|
-
return
|
|
9326
|
+
return compareVersions2(args.currentVersion, cached.latestVersion);
|
|
9295
9327
|
}
|
|
9296
9328
|
return void 0;
|
|
9297
9329
|
}
|
|
@@ -9309,7 +9341,7 @@ function spawnDetachedAutoUpdate() {
|
|
|
9309
9341
|
} catch {
|
|
9310
9342
|
}
|
|
9311
9343
|
}
|
|
9312
|
-
function
|
|
9344
|
+
function compareVersions2(currentVersion, latestVersion) {
|
|
9313
9345
|
return {
|
|
9314
9346
|
currentVersion,
|
|
9315
9347
|
latestVersion,
|
|
@@ -9317,8 +9349,8 @@ function compareVersions(currentVersion, latestVersion) {
|
|
|
9317
9349
|
};
|
|
9318
9350
|
}
|
|
9319
9351
|
function isNewerVersion(candidate, baseline) {
|
|
9320
|
-
const candidateParts =
|
|
9321
|
-
const baselineParts =
|
|
9352
|
+
const candidateParts = parseVersion2(candidate);
|
|
9353
|
+
const baselineParts = parseVersion2(baseline);
|
|
9322
9354
|
for (let index = 0; index < 3; index += 1) {
|
|
9323
9355
|
if (candidateParts[index] !== baselineParts[index]) {
|
|
9324
9356
|
return candidateParts[index] > baselineParts[index];
|
|
@@ -9326,7 +9358,7 @@ function isNewerVersion(candidate, baseline) {
|
|
|
9326
9358
|
}
|
|
9327
9359
|
return false;
|
|
9328
9360
|
}
|
|
9329
|
-
function
|
|
9361
|
+
function parseVersion2(value) {
|
|
9330
9362
|
const parts = value.split(".").map((part) => parseInt(part, 10));
|
|
9331
9363
|
return [parts[0] || 0, parts[1] || 0, parts[2] || 0];
|
|
9332
9364
|
}
|
|
@@ -10044,7 +10076,7 @@ async function runUpdate(config, options) {
|
|
|
10044
10076
|
console.log(`Update available. Run: threadnote update`);
|
|
10045
10077
|
} else {
|
|
10046
10078
|
console.log(
|
|
10047
|
-
|
|
10079
|
+
compareVersions(info.currentVersion, info.latestVersion) > 0 ? "Current version is newer than npm latest." : "Threadnote is up to date."
|
|
10048
10080
|
);
|
|
10049
10081
|
}
|
|
10050
10082
|
return;
|
|
@@ -10091,10 +10123,16 @@ async function runPostUpdate(config, options) {
|
|
|
10091
10123
|
if (!options.fromVersion || !options.toVersion) {
|
|
10092
10124
|
throw new Error("Provide --from-version and --to-version for post-update.");
|
|
10093
10125
|
}
|
|
10126
|
+
const interactive = process.stdin.isTTY === true && process.stdout.isTTY === true;
|
|
10127
|
+
await ensurePinnedOpenVikingInstalled(config, {
|
|
10128
|
+
dryRun: options.dryRun === true,
|
|
10129
|
+
interactive,
|
|
10130
|
+
yes: options.yes === true
|
|
10131
|
+
});
|
|
10094
10132
|
await runApplicablePostUpdateMigrations(config, {
|
|
10095
10133
|
dryRun: options.dryRun === true,
|
|
10096
10134
|
fromVersion: options.fromVersion,
|
|
10097
|
-
interactive
|
|
10135
|
+
interactive,
|
|
10098
10136
|
markHandled: true,
|
|
10099
10137
|
toVersion: options.toVersion,
|
|
10100
10138
|
yes: options.yes === true
|
|
@@ -10102,6 +10140,8 @@ async function runPostUpdate(config, options) {
|
|
|
10102
10140
|
}
|
|
10103
10141
|
async function maybeRunPostUpdateAfterRepair(config, options) {
|
|
10104
10142
|
const toVersion = await currentPackageVersion();
|
|
10143
|
+
const interactive = process.stdin.isTTY === true && process.stdout.isTTY === true;
|
|
10144
|
+
await ensurePinnedOpenVikingInstalled(config, { dryRun: options.dryRun, interactive, yes: false });
|
|
10105
10145
|
const state = await readPostUpdateState(config);
|
|
10106
10146
|
const migrations = await applicablePostUpdateMigrations(config, {
|
|
10107
10147
|
fromVersion: "0.0.0",
|
|
@@ -10114,7 +10154,7 @@ async function maybeRunPostUpdateAfterRepair(config, options) {
|
|
|
10114
10154
|
console.log("");
|
|
10115
10155
|
console.log("Repair found package post-update migrations.");
|
|
10116
10156
|
console.log("This also covers updates launched by older Threadnote versions that only knew how to run repair.");
|
|
10117
|
-
if (
|
|
10157
|
+
if (!interactive) {
|
|
10118
10158
|
console.log(
|
|
10119
10159
|
"This process is non-interactive, so Threadnote will print the manual migration command instead of prompting."
|
|
10120
10160
|
);
|
|
@@ -10123,12 +10163,48 @@ async function maybeRunPostUpdateAfterRepair(config, options) {
|
|
|
10123
10163
|
await runApplicablePostUpdateMigrations(config, {
|
|
10124
10164
|
dryRun: options.dryRun,
|
|
10125
10165
|
fromVersion: "0.0.0",
|
|
10126
|
-
interactive
|
|
10166
|
+
interactive,
|
|
10127
10167
|
markHandled: true,
|
|
10128
10168
|
toVersion,
|
|
10129
10169
|
yes: false
|
|
10130
10170
|
});
|
|
10131
10171
|
}
|
|
10172
|
+
async function ensurePinnedOpenVikingInstalled(config, options) {
|
|
10173
|
+
const ov = await findExecutable(["ov", "openviking"]);
|
|
10174
|
+
if (!ov) {
|
|
10175
|
+
return;
|
|
10176
|
+
}
|
|
10177
|
+
const installedVersion = await readOpenVikingCliVersion(ov);
|
|
10178
|
+
if (!installedVersion) {
|
|
10179
|
+
console.log(`Could not detect OpenViking CLI version via \`${ov} version\`; skipping pinned-version check.`);
|
|
10180
|
+
return;
|
|
10181
|
+
}
|
|
10182
|
+
const pinned = config.openVikingVersion;
|
|
10183
|
+
if (compareVersions(installedVersion, pinned) >= 0) {
|
|
10184
|
+
return;
|
|
10185
|
+
}
|
|
10186
|
+
console.log("");
|
|
10187
|
+
console.log(`OpenViking ${installedVersion} is older than the pinned version ${pinned}.`);
|
|
10188
|
+
console.log(
|
|
10189
|
+
"Upgrading picks up upstream fixes for share-sync reliability (reindex lock acquisition, ov wait timeout)."
|
|
10190
|
+
);
|
|
10191
|
+
const threadnoteCommand = currentThreadnoteCommand() ?? await findExecutable([NPM_PACKAGE_NAME]) ?? NPM_PACKAGE_NAME;
|
|
10192
|
+
const installArgs = ["install", "--force", "--no-start"];
|
|
10193
|
+
const accepted = options.dryRun || options.yes || options.interactive && await confirmPostUpdateMigration(`Upgrade OpenViking to ${pinned} now? [Y/n] `, true);
|
|
10194
|
+
if (!accepted) {
|
|
10195
|
+
console.log(`Skipped. Run manually later: ${formatMigrationCommand(threadnoteCommand, installArgs)}`);
|
|
10196
|
+
return;
|
|
10197
|
+
}
|
|
10198
|
+
await maybeRun(options.dryRun, threadnoteCommand, installArgs);
|
|
10199
|
+
}
|
|
10200
|
+
async function readOpenVikingCliVersion(ov) {
|
|
10201
|
+
const result = await runCommand(ov, ["version"], { allowFailure: true });
|
|
10202
|
+
if (result.exitCode !== 0) {
|
|
10203
|
+
return void 0;
|
|
10204
|
+
}
|
|
10205
|
+
const match = result.stdout.match(/^\s*CLI:\s*(\S+)/m);
|
|
10206
|
+
return match ? match[1] : void 0;
|
|
10207
|
+
}
|
|
10132
10208
|
async function getUpdateInfo(config, options) {
|
|
10133
10209
|
const currentVersion = await currentPackageVersion();
|
|
10134
10210
|
const cached = options.preferFresh ? void 0 : await readFreshCache(config, options.registry);
|
|
@@ -10138,7 +10214,7 @@ async function getUpdateInfo(config, options) {
|
|
|
10138
10214
|
}
|
|
10139
10215
|
return {
|
|
10140
10216
|
currentVersion,
|
|
10141
|
-
isUpdateAvailable:
|
|
10217
|
+
isUpdateAvailable: compareVersions(currentVersion, latestVersion) < 0,
|
|
10142
10218
|
latestVersion,
|
|
10143
10219
|
registry: options.registry
|
|
10144
10220
|
};
|
|
@@ -10248,10 +10324,10 @@ async function applicablePostUpdateMigrations(config, options) {
|
|
|
10248
10324
|
if (handled.has(migration.id)) {
|
|
10249
10325
|
continue;
|
|
10250
10326
|
}
|
|
10251
|
-
if (
|
|
10327
|
+
if (compareVersions(options.fromVersion, migration.introducedIn) >= 0) {
|
|
10252
10328
|
continue;
|
|
10253
10329
|
}
|
|
10254
|
-
if (
|
|
10330
|
+
if (compareVersions(migration.introducedIn, options.toVersion) > 0) {
|
|
10255
10331
|
continue;
|
|
10256
10332
|
}
|
|
10257
10333
|
if (migration.requiresLegacyHandoffs === true && !await hasLegacyLifecycleHandoffCandidates(config)) {
|
|
@@ -10300,10 +10376,13 @@ function printPostUpdateMigration(migration) {
|
|
|
10300
10376
|
console.log(`- ${line}`);
|
|
10301
10377
|
}
|
|
10302
10378
|
}
|
|
10303
|
-
async function confirmPostUpdateMigration(prompt) {
|
|
10379
|
+
async function confirmPostUpdateMigration(prompt, defaultYes = false) {
|
|
10304
10380
|
const readline = (0, import_promises10.createInterface)({ input: import_node_process.stdin, output: import_node_process.stdout });
|
|
10305
10381
|
try {
|
|
10306
10382
|
const answer = (await readline.question(prompt)).trim().toLowerCase();
|
|
10383
|
+
if (answer === "") {
|
|
10384
|
+
return defaultYes;
|
|
10385
|
+
}
|
|
10307
10386
|
return answer === "y" || answer === "yes";
|
|
10308
10387
|
} finally {
|
|
10309
10388
|
readline.close();
|
|
@@ -10419,38 +10498,6 @@ function updateRegistry() {
|
|
|
10419
10498
|
function isUpdateNotificationDisabled() {
|
|
10420
10499
|
return process.env.CI !== void 0 || process.env.NO_UPDATE_NOTIFIER !== void 0 || process.env.THREADNOTE_NO_UPDATE_CHECK !== void 0;
|
|
10421
10500
|
}
|
|
10422
|
-
function compareVersions2(currentVersion, latestVersion) {
|
|
10423
|
-
const current = parseVersion2(currentVersion);
|
|
10424
|
-
const latest = parseVersion2(latestVersion);
|
|
10425
|
-
for (let index = 0; index < 3; index += 1) {
|
|
10426
|
-
const difference = current.numbers[index] - latest.numbers[index];
|
|
10427
|
-
if (difference !== 0) {
|
|
10428
|
-
return difference;
|
|
10429
|
-
}
|
|
10430
|
-
}
|
|
10431
|
-
if (current.prerelease === latest.prerelease) {
|
|
10432
|
-
return 0;
|
|
10433
|
-
}
|
|
10434
|
-
if (current.prerelease === void 0) {
|
|
10435
|
-
return 1;
|
|
10436
|
-
}
|
|
10437
|
-
if (latest.prerelease === void 0) {
|
|
10438
|
-
return -1;
|
|
10439
|
-
}
|
|
10440
|
-
return current.prerelease.localeCompare(latest.prerelease);
|
|
10441
|
-
}
|
|
10442
|
-
function parseVersion2(version) {
|
|
10443
|
-
const normalized = version.trim().replace(/^v/, "");
|
|
10444
|
-
const [core2, prerelease] = normalized.split("-", 2);
|
|
10445
|
-
const parts = core2.split(".").map((part) => Number(part));
|
|
10446
|
-
return {
|
|
10447
|
-
numbers: [safeVersionNumber(parts[0]), safeVersionNumber(parts[1]), safeVersionNumber(parts[2])],
|
|
10448
|
-
prerelease
|
|
10449
|
-
};
|
|
10450
|
-
}
|
|
10451
|
-
function safeVersionNumber(value) {
|
|
10452
|
-
return typeof value === "number" && Number.isInteger(value) && value >= 0 ? value : 0;
|
|
10453
|
-
}
|
|
10454
10501
|
|
|
10455
10502
|
// src/lifecycle.ts
|
|
10456
10503
|
async function runDoctor(config, options) {
|
|
@@ -10498,7 +10545,10 @@ async function runInstall(config, options) {
|
|
|
10498
10545
|
console.log(`OpenViking server already installed: ${serverPath}`);
|
|
10499
10546
|
const localEmbeddingMissing = await hasLocalEmbeddingDependency(serverPath) === false;
|
|
10500
10547
|
const pythonSystemCertificatesMissing = await hasPythonSystemCertificatesPatch(serverPath) === false;
|
|
10501
|
-
if (
|
|
10548
|
+
if (options.force === true) {
|
|
10549
|
+
console.log(`Reinstalling OpenViking at pinned version ${config.openVikingVersion} (--force).`);
|
|
10550
|
+
await runInstallCommands(config, options.packageManager, true, dryRun);
|
|
10551
|
+
} else if (localEmbeddingMissing) {
|
|
10502
10552
|
const repairReasons = [];
|
|
10503
10553
|
repairReasons.push("local embedding extra is missing");
|
|
10504
10554
|
if (pythonSystemCertificatesMissing) {
|
|
@@ -11414,7 +11464,7 @@ async function main() {
|
|
|
11414
11464
|
await runDoctor(config, options);
|
|
11415
11465
|
await maybeNotifyUpdate(config, { dryRun: options.dryRun === true });
|
|
11416
11466
|
});
|
|
11417
|
-
program2.command("install").description("Install OpenViking, local config files, command shim, and user-level agent instructions").option("--dry-run", "Print the actions without making changes").option("--no-start", "Do not start OpenViking or check server health after installing").option("--package-manager <manager>", "uv, pipx, or pip", parsePackageManager).option(
|
|
11467
|
+
program2.command("install").description("Install OpenViking, local config files, command shim, and user-level agent instructions").option("--dry-run", "Print the actions without making changes").option("--force", "Reinstall OpenViking at the pinned version even if a working install is already present").option("--no-start", "Do not start OpenViking or check server health after installing").option("--package-manager <manager>", "uv, pipx, or pip", parsePackageManager).option(
|
|
11418
11468
|
"--with-hooks",
|
|
11419
11469
|
"Also install agent-side hooks (Claude PreCompact + SessionStart) for deterministic handoff snapshots and context preload"
|
|
11420
11470
|
).action(async (options) => {
|