@metaphi-ai/hum 0.1.26 → 0.1.30
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/cli.mjs +1124 -474
- package/dist/install.mjs +119 -0
- package/package.json +1 -1
- package/scripts/postinstall.js +10 -51
package/dist/cli.mjs
CHANGED
|
@@ -1257,26 +1257,26 @@ var require_react_development = __commonJS({
|
|
|
1257
1257
|
}
|
|
1258
1258
|
return lazyType;
|
|
1259
1259
|
}
|
|
1260
|
-
function forwardRef3(
|
|
1260
|
+
function forwardRef3(render3) {
|
|
1261
1261
|
{
|
|
1262
|
-
if (
|
|
1262
|
+
if (render3 != null && render3.$$typeof === REACT_MEMO_TYPE) {
|
|
1263
1263
|
error("forwardRef requires a render function but received a `memo` component. Instead of forwardRef(memo(...)), use memo(forwardRef(...)).");
|
|
1264
|
-
} else if (typeof
|
|
1265
|
-
error("forwardRef requires a render function but was given %s.",
|
|
1264
|
+
} else if (typeof render3 !== "function") {
|
|
1265
|
+
error("forwardRef requires a render function but was given %s.", render3 === null ? "null" : typeof render3);
|
|
1266
1266
|
} else {
|
|
1267
|
-
if (
|
|
1268
|
-
error("forwardRef render functions accept exactly two parameters: props and ref. %s",
|
|
1267
|
+
if (render3.length !== 0 && render3.length !== 2) {
|
|
1268
|
+
error("forwardRef render functions accept exactly two parameters: props and ref. %s", render3.length === 1 ? "Did you forget to use the ref parameter?" : "Any additional parameter will be undefined.");
|
|
1269
1269
|
}
|
|
1270
1270
|
}
|
|
1271
|
-
if (
|
|
1272
|
-
if (
|
|
1271
|
+
if (render3 != null) {
|
|
1272
|
+
if (render3.defaultProps != null || render3.propTypes != null) {
|
|
1273
1273
|
error("forwardRef render functions do not support propTypes or defaultProps. Did you accidentally pass a React component?");
|
|
1274
1274
|
}
|
|
1275
1275
|
}
|
|
1276
1276
|
}
|
|
1277
1277
|
var elementType = {
|
|
1278
1278
|
$$typeof: REACT_FORWARD_REF_TYPE,
|
|
1279
|
-
render:
|
|
1279
|
+
render: render3
|
|
1280
1280
|
};
|
|
1281
1281
|
{
|
|
1282
1282
|
var ownName;
|
|
@@ -1288,8 +1288,8 @@ var require_react_development = __commonJS({
|
|
|
1288
1288
|
},
|
|
1289
1289
|
set: function(name) {
|
|
1290
1290
|
ownName = name;
|
|
1291
|
-
if (!
|
|
1292
|
-
|
|
1291
|
+
if (!render3.name && !render3.displayName) {
|
|
1292
|
+
render3.displayName = name;
|
|
1293
1293
|
}
|
|
1294
1294
|
}
|
|
1295
1295
|
});
|
|
@@ -2249,7 +2249,7 @@ var require_signal_exit = __commonJS({
|
|
|
2249
2249
|
} else {
|
|
2250
2250
|
assert = __require("assert");
|
|
2251
2251
|
signals = require_signals();
|
|
2252
|
-
|
|
2252
|
+
isWin2 = /^win/i.test(process13.platform);
|
|
2253
2253
|
EE = __require("events");
|
|
2254
2254
|
if (typeof EE !== "function") {
|
|
2255
2255
|
EE = EE.EventEmitter;
|
|
@@ -2321,7 +2321,7 @@ var require_signal_exit = __commonJS({
|
|
|
2321
2321
|
unload();
|
|
2322
2322
|
emit("exit", null, sig);
|
|
2323
2323
|
emit("afterexit", null, sig);
|
|
2324
|
-
if (
|
|
2324
|
+
if (isWin2 && sig === "SIGHUP") {
|
|
2325
2325
|
sig = "SIGINT";
|
|
2326
2326
|
}
|
|
2327
2327
|
process13.kill(process13.pid, sig);
|
|
@@ -2378,7 +2378,7 @@ var require_signal_exit = __commonJS({
|
|
|
2378
2378
|
}
|
|
2379
2379
|
var assert;
|
|
2380
2380
|
var signals;
|
|
2381
|
-
var
|
|
2381
|
+
var isWin2;
|
|
2382
2382
|
var EE;
|
|
2383
2383
|
var emitter;
|
|
2384
2384
|
var unload;
|
|
@@ -13104,7 +13104,7 @@ var require_react_reconciler_development = __commonJS({
|
|
|
13104
13104
|
}
|
|
13105
13105
|
function pushStoreConsistencyCheck(fiber, getSnapshot, renderedSnapshot) {
|
|
13106
13106
|
fiber.flags |= StoreConsistency;
|
|
13107
|
-
var
|
|
13107
|
+
var check2 = {
|
|
13108
13108
|
getSnapshot,
|
|
13109
13109
|
value: renderedSnapshot
|
|
13110
13110
|
};
|
|
@@ -13112,13 +13112,13 @@ var require_react_reconciler_development = __commonJS({
|
|
|
13112
13112
|
if (componentUpdateQueue === null) {
|
|
13113
13113
|
componentUpdateQueue = createFunctionComponentUpdateQueue();
|
|
13114
13114
|
currentlyRenderingFiber$1.updateQueue = componentUpdateQueue;
|
|
13115
|
-
componentUpdateQueue.stores = [
|
|
13115
|
+
componentUpdateQueue.stores = [check2];
|
|
13116
13116
|
} else {
|
|
13117
13117
|
var stores = componentUpdateQueue.stores;
|
|
13118
13118
|
if (stores === null) {
|
|
13119
|
-
componentUpdateQueue.stores = [
|
|
13119
|
+
componentUpdateQueue.stores = [check2];
|
|
13120
13120
|
} else {
|
|
13121
|
-
stores.push(
|
|
13121
|
+
stores.push(check2);
|
|
13122
13122
|
}
|
|
13123
13123
|
}
|
|
13124
13124
|
}
|
|
@@ -15465,7 +15465,7 @@ var require_react_reconciler_development = __commonJS({
|
|
|
15465
15465
|
}
|
|
15466
15466
|
}
|
|
15467
15467
|
}
|
|
15468
|
-
var
|
|
15468
|
+
var render3 = Component.render;
|
|
15469
15469
|
var ref = workInProgress2.ref;
|
|
15470
15470
|
var nextChildren;
|
|
15471
15471
|
var hasId;
|
|
@@ -15476,12 +15476,12 @@ var require_react_reconciler_development = __commonJS({
|
|
|
15476
15476
|
{
|
|
15477
15477
|
ReactCurrentOwner$1.current = workInProgress2;
|
|
15478
15478
|
setIsRendering(true);
|
|
15479
|
-
nextChildren = renderWithHooks(current2, workInProgress2,
|
|
15479
|
+
nextChildren = renderWithHooks(current2, workInProgress2, render3, nextProps, ref, renderLanes2);
|
|
15480
15480
|
hasId = checkDidRenderIdHook();
|
|
15481
15481
|
if (workInProgress2.mode & StrictLegacyMode) {
|
|
15482
15482
|
setIsStrictModeForDevtools(true);
|
|
15483
15483
|
try {
|
|
15484
|
-
nextChildren = renderWithHooks(current2, workInProgress2,
|
|
15484
|
+
nextChildren = renderWithHooks(current2, workInProgress2, render3, nextProps, ref, renderLanes2);
|
|
15485
15485
|
hasId = checkDidRenderIdHook();
|
|
15486
15486
|
} finally {
|
|
15487
15487
|
setIsStrictModeForDevtools(false);
|
|
@@ -16661,7 +16661,7 @@ var require_react_reconciler_development = __commonJS({
|
|
|
16661
16661
|
}
|
|
16662
16662
|
}
|
|
16663
16663
|
}
|
|
16664
|
-
function initSuspenseListRenderState(workInProgress2, isBackwards,
|
|
16664
|
+
function initSuspenseListRenderState(workInProgress2, isBackwards, tail3, lastContentRow, tailMode) {
|
|
16665
16665
|
var renderState = workInProgress2.memoizedState;
|
|
16666
16666
|
if (renderState === null) {
|
|
16667
16667
|
workInProgress2.memoizedState = {
|
|
@@ -16669,7 +16669,7 @@ var require_react_reconciler_development = __commonJS({
|
|
|
16669
16669
|
rendering: null,
|
|
16670
16670
|
renderingStartTime: 0,
|
|
16671
16671
|
last: lastContentRow,
|
|
16672
|
-
tail:
|
|
16672
|
+
tail: tail3,
|
|
16673
16673
|
tailMode
|
|
16674
16674
|
};
|
|
16675
16675
|
} else {
|
|
@@ -16677,7 +16677,7 @@ var require_react_reconciler_development = __commonJS({
|
|
|
16677
16677
|
renderState.rendering = null;
|
|
16678
16678
|
renderState.renderingStartTime = 0;
|
|
16679
16679
|
renderState.last = lastContentRow;
|
|
16680
|
-
renderState.tail =
|
|
16680
|
+
renderState.tail = tail3;
|
|
16681
16681
|
renderState.tailMode = tailMode;
|
|
16682
16682
|
}
|
|
16683
16683
|
}
|
|
@@ -16709,19 +16709,19 @@ var require_react_reconciler_development = __commonJS({
|
|
|
16709
16709
|
switch (revealOrder) {
|
|
16710
16710
|
case "forwards": {
|
|
16711
16711
|
var lastContentRow = findLastContentRow(workInProgress2.child);
|
|
16712
|
-
var
|
|
16712
|
+
var tail3;
|
|
16713
16713
|
if (lastContentRow === null) {
|
|
16714
|
-
|
|
16714
|
+
tail3 = workInProgress2.child;
|
|
16715
16715
|
workInProgress2.child = null;
|
|
16716
16716
|
} else {
|
|
16717
|
-
|
|
16717
|
+
tail3 = lastContentRow.sibling;
|
|
16718
16718
|
lastContentRow.sibling = null;
|
|
16719
16719
|
}
|
|
16720
16720
|
initSuspenseListRenderState(
|
|
16721
16721
|
workInProgress2,
|
|
16722
16722
|
false,
|
|
16723
16723
|
// isBackwards
|
|
16724
|
-
|
|
16724
|
+
tail3,
|
|
16725
16725
|
lastContentRow,
|
|
16726
16726
|
tailMode
|
|
16727
16727
|
);
|
|
@@ -16835,9 +16835,9 @@ var require_react_reconciler_development = __commonJS({
|
|
|
16835
16835
|
}
|
|
16836
16836
|
}
|
|
16837
16837
|
var newProps = workInProgress2.pendingProps;
|
|
16838
|
-
var
|
|
16838
|
+
var render3 = newProps.children;
|
|
16839
16839
|
{
|
|
16840
|
-
if (typeof
|
|
16840
|
+
if (typeof render3 !== "function") {
|
|
16841
16841
|
error("A context consumer was rendered with multiple children, or a child that isn't a function. A context consumer expects a single child that is a function. If you did pass a function, make sure there is no trailing or leading whitespace around it.");
|
|
16842
16842
|
}
|
|
16843
16843
|
}
|
|
@@ -16850,7 +16850,7 @@ var require_react_reconciler_development = __commonJS({
|
|
|
16850
16850
|
{
|
|
16851
16851
|
ReactCurrentOwner$1.current = workInProgress2;
|
|
16852
16852
|
setIsRendering(true);
|
|
16853
|
-
newChildren =
|
|
16853
|
+
newChildren = render3(newValue);
|
|
16854
16854
|
setIsRendering(false);
|
|
16855
16855
|
}
|
|
16856
16856
|
{
|
|
@@ -20619,9 +20619,9 @@ var require_react_reconciler_development = __commonJS({
|
|
|
20619
20619
|
var checks = updateQueue.stores;
|
|
20620
20620
|
if (checks !== null) {
|
|
20621
20621
|
for (var i = 0; i < checks.length; i++) {
|
|
20622
|
-
var
|
|
20623
|
-
var getSnapshot =
|
|
20624
|
-
var renderedValue =
|
|
20622
|
+
var check2 = checks[i];
|
|
20623
|
+
var getSnapshot = check2.getSnapshot;
|
|
20624
|
+
var renderedValue = check2.value;
|
|
20625
20625
|
try {
|
|
20626
20626
|
if (!objectIs(getSnapshot(), renderedValue)) {
|
|
20627
20627
|
return false;
|
|
@@ -22744,10 +22744,10 @@ var require_react_reconciler_development = __commonJS({
|
|
|
22744
22744
|
var setErrorHandler = null;
|
|
22745
22745
|
var setSuspenseHandler = null;
|
|
22746
22746
|
{
|
|
22747
|
-
var copyWithDeleteImpl = function(obj,
|
|
22748
|
-
var key =
|
|
22747
|
+
var copyWithDeleteImpl = function(obj, path6, index2) {
|
|
22748
|
+
var key = path6[index2];
|
|
22749
22749
|
var updated = isArray(obj) ? obj.slice() : assign({}, obj);
|
|
22750
|
-
if (index2 + 1 ===
|
|
22750
|
+
if (index2 + 1 === path6.length) {
|
|
22751
22751
|
if (isArray(updated)) {
|
|
22752
22752
|
updated.splice(key, 1);
|
|
22753
22753
|
} else {
|
|
@@ -22755,11 +22755,11 @@ var require_react_reconciler_development = __commonJS({
|
|
|
22755
22755
|
}
|
|
22756
22756
|
return updated;
|
|
22757
22757
|
}
|
|
22758
|
-
updated[key] = copyWithDeleteImpl(obj[key],
|
|
22758
|
+
updated[key] = copyWithDeleteImpl(obj[key], path6, index2 + 1);
|
|
22759
22759
|
return updated;
|
|
22760
22760
|
};
|
|
22761
|
-
var copyWithDelete = function(obj,
|
|
22762
|
-
return copyWithDeleteImpl(obj,
|
|
22761
|
+
var copyWithDelete = function(obj, path6) {
|
|
22762
|
+
return copyWithDeleteImpl(obj, path6, 0);
|
|
22763
22763
|
};
|
|
22764
22764
|
var copyWithRenameImpl = function(obj, oldPath, newPath, index2) {
|
|
22765
22765
|
var oldKey = oldPath[index2];
|
|
@@ -22797,17 +22797,17 @@ var require_react_reconciler_development = __commonJS({
|
|
|
22797
22797
|
}
|
|
22798
22798
|
return copyWithRenameImpl(obj, oldPath, newPath, 0);
|
|
22799
22799
|
};
|
|
22800
|
-
var copyWithSetImpl = function(obj,
|
|
22801
|
-
if (index2 >=
|
|
22800
|
+
var copyWithSetImpl = function(obj, path6, index2, value) {
|
|
22801
|
+
if (index2 >= path6.length) {
|
|
22802
22802
|
return value;
|
|
22803
22803
|
}
|
|
22804
|
-
var key =
|
|
22804
|
+
var key = path6[index2];
|
|
22805
22805
|
var updated = isArray(obj) ? obj.slice() : assign({}, obj);
|
|
22806
|
-
updated[key] = copyWithSetImpl(obj[key],
|
|
22806
|
+
updated[key] = copyWithSetImpl(obj[key], path6, index2 + 1, value);
|
|
22807
22807
|
return updated;
|
|
22808
22808
|
};
|
|
22809
|
-
var copyWithSet = function(obj,
|
|
22810
|
-
return copyWithSetImpl(obj,
|
|
22809
|
+
var copyWithSet = function(obj, path6, value) {
|
|
22810
|
+
return copyWithSetImpl(obj, path6, 0, value);
|
|
22811
22811
|
};
|
|
22812
22812
|
var findHook = function(fiber, id) {
|
|
22813
22813
|
var currentHook2 = fiber.memoizedState;
|
|
@@ -22817,10 +22817,10 @@ var require_react_reconciler_development = __commonJS({
|
|
|
22817
22817
|
}
|
|
22818
22818
|
return currentHook2;
|
|
22819
22819
|
};
|
|
22820
|
-
overrideHookState = function(fiber, id,
|
|
22820
|
+
overrideHookState = function(fiber, id, path6, value) {
|
|
22821
22821
|
var hook = findHook(fiber, id);
|
|
22822
22822
|
if (hook !== null) {
|
|
22823
|
-
var newState = copyWithSet(hook.memoizedState,
|
|
22823
|
+
var newState = copyWithSet(hook.memoizedState, path6, value);
|
|
22824
22824
|
hook.memoizedState = newState;
|
|
22825
22825
|
hook.baseState = newState;
|
|
22826
22826
|
fiber.memoizedProps = assign({}, fiber.memoizedProps);
|
|
@@ -22830,10 +22830,10 @@ var require_react_reconciler_development = __commonJS({
|
|
|
22830
22830
|
}
|
|
22831
22831
|
}
|
|
22832
22832
|
};
|
|
22833
|
-
overrideHookStateDeletePath = function(fiber, id,
|
|
22833
|
+
overrideHookStateDeletePath = function(fiber, id, path6) {
|
|
22834
22834
|
var hook = findHook(fiber, id);
|
|
22835
22835
|
if (hook !== null) {
|
|
22836
|
-
var newState = copyWithDelete(hook.memoizedState,
|
|
22836
|
+
var newState = copyWithDelete(hook.memoizedState, path6);
|
|
22837
22837
|
hook.memoizedState = newState;
|
|
22838
22838
|
hook.baseState = newState;
|
|
22839
22839
|
fiber.memoizedProps = assign({}, fiber.memoizedProps);
|
|
@@ -22856,8 +22856,8 @@ var require_react_reconciler_development = __commonJS({
|
|
|
22856
22856
|
}
|
|
22857
22857
|
}
|
|
22858
22858
|
};
|
|
22859
|
-
overrideProps = function(fiber,
|
|
22860
|
-
fiber.pendingProps = copyWithSet(fiber.memoizedProps,
|
|
22859
|
+
overrideProps = function(fiber, path6, value) {
|
|
22860
|
+
fiber.pendingProps = copyWithSet(fiber.memoizedProps, path6, value);
|
|
22861
22861
|
if (fiber.alternate) {
|
|
22862
22862
|
fiber.alternate.pendingProps = fiber.pendingProps;
|
|
22863
22863
|
}
|
|
@@ -22866,8 +22866,8 @@ var require_react_reconciler_development = __commonJS({
|
|
|
22866
22866
|
scheduleUpdateOnFiber(root, fiber, SyncLane, NoTimestamp);
|
|
22867
22867
|
}
|
|
22868
22868
|
};
|
|
22869
|
-
overridePropsDeletePath = function(fiber,
|
|
22870
|
-
fiber.pendingProps = copyWithDelete(fiber.memoizedProps,
|
|
22869
|
+
overridePropsDeletePath = function(fiber, path6) {
|
|
22870
|
+
fiber.pendingProps = copyWithDelete(fiber.memoizedProps, path6);
|
|
22871
22871
|
if (fiber.alternate) {
|
|
22872
22872
|
fiber.alternate.pendingProps = fiber.pendingProps;
|
|
22873
22873
|
}
|
|
@@ -29446,7 +29446,7 @@ var require_has_flag = __commonJS({
|
|
|
29446
29446
|
var require_supports_colors = __commonJS({
|
|
29447
29447
|
"node_modules/@colors/colors/lib/system/supports-colors.js"(exports, module) {
|
|
29448
29448
|
"use strict";
|
|
29449
|
-
var
|
|
29449
|
+
var os8 = __require("os");
|
|
29450
29450
|
var hasFlag2 = require_has_flag();
|
|
29451
29451
|
var env3 = process.env;
|
|
29452
29452
|
var forceColor = void 0;
|
|
@@ -29484,7 +29484,7 @@ var require_supports_colors = __commonJS({
|
|
|
29484
29484
|
}
|
|
29485
29485
|
var min = forceColor ? 1 : 0;
|
|
29486
29486
|
if (process.platform === "win32") {
|
|
29487
|
-
var osRelease =
|
|
29487
|
+
var osRelease = os8.release().split(".");
|
|
29488
29488
|
if (Number(process.versions.node.split(".")[0]) >= 8 && Number(osRelease[0]) >= 10 && Number(osRelease[2]) >= 10586) {
|
|
29489
29489
|
return Number(osRelease[2]) >= 14931 ? 3 : 2;
|
|
29490
29490
|
}
|
|
@@ -31587,7 +31587,7 @@ var require_core = __commonJS({
|
|
|
31587
31587
|
function close(node) {
|
|
31588
31588
|
result += "</" + tag2(node) + ">";
|
|
31589
31589
|
}
|
|
31590
|
-
function
|
|
31590
|
+
function render3(event) {
|
|
31591
31591
|
(event.event === "start" ? open : close)(event.node);
|
|
31592
31592
|
}
|
|
31593
31593
|
while (original.length || highlighted.length) {
|
|
@@ -31597,7 +31597,7 @@ var require_core = __commonJS({
|
|
|
31597
31597
|
if (stream === original) {
|
|
31598
31598
|
nodeStack.reverse().forEach(close);
|
|
31599
31599
|
do {
|
|
31600
|
-
|
|
31600
|
+
render3(stream.splice(0, 1)[0]);
|
|
31601
31601
|
stream = selectStream();
|
|
31602
31602
|
} while (stream === original && stream.length && stream[0].offset === processed);
|
|
31603
31603
|
nodeStack.reverse().forEach(open);
|
|
@@ -31607,7 +31607,7 @@ var require_core = __commonJS({
|
|
|
31607
31607
|
} else {
|
|
31608
31608
|
nodeStack.pop();
|
|
31609
31609
|
}
|
|
31610
|
-
|
|
31610
|
+
render3(stream.splice(0, 1)[0]);
|
|
31611
31611
|
}
|
|
31612
31612
|
}
|
|
31613
31613
|
return result + escapeHTML(value.substr(processed));
|
|
@@ -73569,15 +73569,15 @@ var require_route = __commonJS({
|
|
|
73569
73569
|
};
|
|
73570
73570
|
}
|
|
73571
73571
|
function wrapConversion(toModel, graph) {
|
|
73572
|
-
const
|
|
73572
|
+
const path6 = [graph[toModel].parent, toModel];
|
|
73573
73573
|
let fn = conversions[graph[toModel].parent][toModel];
|
|
73574
73574
|
let cur = graph[toModel].parent;
|
|
73575
73575
|
while (graph[cur].parent) {
|
|
73576
|
-
|
|
73576
|
+
path6.unshift(graph[cur].parent);
|
|
73577
73577
|
fn = link3(conversions[graph[cur].parent][cur], fn);
|
|
73578
73578
|
cur = graph[cur].parent;
|
|
73579
73579
|
}
|
|
73580
|
-
fn.conversion =
|
|
73580
|
+
fn.conversion = path6;
|
|
73581
73581
|
return fn;
|
|
73582
73582
|
}
|
|
73583
73583
|
module.exports = function(fromModel) {
|
|
@@ -73817,7 +73817,7 @@ var require_has_flag2 = __commonJS({
|
|
|
73817
73817
|
var require_supports_color = __commonJS({
|
|
73818
73818
|
"node_modules/supports-color/index.js"(exports, module) {
|
|
73819
73819
|
"use strict";
|
|
73820
|
-
var
|
|
73820
|
+
var os8 = __require("os");
|
|
73821
73821
|
var tty2 = __require("tty");
|
|
73822
73822
|
var hasFlag2 = require_has_flag2();
|
|
73823
73823
|
var { env: env3 } = process;
|
|
@@ -73865,7 +73865,7 @@ var require_supports_color = __commonJS({
|
|
|
73865
73865
|
return min;
|
|
73866
73866
|
}
|
|
73867
73867
|
if (process.platform === "win32") {
|
|
73868
|
-
const osRelease =
|
|
73868
|
+
const osRelease = os8.release().split(".");
|
|
73869
73869
|
if (Number(osRelease[0]) >= 10 && Number(osRelease[2]) >= 10586) {
|
|
73870
73870
|
return Number(osRelease[2]) >= 14931 ? 3 : 2;
|
|
73871
73871
|
}
|
|
@@ -74575,6 +74575,246 @@ var require_dist = __commonJS({
|
|
|
74575
74575
|
}
|
|
74576
74576
|
});
|
|
74577
74577
|
|
|
74578
|
+
// src/install.js
|
|
74579
|
+
import { spawnSync } from "node:child_process";
|
|
74580
|
+
import fs2 from "node:fs";
|
|
74581
|
+
import os3 from "node:os";
|
|
74582
|
+
import path from "node:path";
|
|
74583
|
+
function importedVersion(env3 = process.env, runImpl = run) {
|
|
74584
|
+
const r = runImpl(enginePython(env3), ASK_VERSION);
|
|
74585
|
+
return r && r.status === 0 ? String(r.stdout).trim() : null;
|
|
74586
|
+
}
|
|
74587
|
+
function installedVersion(env3 = process.env, runImpl = run) {
|
|
74588
|
+
try {
|
|
74589
|
+
return fs2.readFileSync(stampPath(env3), "utf8").trim() || null;
|
|
74590
|
+
} catch {
|
|
74591
|
+
}
|
|
74592
|
+
if (!fs2.existsSync(enginePython(env3))) return null;
|
|
74593
|
+
const v = importedVersion(env3, runImpl);
|
|
74594
|
+
if (v) {
|
|
74595
|
+
try {
|
|
74596
|
+
fs2.writeFileSync(stampPath(env3), `${v}
|
|
74597
|
+
`);
|
|
74598
|
+
} catch {
|
|
74599
|
+
}
|
|
74600
|
+
}
|
|
74601
|
+
return v;
|
|
74602
|
+
}
|
|
74603
|
+
function needsInstall(version, { env: env3 = process.env, installed = () => installedVersion(env3), now = Date.now(), state = readInstallState(env3) } = {}) {
|
|
74604
|
+
if (!version || env3.HUM_ENGINE || env3.HUM_ENGINE_PORT) return false;
|
|
74605
|
+
if (installed() === version) return false;
|
|
74606
|
+
if (state && !state.ok && state.version === version && now - (state.at || 0) < 10 * 60 * 1e3) return false;
|
|
74607
|
+
return true;
|
|
74608
|
+
}
|
|
74609
|
+
function installEngine(version, { env: env3 = process.env, say = (m) => console.log(`hum: ${m}`), runImpl = run, now = Date.now() } = {}) {
|
|
74610
|
+
const home = humHome(env3);
|
|
74611
|
+
const dir = engineDir(env3);
|
|
74612
|
+
const python = enginePython(env3);
|
|
74613
|
+
const localBin = path.join(os3.homedir(), ".local", "bin");
|
|
74614
|
+
const uvNames = ["uv", path.join(localBin, win ? "uv.exe" : "uv")];
|
|
74615
|
+
const uv = () => uvNames.find((u) => {
|
|
74616
|
+
const r = runImpl(u, ["--version"]);
|
|
74617
|
+
return r && r.status === 0;
|
|
74618
|
+
});
|
|
74619
|
+
const spec = env3.HUM_ENGINE_SPEC || `hum-cli==${version}`;
|
|
74620
|
+
const outcome = (ok, error = null, got = version) => {
|
|
74621
|
+
writeInstallState({ version: got, wanted: version, ok, error, at: now }, env3);
|
|
74622
|
+
return { ok, version: got, error };
|
|
74623
|
+
};
|
|
74624
|
+
try {
|
|
74625
|
+
let u = uv();
|
|
74626
|
+
if (!u) {
|
|
74627
|
+
say("installing uv (it creates the Python environment for the part of hum that does the work) \u2026");
|
|
74628
|
+
const r = win ? runImpl("powershell", ["-ExecutionPolicy", "ByPass", "-c", "irm https://astral.sh/uv/install.ps1 | iex"], { stdio: "inherit" }) : runImpl("sh", ["-c", "curl -LsSf https://astral.sh/uv/install.sh | sh"], { stdio: "inherit" });
|
|
74629
|
+
u = r && r.status === 0 ? uv() : null;
|
|
74630
|
+
if (!u) return outcome(false, `could not install uv; install it from https://astral.sh/uv and run: ${npmFix(version)}`);
|
|
74631
|
+
}
|
|
74632
|
+
say(`installing ${env3.HUM_ENGINE_SPEC ? spec : `hum ${version}`} into ${dir} \u2026`);
|
|
74633
|
+
fs2.mkdirSync(home, { recursive: true });
|
|
74634
|
+
try {
|
|
74635
|
+
fs2.unlinkSync(stampPath(env3));
|
|
74636
|
+
} catch {
|
|
74637
|
+
}
|
|
74638
|
+
if (!fs2.existsSync(python)) {
|
|
74639
|
+
const args2 = ["venv", "--quiet", "--python", "3.12", ...fs2.existsSync(dir) ? ["--clear"] : [], dir];
|
|
74640
|
+
if ((runImpl(u, args2, { stdio: "inherit" }) || {}).status !== 0) return outcome(false, "uv venv failed");
|
|
74641
|
+
}
|
|
74642
|
+
if ((runImpl(u, ["pip", "install", "--quiet", "--python", python, spec], { stdio: "inherit" }) || {}).status !== 0) return outcome(false, `uv pip install ${spec} failed`);
|
|
74643
|
+
const got = importedVersion(env3, runImpl);
|
|
74644
|
+
if (!got) return outcome(false, "hum did not import after the install");
|
|
74645
|
+
if (got !== version && !env3.HUM_ENGINE_SPEC) return outcome(false, `installed ${got}, wanted ${version}`, got);
|
|
74646
|
+
fs2.mkdirSync(dir, { recursive: true });
|
|
74647
|
+
fs2.writeFileSync(stampPath(env3), `${got}
|
|
74648
|
+
`);
|
|
74649
|
+
const list2 = runImpl(u, ["tool", "list"]);
|
|
74650
|
+
if (list2 && list2.status === 0 && /^hum-cli\b/m.test(list2.stdout)) {
|
|
74651
|
+
const rm = runImpl(u, ["tool", "uninstall", "hum-cli"]);
|
|
74652
|
+
if (rm && rm.status === 0) say(`removed the uv install of hum-cli and its shims in ${localBin}; hum lives in ${dir} now`);
|
|
74653
|
+
}
|
|
74654
|
+
say(`hum ${got} ready`);
|
|
74655
|
+
return outcome(true, null, got);
|
|
74656
|
+
} catch (e) {
|
|
74657
|
+
return outcome(false, e && e.message ? e.message : String(e));
|
|
74658
|
+
}
|
|
74659
|
+
}
|
|
74660
|
+
var win, npmFix, NPM_FIX, humHome, engineDir, enginePython, stampPath, statePath, run, ASK_VERSION, readInstallState, writeInstallState;
|
|
74661
|
+
var init_install = __esm({
|
|
74662
|
+
"src/install.js"() {
|
|
74663
|
+
win = process.platform === "win32";
|
|
74664
|
+
npmFix = (version = "") => `npm i -g @metaphi-ai/hum@${version || "latest"} --foreground-scripts`;
|
|
74665
|
+
NPM_FIX = npmFix("latest");
|
|
74666
|
+
humHome = (env3 = process.env) => env3.HUM_HOME || path.join(os3.homedir(), ".hum");
|
|
74667
|
+
engineDir = (env3 = process.env) => path.join(humHome(env3), "engine");
|
|
74668
|
+
enginePython = (env3 = process.env) => win ? path.join(engineDir(env3), "Scripts", "python.exe") : path.join(engineDir(env3), "bin", "python");
|
|
74669
|
+
stampPath = (env3) => path.join(engineDir(env3), "version");
|
|
74670
|
+
statePath = (env3) => path.join(humHome(env3), "engine-install.json");
|
|
74671
|
+
run = (cmd, args2, opts = {}) => spawnSync(cmd, args2, { encoding: "utf8", windowsHide: true, ...opts });
|
|
74672
|
+
ASK_VERSION = ["-I", "-c", "import hum; print(hum.__version__)"];
|
|
74673
|
+
readInstallState = (env3 = process.env) => {
|
|
74674
|
+
try {
|
|
74675
|
+
return JSON.parse(fs2.readFileSync(statePath(env3), "utf8"));
|
|
74676
|
+
} catch {
|
|
74677
|
+
return null;
|
|
74678
|
+
}
|
|
74679
|
+
};
|
|
74680
|
+
writeInstallState = (s, env3) => {
|
|
74681
|
+
try {
|
|
74682
|
+
fs2.mkdirSync(humHome(env3), { recursive: true });
|
|
74683
|
+
fs2.writeFileSync(statePath(env3), JSON.stringify(s));
|
|
74684
|
+
} catch {
|
|
74685
|
+
}
|
|
74686
|
+
};
|
|
74687
|
+
}
|
|
74688
|
+
});
|
|
74689
|
+
|
|
74690
|
+
// src/update.js
|
|
74691
|
+
import fs3 from "node:fs";
|
|
74692
|
+
import os4 from "node:os";
|
|
74693
|
+
import path2 from "node:path";
|
|
74694
|
+
import { spawn, spawnSync as spawnSync2 } from "node:child_process";
|
|
74695
|
+
async function latestVersion(fetchImpl = globalThis.fetch, env3 = process.env) {
|
|
74696
|
+
if (env3.HUM_NO_UPDATE_CHECK || typeof fetchImpl !== "function") return "";
|
|
74697
|
+
try {
|
|
74698
|
+
const r = await fetchImpl(`${dist(env3)}/releases/latest`, { signal: AbortSignal.timeout(2500) });
|
|
74699
|
+
if (!r.ok) return "";
|
|
74700
|
+
const v = (await r.text()).trim();
|
|
74701
|
+
return /^\d+\.\d+\.\d+$/.test(v) ? v : "";
|
|
74702
|
+
} catch {
|
|
74703
|
+
return "";
|
|
74704
|
+
}
|
|
74705
|
+
}
|
|
74706
|
+
function installLayout(execPath = process.execPath, env3 = process.env) {
|
|
74707
|
+
const exe = String(execPath).split(/[\\/]/).pop();
|
|
74708
|
+
if (/^(node|bun)(\.exe)?$/i.test(exe)) return { kind: env3.HUM_ENGINE_PORT ? "python" : "npm" };
|
|
74709
|
+
let real = execPath;
|
|
74710
|
+
try {
|
|
74711
|
+
real = fs3.realpathSync(execPath);
|
|
74712
|
+
} catch {
|
|
74713
|
+
}
|
|
74714
|
+
return { kind: "native", exe, dir: path2.dirname(real), base: path2.dirname(path2.dirname(real)) };
|
|
74715
|
+
}
|
|
74716
|
+
function installerArgv(version, platform2 = process.platform) {
|
|
74717
|
+
const base = dist();
|
|
74718
|
+
if (platform2 === "win32") return ["powershell", ["-NoProfile", "-ExecutionPolicy", "Bypass", "-Command", `irm ${base}/install.ps1 | iex`]];
|
|
74719
|
+
return ["/bin/sh", ["-c", `curl -fsSL "${base}/install.sh" | sh`]];
|
|
74720
|
+
}
|
|
74721
|
+
function startBackgroundUpdate(version, { env: env3 = process.env, now = Date.now(), spawnImpl = spawn } = {}) {
|
|
74722
|
+
if (env3.HUM_NO_AUTO_UPDATE) return false;
|
|
74723
|
+
const s = readState(env3);
|
|
74724
|
+
if (s.version === version && now - (s.started || 0) < 30 * 60 * 1e3) return false;
|
|
74725
|
+
const log = path2.join(humHome2(env3), "update.log");
|
|
74726
|
+
let out = "ignore";
|
|
74727
|
+
try {
|
|
74728
|
+
fs3.mkdirSync(humHome2(env3), { recursive: true });
|
|
74729
|
+
out = fs3.openSync(log, "w");
|
|
74730
|
+
} catch {
|
|
74731
|
+
}
|
|
74732
|
+
const [bin, args2] = installerArgv(version);
|
|
74733
|
+
try {
|
|
74734
|
+
const child = spawnImpl(bin, args2, {
|
|
74735
|
+
detached: true,
|
|
74736
|
+
stdio: ["ignore", out, out],
|
|
74737
|
+
windowsHide: true,
|
|
74738
|
+
env: { ...env3, HUM_VERSION: version, HUM_DIST: dist(env3) }
|
|
74739
|
+
});
|
|
74740
|
+
child.unref();
|
|
74741
|
+
writeState({ version, started: now }, env3);
|
|
74742
|
+
return true;
|
|
74743
|
+
} catch {
|
|
74744
|
+
return false;
|
|
74745
|
+
}
|
|
74746
|
+
}
|
|
74747
|
+
function mismatchLine(mine, running, { env: env3 = process.env, layout: layout2 = installLayout(process.execPath, env3), state = readInstallState(env3) } = {}) {
|
|
74748
|
+
if (!mine || !running || mine === running) return "";
|
|
74749
|
+
const head = `hum ${mine} is installed but ${running} is what runs`;
|
|
74750
|
+
if (env3.HUM_ENGINE) return `${head}: HUM_ENGINE points at it \xB7 unset HUM_ENGINE to use ${mine}`;
|
|
74751
|
+
const fix = layout2.kind === "npm" ? npmFix(mine) : updateCommand(layout2);
|
|
74752
|
+
if (state && !state.ok && state.wanted === mine && state.error) return `${head}: the update did not finish (${state.error}) \xB7 ${fix}`;
|
|
74753
|
+
return `${head} \xB7 ${fix}`;
|
|
74754
|
+
}
|
|
74755
|
+
async function updateNotice(mine, { running = "", env: env3 = process.env, fetchImpl = globalThis.fetch, layout: layout2 = installLayout(process.execPath, env3), spawnImpl = spawn } = {}) {
|
|
74756
|
+
const drift = mismatchLine(mine, running, { env: env3, layout: layout2 });
|
|
74757
|
+
if (drift) return drift;
|
|
74758
|
+
const latest = await latestVersion(fetchImpl, env3);
|
|
74759
|
+
if (!latest || !newer(latest, mine)) return "";
|
|
74760
|
+
if (layout2.kind !== "native") return `hum ${latest} is out (this is ${mine}) \xB7 ${updateCommand(layout2)}`;
|
|
74761
|
+
if (readyVersion(layout2, latest)) return `hum ${latest} is ready \xB7 restart hum to use it`;
|
|
74762
|
+
if (startBackgroundUpdate(latest, { env: env3, spawnImpl })) return `hum ${latest} is downloading in the background \xB7 it takes effect the next time you start hum`;
|
|
74763
|
+
const s = readState(env3);
|
|
74764
|
+
if (s.version === latest && !env3.HUM_NO_AUTO_UPDATE) return `hum ${latest} is still installing in the background (${path2.join(humHome2(env3), "update.log")} has the details)`;
|
|
74765
|
+
return `hum ${latest} is out (this is ${mine}) \xB7 ${updateCommand(layout2)}`;
|
|
74766
|
+
}
|
|
74767
|
+
function updateNow(layout2 = installLayout()) {
|
|
74768
|
+
if (layout2.kind === "native") {
|
|
74769
|
+
const [bin, args2] = installerArgv();
|
|
74770
|
+
return spawnSync2(bin, args2, { stdio: "inherit", env: { ...process.env, HUM_DIST: dist() } }).status ?? 1;
|
|
74771
|
+
}
|
|
74772
|
+
if (layout2.kind === "python") {
|
|
74773
|
+
process.stdout.write(`update with your package manager: ${updateCommand(layout2)}
|
|
74774
|
+
`);
|
|
74775
|
+
return 0;
|
|
74776
|
+
}
|
|
74777
|
+
const r = spawnSync2(win2() ? "npm.cmd" : "npm", ["i", "-g", "@metaphi-ai/hum@latest"], { stdio: "inherit", shell: win2() });
|
|
74778
|
+
return r.status ?? 1;
|
|
74779
|
+
}
|
|
74780
|
+
var dist, humHome2, win2, newer, updateCommand, readyVersion, stateFile, readState, writeState;
|
|
74781
|
+
var init_update = __esm({
|
|
74782
|
+
"src/update.js"() {
|
|
74783
|
+
init_install();
|
|
74784
|
+
dist = (env3 = process.env) => (env3.HUM_DIST || "https://metaphi.ai/hum").replace(/\/+$/, "");
|
|
74785
|
+
humHome2 = (env3 = process.env) => env3.HUM_HOME || path2.join(os4.homedir(), ".hum");
|
|
74786
|
+
win2 = () => process.platform === "win32";
|
|
74787
|
+
newer = (a, b) => {
|
|
74788
|
+
const pa = String(a).split(".").map(Number), pb = String(b).split(".").map(Number);
|
|
74789
|
+
for (let i = 0; i < 3; i += 1) {
|
|
74790
|
+
if ((pa[i] || 0) !== (pb[i] || 0)) return (pa[i] || 0) > (pb[i] || 0);
|
|
74791
|
+
}
|
|
74792
|
+
return false;
|
|
74793
|
+
};
|
|
74794
|
+
updateCommand = (layout2 = installLayout(), platform2 = process.platform) => {
|
|
74795
|
+
if (layout2.kind === "native") return platform2 === "win32" ? `irm ${dist()}/install.ps1 | iex` : `curl -fsSL ${dist()}/install.sh | sh`;
|
|
74796
|
+
if (layout2.kind === "python") return "uv tool upgrade hum-cli (or: pip install -U hum-cli)";
|
|
74797
|
+
return "npm i -g @metaphi-ai/hum@latest";
|
|
74798
|
+
};
|
|
74799
|
+
readyVersion = (layout2, version) => layout2.kind === "native" && version && fs3.existsSync(path2.join(layout2.base, version, layout2.exe)) ? version : "";
|
|
74800
|
+
stateFile = (env3 = process.env) => path2.join(humHome2(env3), "update.json");
|
|
74801
|
+
readState = (env3 = process.env) => {
|
|
74802
|
+
try {
|
|
74803
|
+
return JSON.parse(fs3.readFileSync(stateFile(env3), "utf8"));
|
|
74804
|
+
} catch {
|
|
74805
|
+
return {};
|
|
74806
|
+
}
|
|
74807
|
+
};
|
|
74808
|
+
writeState = (s, env3 = process.env) => {
|
|
74809
|
+
try {
|
|
74810
|
+
fs3.mkdirSync(humHome2(env3), { recursive: true });
|
|
74811
|
+
fs3.writeFileSync(stateFile(env3), JSON.stringify(s));
|
|
74812
|
+
} catch {
|
|
74813
|
+
}
|
|
74814
|
+
};
|
|
74815
|
+
}
|
|
74816
|
+
});
|
|
74817
|
+
|
|
74578
74818
|
// node_modules/react/cjs/react-jsx-runtime.production.min.js
|
|
74579
74819
|
var require_react_jsx_runtime_production_min = __commonJS({
|
|
74580
74820
|
"node_modules/react/cjs/react-jsx-runtime.production.min.js"(exports) {
|
|
@@ -75505,6 +75745,571 @@ var require_jsx_runtime = __commonJS({
|
|
|
75505
75745
|
}
|
|
75506
75746
|
});
|
|
75507
75747
|
|
|
75748
|
+
// src/engine.js
|
|
75749
|
+
import fs5 from "node:fs";
|
|
75750
|
+
import net from "node:net";
|
|
75751
|
+
import os6 from "node:os";
|
|
75752
|
+
import path4 from "node:path";
|
|
75753
|
+
import crypto from "node:crypto";
|
|
75754
|
+
import { spawn as spawn2, spawnSync as spawnSync3 } from "node:child_process";
|
|
75755
|
+
function uvToolDirs() {
|
|
75756
|
+
const dirs = [];
|
|
75757
|
+
if (process.env.UV_TOOL_DIR) dirs.push(process.env.UV_TOOL_DIR);
|
|
75758
|
+
if (win3) {
|
|
75759
|
+
for (const base of [process.env.APPDATA, process.env.LOCALAPPDATA]) if (base) dirs.push(path4.join(base, "uv", "tools"));
|
|
75760
|
+
} else dirs.push(path4.join(process.env.XDG_DATA_HOME || path4.join(os6.homedir(), ".local", "share"), "uv", "tools"));
|
|
75761
|
+
if (!dirs.some(exists)) {
|
|
75762
|
+
for (const uv of ["uv", path4.join(os6.homedir(), ".local", "bin", win3 ? "uv.exe" : "uv")]) {
|
|
75763
|
+
try {
|
|
75764
|
+
const r = spawnSync3(uv, ["tool", "dir"], { encoding: "utf8", windowsHide: true });
|
|
75765
|
+
if (r.status === 0 && r.stdout.trim()) {
|
|
75766
|
+
dirs.push(r.stdout.trim());
|
|
75767
|
+
break;
|
|
75768
|
+
}
|
|
75769
|
+
} catch {
|
|
75770
|
+
}
|
|
75771
|
+
}
|
|
75772
|
+
}
|
|
75773
|
+
return dirs;
|
|
75774
|
+
}
|
|
75775
|
+
function enginePython2(dirs = uvToolDirs()) {
|
|
75776
|
+
for (const dir of dirs) for (const name of ["hum-cli", "hum"]) {
|
|
75777
|
+
const py = win3 ? path4.join(dir, name, "Scripts", "python.exe") : path4.join(dir, name, "bin", "python");
|
|
75778
|
+
if (exists(py)) return py;
|
|
75779
|
+
}
|
|
75780
|
+
return null;
|
|
75781
|
+
}
|
|
75782
|
+
function siblingEngine(execPath = process.execPath) {
|
|
75783
|
+
let dir;
|
|
75784
|
+
try {
|
|
75785
|
+
dir = path4.dirname(fs5.realpathSync(execPath));
|
|
75786
|
+
} catch {
|
|
75787
|
+
return null;
|
|
75788
|
+
}
|
|
75789
|
+
const p = path4.join(dir, "engine", win3 ? "hum-engine.exe" : "hum-engine");
|
|
75790
|
+
return exists(p) ? p : null;
|
|
75791
|
+
}
|
|
75792
|
+
function homeEngine(env3 = process.env) {
|
|
75793
|
+
const home = env3.HUM_HOME || path4.join(os6.homedir(), ".hum");
|
|
75794
|
+
const py = win3 ? path4.join(home, "engine", "Scripts", "python.exe") : path4.join(home, "engine", "bin", "python");
|
|
75795
|
+
return exists(py) ? py : null;
|
|
75796
|
+
}
|
|
75797
|
+
function engineCandidates(env3 = process.env) {
|
|
75798
|
+
const out = [];
|
|
75799
|
+
if (env3.HUM_ENGINE) {
|
|
75800
|
+
const [bin, ...args2] = env3.HUM_ENGINE.split(" ");
|
|
75801
|
+
out.push({ bin, args: args2, where: "HUM_ENGINE" });
|
|
75802
|
+
}
|
|
75803
|
+
const sib = siblingEngine();
|
|
75804
|
+
if (sib) out.push({ bin: sib, args: ["engine"], where: "beside hum" });
|
|
75805
|
+
const home = homeEngine(env3);
|
|
75806
|
+
if (home) out.push({ bin: home, args: ["-m", "hum.cli", "engine"], where: "HUM_HOME/engine" });
|
|
75807
|
+
const py = enginePython2();
|
|
75808
|
+
if (py) out.push({ bin: py, args: ["-m", "hum.cli", "engine"], where: "the interpreter beside it" });
|
|
75809
|
+
out.push({ bin: "hum-engine", args: [], where: "PATH" });
|
|
75810
|
+
out.push({ bin: path4.join(os6.homedir(), ".local", "bin", win3 ? "hum-engine.exe" : "hum-engine"), args: [], where: "uv's bin dir" });
|
|
75811
|
+
return out;
|
|
75812
|
+
}
|
|
75813
|
+
function engineCommand(argv, candidates = engineCandidates()) {
|
|
75814
|
+
for (const c of candidates) {
|
|
75815
|
+
if (c.args[c.args.length - 1] !== "engine") continue;
|
|
75816
|
+
return { bin: c.bin, args: [...c.args.slice(0, -1), ...argv], where: c.where };
|
|
75817
|
+
}
|
|
75818
|
+
return null;
|
|
75819
|
+
}
|
|
75820
|
+
function candidateVersion(c, { env: env3 = process.env, runImpl = spawnSync3 } = {}) {
|
|
75821
|
+
if (!c || !c.bin) return null;
|
|
75822
|
+
if (c.where === "HUM_HOME/engine") return installedVersion(env3);
|
|
75823
|
+
const interp = c.args.length >= 3 && c.args[c.args.length - 3] === "-m" && c.args[c.args.length - 2] === "hum.cli";
|
|
75824
|
+
let r;
|
|
75825
|
+
try {
|
|
75826
|
+
r = runImpl(c.bin, interp ? ASK_VERSION : ["--version"], { encoding: "utf8", windowsHide: true, timeout: 2e4 });
|
|
75827
|
+
} catch {
|
|
75828
|
+
return null;
|
|
75829
|
+
}
|
|
75830
|
+
if (!r || r.status !== 0) return null;
|
|
75831
|
+
const m = String(r.stdout || "").match(/(\d+\.\d+\.\d+)/);
|
|
75832
|
+
return m ? m[1] : null;
|
|
75833
|
+
}
|
|
75834
|
+
function runningVersion(candidates = engineCandidates(), opts = {}) {
|
|
75835
|
+
for (const c of candidates) {
|
|
75836
|
+
const v = candidateVersion(c, opts);
|
|
75837
|
+
if (v) return { version: v, where: c.where };
|
|
75838
|
+
}
|
|
75839
|
+
return null;
|
|
75840
|
+
}
|
|
75841
|
+
function startFailure(failures, { npm = /^(node|bun)(\.exe)?$/i.test(String(process.execPath).split(/[\\/]/).pop()), platform: platform2 = process.platform, version = true ? "0.1.30" : "" } = {}) {
|
|
75842
|
+
const refused = failures.find((f) => f.error && f.error.code !== "ENOENT");
|
|
75843
|
+
const fix = npm ? npmFix(version) : updateCommand({ kind: "native" }, platform2);
|
|
75844
|
+
if (!refused) {
|
|
75845
|
+
return `Hum is not fully installed here \u2014 the half that does the work is missing. Run: ${fix} (or set HUM_ENGINE to the command that runs it)`;
|
|
75846
|
+
}
|
|
75847
|
+
const what = refused.error.code || refused.error.message;
|
|
75848
|
+
const lines = [
|
|
75849
|
+
`Hum is installed (${refused.bin}) but this machine would not run it: ${what}.`
|
|
75850
|
+
];
|
|
75851
|
+
if (win3) {
|
|
75852
|
+
lines.push("On a managed Windows machine that is usually Device Guard / WDAC refusing an executable it does not know.");
|
|
75853
|
+
lines.push(`To see the policy's own message, run: "${refused.bin}" --help`);
|
|
75854
|
+
const dir = uvToolDirs()[0];
|
|
75855
|
+
lines.push(`If uv's environment is elsewhere, point Hum at its interpreter: set HUM_ENGINE=${path4.join(dir || "<uv tool dir>", "hum-cli", "Scripts", "python.exe")} -m hum.cli engine`);
|
|
75856
|
+
} else {
|
|
75857
|
+
lines.push('Set HUM_ENGINE to a command that starts it, e.g. HUM_ENGINE="python -m hum.cli engine"');
|
|
75858
|
+
}
|
|
75859
|
+
return lines.join("\n");
|
|
75860
|
+
}
|
|
75861
|
+
function attempt({ bin, args: args2 }, cwd2, { task, images, resume }) {
|
|
75862
|
+
return new Promise((resolve, reject) => {
|
|
75863
|
+
const runId = crypto.randomBytes(6).toString("hex");
|
|
75864
|
+
fs5.mkdirSync(runDir(), { recursive: true });
|
|
75865
|
+
const logPath = path4.join(runDir(), `${runId}.log`);
|
|
75866
|
+
const log = fs5.openSync(logPath, "a");
|
|
75867
|
+
const argv = [...args2, "-C", cwd2, "--run-id", runId];
|
|
75868
|
+
if (task) argv.push("--task", task);
|
|
75869
|
+
for (const p of images) argv.push("--image", p);
|
|
75870
|
+
if (resume) argv.push("--resume", resume);
|
|
75871
|
+
let settled = false;
|
|
75872
|
+
const settle = (fn) => {
|
|
75873
|
+
if (!settled) {
|
|
75874
|
+
settled = true;
|
|
75875
|
+
fn();
|
|
75876
|
+
}
|
|
75877
|
+
};
|
|
75878
|
+
let child;
|
|
75879
|
+
try {
|
|
75880
|
+
child = spawn2(bin, argv, { stdio: ["ignore", log, log], detached: true, windowsHide: true });
|
|
75881
|
+
} catch (e) {
|
|
75882
|
+
fs5.closeSync(log);
|
|
75883
|
+
reject({ spawn: e });
|
|
75884
|
+
return;
|
|
75885
|
+
}
|
|
75886
|
+
fs5.closeSync(log);
|
|
75887
|
+
let died = false;
|
|
75888
|
+
child.on("error", (e) => settle(() => reject({ spawn: e })));
|
|
75889
|
+
child.on("exit", () => {
|
|
75890
|
+
died = true;
|
|
75891
|
+
});
|
|
75892
|
+
const t0 = Date.now();
|
|
75893
|
+
const poll = () => {
|
|
75894
|
+
if (settled) return;
|
|
75895
|
+
const rec = readRun(runId);
|
|
75896
|
+
if (rec && rec.port) {
|
|
75897
|
+
child.unref();
|
|
75898
|
+
settle(() => resolve(rec));
|
|
75899
|
+
return;
|
|
75900
|
+
}
|
|
75901
|
+
if (rec && rec.error) {
|
|
75902
|
+
settle(() => reject({ failed: rec.error }));
|
|
75903
|
+
return;
|
|
75904
|
+
}
|
|
75905
|
+
if (died && !rec) {
|
|
75906
|
+
settle(() => reject({ died: logPath }));
|
|
75907
|
+
return;
|
|
75908
|
+
}
|
|
75909
|
+
if (Date.now() - t0 > 9e4) {
|
|
75910
|
+
settle(() => reject({ timeout: true }));
|
|
75911
|
+
return;
|
|
75912
|
+
}
|
|
75913
|
+
setTimeout(poll, 50);
|
|
75914
|
+
};
|
|
75915
|
+
poll();
|
|
75916
|
+
});
|
|
75917
|
+
}
|
|
75918
|
+
function failureMessage(error) {
|
|
75919
|
+
return error.message + (error.hint ? `
|
|
75920
|
+
${error.hint}` : "");
|
|
75921
|
+
}
|
|
75922
|
+
function diedMessage(logPath, text = null) {
|
|
75923
|
+
let tail3 = "";
|
|
75924
|
+
try {
|
|
75925
|
+
tail3 = (text ?? fs5.readFileSync(logPath, "utf8")).trim().split("\n").slice(-3).join("\n").trim();
|
|
75926
|
+
} catch {
|
|
75927
|
+
}
|
|
75928
|
+
return `the session did not start${tail3 ? `:
|
|
75929
|
+
${tail3}` : ""}
|
|
75930
|
+
(its log: ${logPath})`;
|
|
75931
|
+
}
|
|
75932
|
+
async function spawnEngine(cwd2, { task = null, images = [], resume = null, candidates = engineCandidates() } = {}) {
|
|
75933
|
+
const failures = [];
|
|
75934
|
+
for (const cand of candidates) {
|
|
75935
|
+
if (!cand.bin) continue;
|
|
75936
|
+
try {
|
|
75937
|
+
return await attempt(cand, cwd2, { task, images, resume });
|
|
75938
|
+
} catch (f) {
|
|
75939
|
+
if (f && f.spawn) {
|
|
75940
|
+
failures.push({ ...cand, error: f.spawn });
|
|
75941
|
+
continue;
|
|
75942
|
+
}
|
|
75943
|
+
if (f && f.failed) throw new EngineError(failureMessage(f.failed));
|
|
75944
|
+
if (f && f.died) throw new EngineError(diedMessage(f.died));
|
|
75945
|
+
if (f && f.timeout) throw new EngineError("the session did not start in time");
|
|
75946
|
+
throw f;
|
|
75947
|
+
}
|
|
75948
|
+
}
|
|
75949
|
+
throw new EngineError(startFailure(failures));
|
|
75950
|
+
}
|
|
75951
|
+
var runDir, readRun, EngineError, win3, exists, Engine;
|
|
75952
|
+
var init_engine = __esm({
|
|
75953
|
+
"src/engine.js"() {
|
|
75954
|
+
init_install();
|
|
75955
|
+
init_update();
|
|
75956
|
+
runDir = () => path4.join(process.env.HUM_HOME || path4.join(os6.homedir(), ".hum"), "run");
|
|
75957
|
+
readRun = (id) => {
|
|
75958
|
+
try {
|
|
75959
|
+
return JSON.parse(fs5.readFileSync(path4.join(runDir(), `${id}.json`), "utf8"));
|
|
75960
|
+
} catch {
|
|
75961
|
+
return null;
|
|
75962
|
+
}
|
|
75963
|
+
};
|
|
75964
|
+
EngineError = class extends Error {
|
|
75965
|
+
};
|
|
75966
|
+
win3 = process.platform === "win32";
|
|
75967
|
+
exists = (p) => {
|
|
75968
|
+
try {
|
|
75969
|
+
fs5.accessSync(p);
|
|
75970
|
+
return true;
|
|
75971
|
+
} catch {
|
|
75972
|
+
return false;
|
|
75973
|
+
}
|
|
75974
|
+
};
|
|
75975
|
+
Engine = class {
|
|
75976
|
+
constructor(port2) {
|
|
75977
|
+
this.port = port2;
|
|
75978
|
+
this.handlers = [];
|
|
75979
|
+
this.closed = false;
|
|
75980
|
+
}
|
|
75981
|
+
connect() {
|
|
75982
|
+
return new Promise((resolve, reject) => {
|
|
75983
|
+
const sock = net.createConnection({ host: "127.0.0.1", port: this.port }, () => resolve());
|
|
75984
|
+
this.sock = sock;
|
|
75985
|
+
sock.on("error", (e) => {
|
|
75986
|
+
if (!this.closed && this.sock === sock) reject(new EngineError(`could not reach the session: ${e.message}`));
|
|
75987
|
+
});
|
|
75988
|
+
let buf = "";
|
|
75989
|
+
sock.on("data", (d) => {
|
|
75990
|
+
if (this.sock !== sock) return;
|
|
75991
|
+
buf += d.toString();
|
|
75992
|
+
const lines = buf.split("\n");
|
|
75993
|
+
buf = lines.pop();
|
|
75994
|
+
for (const line of lines) {
|
|
75995
|
+
if (!line.trim()) continue;
|
|
75996
|
+
let ev;
|
|
75997
|
+
try {
|
|
75998
|
+
ev = JSON.parse(line);
|
|
75999
|
+
} catch {
|
|
76000
|
+
continue;
|
|
76001
|
+
}
|
|
76002
|
+
for (const h of this.handlers) h(ev);
|
|
76003
|
+
}
|
|
76004
|
+
});
|
|
76005
|
+
sock.on("close", () => {
|
|
76006
|
+
if (this.sock !== sock) return;
|
|
76007
|
+
this.closed = true;
|
|
76008
|
+
for (const h of this.handlers) h({ type: "bye", gone: true });
|
|
76009
|
+
});
|
|
76010
|
+
});
|
|
76011
|
+
}
|
|
76012
|
+
// Attach to another engine (a session running elsewhere on this machine): the old
|
|
76013
|
+
// socket is dropped quietly, the new one greets us with hello and a replay.
|
|
76014
|
+
async reconnect(port2) {
|
|
76015
|
+
const old = this.sock;
|
|
76016
|
+
this.sock = null;
|
|
76017
|
+
this.port = port2;
|
|
76018
|
+
this.closed = false;
|
|
76019
|
+
try {
|
|
76020
|
+
old.destroy();
|
|
76021
|
+
} catch {
|
|
76022
|
+
}
|
|
76023
|
+
await this.connect();
|
|
76024
|
+
}
|
|
76025
|
+
on(handler) {
|
|
76026
|
+
this.handlers.push(handler);
|
|
76027
|
+
}
|
|
76028
|
+
send(cmd) {
|
|
76029
|
+
if (this.closed) return;
|
|
76030
|
+
try {
|
|
76031
|
+
this.sock.write(JSON.stringify(cmd) + "\n");
|
|
76032
|
+
} catch {
|
|
76033
|
+
}
|
|
76034
|
+
}
|
|
76035
|
+
close() {
|
|
76036
|
+
this.closed = true;
|
|
76037
|
+
try {
|
|
76038
|
+
this.sock.end();
|
|
76039
|
+
} catch {
|
|
76040
|
+
}
|
|
76041
|
+
}
|
|
76042
|
+
};
|
|
76043
|
+
}
|
|
76044
|
+
});
|
|
76045
|
+
|
|
76046
|
+
// src/doctor.js
|
|
76047
|
+
var doctor_exports = {};
|
|
76048
|
+
__export(doctor_exports, {
|
|
76049
|
+
diagnose: () => diagnose,
|
|
76050
|
+
doctor: () => doctor,
|
|
76051
|
+
onPath: () => onPath,
|
|
76052
|
+
render: () => render2
|
|
76053
|
+
});
|
|
76054
|
+
import fs6 from "node:fs";
|
|
76055
|
+
import os7 from "node:os";
|
|
76056
|
+
import path5 from "node:path";
|
|
76057
|
+
import { spawnSync as spawnSync4 } from "node:child_process";
|
|
76058
|
+
function jsonError(text, e) {
|
|
76059
|
+
const msg = e.message || "";
|
|
76060
|
+
const lc = /\(line (\d+) column \d+\)/.exec(msg);
|
|
76061
|
+
if (lc) return `line ${lc[1]}: ${msg.replace(/ in JSON.*$/, "")}`;
|
|
76062
|
+
const m = /position (\d+)/.exec(msg);
|
|
76063
|
+
if (!m) return msg;
|
|
76064
|
+
const line = text.slice(0, Number(m[1])).split("\n").length;
|
|
76065
|
+
return `line ${line}: ${msg.replace(/ in JSON.*$/, "")}`;
|
|
76066
|
+
}
|
|
76067
|
+
function onPath(env3, { platform: platform2 = process.platform } = {}) {
|
|
76068
|
+
const names = isWin(platform2) ? ["hum.cmd", "hum.exe", "hum", "hum-engine.exe", "hum-engine.cmd"] : ["hum", "hum-engine"];
|
|
76069
|
+
const seen = /* @__PURE__ */ new Set();
|
|
76070
|
+
const hits = [];
|
|
76071
|
+
for (const dir of String(env3.PATH || env3.Path || "").split(path5.delimiter).filter(Boolean)) {
|
|
76072
|
+
for (const n of names) {
|
|
76073
|
+
const p = path5.join(dir, n);
|
|
76074
|
+
if (!exists2(p) || seen.has(p)) continue;
|
|
76075
|
+
seen.add(p);
|
|
76076
|
+
hits.push({ path: p, name: n, real: realpath(p) });
|
|
76077
|
+
}
|
|
76078
|
+
}
|
|
76079
|
+
return hits;
|
|
76080
|
+
}
|
|
76081
|
+
async function diagnose({
|
|
76082
|
+
env: env3 = process.env,
|
|
76083
|
+
mine = "0.0.0",
|
|
76084
|
+
platform: platform2 = process.platform,
|
|
76085
|
+
execPath = process.execPath,
|
|
76086
|
+
homedir = os7.homedir(),
|
|
76087
|
+
cwd: cwd2 = process.cwd(),
|
|
76088
|
+
layout: layout2 = installLayout(execPath, env3),
|
|
76089
|
+
candidates = engineCandidates(env3),
|
|
76090
|
+
runImpl = spawnSync4,
|
|
76091
|
+
fetchImpl = globalThis.fetch
|
|
76092
|
+
} = {}) {
|
|
76093
|
+
const home = env3.HUM_HOME || path5.join(homedir, ".hum");
|
|
76094
|
+
const sections = [];
|
|
76095
|
+
{
|
|
76096
|
+
const checks = [];
|
|
76097
|
+
const from = layout2.kind === "native" ? path5.join(layout2.dir, layout2.exe) : realpath(execPath);
|
|
76098
|
+
const how = { native: "the native install", npm: "npm", python: "Python (uv or pip)" }[layout2.kind] || layout2.kind;
|
|
76099
|
+
checks.push(check("ok", `hum ${mine} \xB7 installed with ${how} \xB7 runs from ${from}`));
|
|
76100
|
+
if (layout2.kind === "native") {
|
|
76101
|
+
const launcher = isWin(platform2) ? path5.join(env3.LOCALAPPDATA || path5.join(homedir, "AppData", "Local"), "hum", "bin", "hum.cmd") : path5.join(homedir, ".local", "bin", "hum");
|
|
76102
|
+
if (!exists2(launcher)) checks.push(check("warn", `no launcher at ${launcher}`, updateCommand(layout2, platform2)));
|
|
76103
|
+
else {
|
|
76104
|
+
const target = isWin(platform2) ? (fs6.readFileSync(launcher, "utf8").match(new RegExp('"([^"]+)"')) || [])[1] || "" : realpath(launcher);
|
|
76105
|
+
const insideVersions = target && realpath(target).startsWith(realpath(layout2.base));
|
|
76106
|
+
checks.push(insideVersions ? check("ok", `launcher ${launcher} \u2192 ${target}`) : check("warn", `launcher ${launcher} is not the installer's (it points at ${target || "?"})`, updateCommand(layout2, platform2)));
|
|
76107
|
+
}
|
|
76108
|
+
}
|
|
76109
|
+
const hits = onPath(env3, { platform: platform2 });
|
|
76110
|
+
const hums = hits.filter((h) => !h.name.startsWith("hum-engine"));
|
|
76111
|
+
const stale = hits.filter((h) => h.name.startsWith("hum-engine"));
|
|
76112
|
+
const targets = new Set(hums.map((h) => h.real));
|
|
76113
|
+
if (hums.length === 0) checks.push(check("warn", "no hum on PATH: a new terminal may not find it", layout2.kind === "native" ? isWin(platform2) ? "open a new terminal" : 'export PATH="$HOME/.local/bin:$PATH"' : "npm bin -g, and put that directory on PATH"));
|
|
76114
|
+
else if (targets.size > 1) checks.push(check("warn", `more than one hum on PATH; the first wins: ${hums.map((h) => h.path).join(" \xB7 ")}`, "remove the ones you did not mean to keep"));
|
|
76115
|
+
else checks.push(check("ok", `hum on PATH: ${hums[0].path}`));
|
|
76116
|
+
for (const s of stale) checks.push(check("warn", `an older install left ${s.path} on PATH`, "uv tool uninstall hum-cli"));
|
|
76117
|
+
sections.push({ key: "install", title: "Install", checks });
|
|
76118
|
+
}
|
|
76119
|
+
let running = null;
|
|
76120
|
+
{
|
|
76121
|
+
const checks = [];
|
|
76122
|
+
if (env3.HUM_ENGINE_PORT) checks.push(check("ok", `started by Python for this hum (HUM_ENGINE_PORT=${env3.HUM_ENGINE_PORT})`));
|
|
76123
|
+
for (const c of candidates) {
|
|
76124
|
+
const v = candidateVersion(c, { env: env3, runImpl });
|
|
76125
|
+
if (v) {
|
|
76126
|
+
running = { ...c, version: v };
|
|
76127
|
+
break;
|
|
76128
|
+
}
|
|
76129
|
+
}
|
|
76130
|
+
if (!running) checks.push(check("fail", "nothing answers: the part of hum that does the work is missing", layout2.kind === "npm" ? npmFix2(mine) : updateCommand(layout2, platform2)));
|
|
76131
|
+
else if (running.version === mine) checks.push(check("ok", `${running.version} runs from ${running.where} (${running.bin})`));
|
|
76132
|
+
else if (env3.HUM_ENGINE) checks.push(check("fail", `${running.version} is what runs: HUM_ENGINE points at it (${env3.HUM_ENGINE}); you installed ${mine}`, "unset HUM_ENGINE"));
|
|
76133
|
+
else checks.push(check("fail", `${running.version} is what runs (${running.where}: ${running.bin}); you installed ${mine}`, layout2.kind === "npm" ? npmFix2(mine) : updateCommand(layout2, platform2)));
|
|
76134
|
+
if (env3.HUM_ENGINE && running && running.version === mine) checks.push(check("warn", `HUM_ENGINE is set (${env3.HUM_ENGINE}): it decides what runs, ahead of any install`, "unset HUM_ENGINE"));
|
|
76135
|
+
if (layout2.kind === "npm") {
|
|
76136
|
+
const st = readInstallState(env3);
|
|
76137
|
+
const stamp = installedVersion(env3, runImpl);
|
|
76138
|
+
if (st && !st.ok) checks.push(check(stamp === mine ? "warn" : "fail", `the last install attempt (wanted ${st.wanted || st.version}) did not finish: ${st.error}`, npmFix2(mine)));
|
|
76139
|
+
else if (!stamp) checks.push(check("fail", `nothing installed under ${engineDir(env3)}`, npmFix2(mine)));
|
|
76140
|
+
else checks.push(check(stamp === mine ? "ok" : "warn", `${engineDir(env3)} holds ${stamp}`, stamp === mine ? "" : npmFix2(mine)));
|
|
76141
|
+
}
|
|
76142
|
+
if (layout2.kind === "native") {
|
|
76143
|
+
const sib = path5.join(layout2.dir, "engine", isWin(platform2) ? "hum-engine.exe" : "hum-engine");
|
|
76144
|
+
checks.push(exists2(sib) ? check("ok", `the working half is beside hum: ${sib}`) : check("fail", `nothing beside hum at ${sib}: the install is incomplete`, updateCommand(layout2, platform2)));
|
|
76145
|
+
}
|
|
76146
|
+
sections.push({ key: "runtime", title: "The part of hum that does the work", checks });
|
|
76147
|
+
}
|
|
76148
|
+
{
|
|
76149
|
+
const checks = [];
|
|
76150
|
+
const st = readState(env3);
|
|
76151
|
+
if (st && st.version) {
|
|
76152
|
+
const ready = readyVersion(layout2, st.version);
|
|
76153
|
+
checks.push(check("ok", `last background update: ${st.version}, started ${st.started ? new Date(st.started).toISOString() : "?"}${ready ? " \xB7 ready, takes effect on restart" : ""}`));
|
|
76154
|
+
const last = tail2(path5.join(home, "update.log"));
|
|
76155
|
+
if (last) checks.push(check("ok", `update.log: ${last}`));
|
|
76156
|
+
} else checks.push(check("ok", "no background update recorded"));
|
|
76157
|
+
if (env3.HUM_NO_UPDATE_CHECK) checks.push(check("warn", "HUM_NO_UPDATE_CHECK is set: hum does not look for releases", "unset HUM_NO_UPDATE_CHECK"));
|
|
76158
|
+
if (env3.HUM_NO_AUTO_UPDATE) checks.push(check("warn", "HUM_NO_AUTO_UPDATE is set: hum tells you about releases but does not fetch them", "unset HUM_NO_AUTO_UPDATE"));
|
|
76159
|
+
const latest = env3.HUM_NO_UPDATE_CHECK ? "" : await latestVersion(fetchImpl, env3);
|
|
76160
|
+
if (!latest && !env3.HUM_NO_UPDATE_CHECK) checks.push(check("warn", `could not reach ${dist(env3)} (offline, or a proxy in the way)`, "try again with a connection"));
|
|
76161
|
+
else if (latest && newer(latest, mine)) checks.push(check("warn", `${latest} is out \xB7 this is ${mine}`, updateCommand(layout2, platform2)));
|
|
76162
|
+
else if (latest) checks.push(check("ok", `${mine} is the latest release`));
|
|
76163
|
+
sections.push({ key: "updates", title: "Updates", checks });
|
|
76164
|
+
}
|
|
76165
|
+
const interp = running && running.args.length >= 3 && running.args[running.args.length - 2] === "hum.cli" ? running.bin : exists2(enginePython(env3)) ? enginePython(env3) : null;
|
|
76166
|
+
let toolServers = null;
|
|
76167
|
+
{
|
|
76168
|
+
const checks = [];
|
|
76169
|
+
try {
|
|
76170
|
+
fs6.accessSync(home, fs6.constants.W_OK);
|
|
76171
|
+
checks.push(check("ok", `HUM_HOME ${home} is writable`));
|
|
76172
|
+
} catch {
|
|
76173
|
+
checks.push(exists2(home) ? check("fail", `${home} is not writable`, `chmod u+w ${home}`) : check("warn", `${home} does not exist yet: it is made on first run`));
|
|
76174
|
+
}
|
|
76175
|
+
const configPath = env3.HUM_CONFIG || path5.join(home, "config.toml");
|
|
76176
|
+
if (!exists2(configPath)) checks.push(check("ok", `no ${configPath}: defaults`));
|
|
76177
|
+
else if (!interp) checks.push(check("warn", `${configPath} not checked: nothing here can parse TOML`, layout2.kind === "npm" ? npmFix2(mine) : updateCommand(layout2, platform2)));
|
|
76178
|
+
else {
|
|
76179
|
+
const r = runImpl(interp, ["-I", "-c", PARSE_CONFIG, configPath], { encoding: "utf8", windowsHide: true, timeout: 2e4 });
|
|
76180
|
+
let parsed = null;
|
|
76181
|
+
try {
|
|
76182
|
+
parsed = JSON.parse(String(r && r.stdout || ""));
|
|
76183
|
+
} catch {
|
|
76184
|
+
}
|
|
76185
|
+
if (!parsed) checks.push(check("warn", `${configPath} not checked: ${interp} did not answer`));
|
|
76186
|
+
else if (parsed.error) checks.push(check("fail", `${configPath}: ${parsed.error}`, `fix ${configPath}`));
|
|
76187
|
+
else {
|
|
76188
|
+
checks.push(check("ok", `${configPath} parses`));
|
|
76189
|
+
toolServers = parsed.mcp;
|
|
76190
|
+
}
|
|
76191
|
+
}
|
|
76192
|
+
for (const f of [path5.join(home, "hooks.json"), path5.join(cwd2, ".hum", "hooks.json"), path5.join(home, "autonomy.json"), path5.join(home, "update.json"), path5.join(home, "engine-install.json")]) {
|
|
76193
|
+
if (!exists2(f)) continue;
|
|
76194
|
+
const text = fs6.readFileSync(f, "utf8");
|
|
76195
|
+
try {
|
|
76196
|
+
JSON.parse(text);
|
|
76197
|
+
checks.push(check("ok", `${f} parses`));
|
|
76198
|
+
} catch (e) {
|
|
76199
|
+
checks.push(check("fail", `${f}: ${jsonError(text, e)}`, `fix ${f}`));
|
|
76200
|
+
}
|
|
76201
|
+
}
|
|
76202
|
+
const credPath = path5.join(home, "credentials.json");
|
|
76203
|
+
let cred = null;
|
|
76204
|
+
if (exists2(credPath)) {
|
|
76205
|
+
const text = fs6.readFileSync(credPath, "utf8");
|
|
76206
|
+
try {
|
|
76207
|
+
cred = JSON.parse(text);
|
|
76208
|
+
} catch (e) {
|
|
76209
|
+
checks.push(check("fail", `${credPath}: ${jsonError(text, e)}`, "hum login"));
|
|
76210
|
+
}
|
|
76211
|
+
}
|
|
76212
|
+
if (cred && cred.access_token) checks.push(check("ok", `signed in${cred.email ? ` as ${cred.email}` : ""}`));
|
|
76213
|
+
else if (!cred) checks.push(check("warn", "not signed in", "hum login"));
|
|
76214
|
+
checks.push(sandboxCheck(platform2, env3));
|
|
76215
|
+
sections.push({ key: "configuration", title: "Configuration", checks });
|
|
76216
|
+
}
|
|
76217
|
+
{
|
|
76218
|
+
const checks = [];
|
|
76219
|
+
const local = Array.isArray(toolServers) ? toolServers : null;
|
|
76220
|
+
if (local) for (const s of local) checks.push(check("ok", `${s.name} \xB7 ${s.transport}${s.at ? ` \xB7 ${s.at}` : ""} \xB7 from config.toml`));
|
|
76221
|
+
else if (toolServers === null && exists2(env3.HUM_CONFIG || path5.join(home, "config.toml"))) checks.push(check("warn", "config.toml servers not listed (it did not parse, or nothing here can read it)"));
|
|
76222
|
+
let cred = null;
|
|
76223
|
+
try {
|
|
76224
|
+
cred = JSON.parse(fs6.readFileSync(path5.join(home, "credentials.json"), "utf8"));
|
|
76225
|
+
} catch {
|
|
76226
|
+
}
|
|
76227
|
+
for (const s of cred && Array.isArray(cred.mcp) ? cred.mcp : []) if (s && s.name) checks.push(check("ok", `${s.name} \xB7 http \xB7 via the server`));
|
|
76228
|
+
if (checks.length === 0) checks.push(check("ok", "none configured"));
|
|
76229
|
+
sections.push({ key: "tool_servers", title: "Tool servers", checks });
|
|
76230
|
+
}
|
|
76231
|
+
const summary = { ok: 0, warn: 0, fail: 0 };
|
|
76232
|
+
for (const s of sections) for (const c of s.checks) summary[c.status] += 1;
|
|
76233
|
+
return { hum: mine, platform: platform2, layout: layout2.kind, sections, summary };
|
|
76234
|
+
}
|
|
76235
|
+
function sandboxCheck(platform2, env3) {
|
|
76236
|
+
if (isWin(platform2)) return check("ok", "no sandbox on Windows: commands run as you, in your account");
|
|
76237
|
+
if (platform2 === "darwin") return exists2("/usr/bin/sandbox-exec") ? check("ok", "sandbox: macOS Seatbelt (/usr/bin/sandbox-exec)") : check("warn", "/usr/bin/sandbox-exec is missing: commands run unsandboxed");
|
|
76238
|
+
const dirs = String(env3.PATH || "").split(path5.delimiter);
|
|
76239
|
+
const bwrap = dirs.map((d) => path5.join(d, "bwrap")).find(exists2);
|
|
76240
|
+
if (!bwrap) return check("warn", "bubblewrap is not installed: commands run unsandboxed", "sudo apt install bubblewrap");
|
|
76241
|
+
const restricted = (() => {
|
|
76242
|
+
try {
|
|
76243
|
+
return fs6.readFileSync("/proc/sys/kernel/apparmor_restrict_unprivileged_userns", "utf8").trim() === "1";
|
|
76244
|
+
} catch {
|
|
76245
|
+
return false;
|
|
76246
|
+
}
|
|
76247
|
+
})();
|
|
76248
|
+
if (restricted) return check("warn", "bubblewrap is installed but unprivileged user namespaces are restricted", "sudo sysctl -w kernel.apparmor_restrict_unprivileged_userns=0");
|
|
76249
|
+
return check("ok", `sandbox: bubblewrap (${bwrap})`);
|
|
76250
|
+
}
|
|
76251
|
+
function render2(report) {
|
|
76252
|
+
const out = [];
|
|
76253
|
+
for (const s of report.sections) {
|
|
76254
|
+
out.push(s.title);
|
|
76255
|
+
for (const c of s.checks) out.push(` ${MARK[c.status]} ${c.text}${c.fix ? `
|
|
76256
|
+
\u2192 ${c.fix}` : ""}`);
|
|
76257
|
+
out.push("");
|
|
76258
|
+
}
|
|
76259
|
+
out.push(`${report.summary.ok} ok \xB7 ${report.summary.warn} warn \xB7 ${report.summary.fail} fail`);
|
|
76260
|
+
return out.join("\n") + "\n";
|
|
76261
|
+
}
|
|
76262
|
+
async function doctor({ json = false, mine, write = (t) => process.stdout.write(t), ...opts } = {}) {
|
|
76263
|
+
const report = await diagnose({ mine, ...opts });
|
|
76264
|
+
write(json ? JSON.stringify(report, null, 2) + "\n" : render2(report));
|
|
76265
|
+
return report.summary.fail ? 1 : 0;
|
|
76266
|
+
}
|
|
76267
|
+
var isWin, npmFix2, exists2, realpath, tail2, check, PARSE_CONFIG, MARK;
|
|
76268
|
+
var init_doctor = __esm({
|
|
76269
|
+
"src/doctor.js"() {
|
|
76270
|
+
init_engine();
|
|
76271
|
+
init_install();
|
|
76272
|
+
init_update();
|
|
76273
|
+
isWin = (platform2) => platform2 === "win32";
|
|
76274
|
+
npmFix2 = (version) => `npm i -g @metaphi-ai/hum@${version || "latest"} --foreground-scripts`;
|
|
76275
|
+
exists2 = (p) => {
|
|
76276
|
+
try {
|
|
76277
|
+
fs6.accessSync(p);
|
|
76278
|
+
return true;
|
|
76279
|
+
} catch {
|
|
76280
|
+
return false;
|
|
76281
|
+
}
|
|
76282
|
+
};
|
|
76283
|
+
realpath = (p) => {
|
|
76284
|
+
try {
|
|
76285
|
+
return fs6.realpathSync(p);
|
|
76286
|
+
} catch {
|
|
76287
|
+
return p;
|
|
76288
|
+
}
|
|
76289
|
+
};
|
|
76290
|
+
tail2 = (p) => {
|
|
76291
|
+
try {
|
|
76292
|
+
const lines = fs6.readFileSync(p, "utf8").trim().split("\n");
|
|
76293
|
+
return lines[lines.length - 1] || "";
|
|
76294
|
+
} catch {
|
|
76295
|
+
return "";
|
|
76296
|
+
}
|
|
76297
|
+
};
|
|
76298
|
+
check = (status, text, fix = "") => ({ status, text, ...fix ? { fix } : {} });
|
|
76299
|
+
PARSE_CONFIG = [
|
|
76300
|
+
"import json, sys, tomllib",
|
|
76301
|
+
"p = sys.argv[1]",
|
|
76302
|
+
"try:",
|
|
76303
|
+
' d = tomllib.loads(open(p, "rb").read().decode("utf-8"))',
|
|
76304
|
+
"except Exception as e:",
|
|
76305
|
+
' print(json.dumps({"error": str(e)})); sys.exit(0)',
|
|
76306
|
+
'mcp = [{"name": s.get("name", "?"), "transport": "http" if s.get("url") else "stdio", "at": s.get("url") or s.get("command") or ""} for s in d.get("mcp", [])]',
|
|
76307
|
+
'print(json.dumps({"mcp": mcp}))'
|
|
76308
|
+
].join("\n");
|
|
76309
|
+
MARK = { ok: "ok ", warn: "warn", fail: "FAIL" };
|
|
76310
|
+
}
|
|
76311
|
+
});
|
|
76312
|
+
|
|
75508
76313
|
// src/cli.jsx
|
|
75509
76314
|
var import_react25 = __toESM(require_react(), 1);
|
|
75510
76315
|
|
|
@@ -80199,7 +81004,7 @@ var create = (stream, { showCursor = false } = {}) => {
|
|
|
80199
81004
|
let previousLineCount = 0;
|
|
80200
81005
|
let previousOutput = "";
|
|
80201
81006
|
let hasHiddenCursor = false;
|
|
80202
|
-
const
|
|
81007
|
+
const render3 = (str) => {
|
|
80203
81008
|
if (!showCursor && !hasHiddenCursor) {
|
|
80204
81009
|
cli_cursor_default.hide();
|
|
80205
81010
|
hasHiddenCursor = true;
|
|
@@ -80212,12 +81017,12 @@ var create = (stream, { showCursor = false } = {}) => {
|
|
|
80212
81017
|
stream.write(base_exports.eraseLines(previousLineCount) + output);
|
|
80213
81018
|
previousLineCount = output.split("\n").length;
|
|
80214
81019
|
};
|
|
80215
|
-
|
|
81020
|
+
render3.clear = () => {
|
|
80216
81021
|
stream.write(base_exports.eraseLines(previousLineCount));
|
|
80217
81022
|
previousOutput = "";
|
|
80218
81023
|
previousLineCount = 0;
|
|
80219
81024
|
};
|
|
80220
|
-
|
|
81025
|
+
render3.done = () => {
|
|
80221
81026
|
previousOutput = "";
|
|
80222
81027
|
previousLineCount = 0;
|
|
80223
81028
|
if (!showCursor) {
|
|
@@ -80225,7 +81030,7 @@ var create = (stream, { showCursor = false } = {}) => {
|
|
|
80225
81030
|
hasHiddenCursor = false;
|
|
80226
81031
|
}
|
|
80227
81032
|
};
|
|
80228
|
-
return
|
|
81033
|
+
return render3;
|
|
80229
81034
|
};
|
|
80230
81035
|
var logUpdate = { create };
|
|
80231
81036
|
var log_update_default = logUpdate;
|
|
@@ -80406,8 +81211,8 @@ function Text({ color, backgroundColor, dimColor = false, bold = false, italic =
|
|
|
80406
81211
|
}
|
|
80407
81212
|
|
|
80408
81213
|
// node_modules/ink/build/components/ErrorOverview.js
|
|
80409
|
-
var cleanupPath = (
|
|
80410
|
-
return
|
|
81214
|
+
var cleanupPath = (path6) => {
|
|
81215
|
+
return path6?.replace(`file://${cwd()}/`, "");
|
|
80411
81216
|
};
|
|
80412
81217
|
var stackUtils = new import_stack_utils.default({
|
|
80413
81218
|
cwd: cwd(),
|
|
@@ -81042,7 +81847,7 @@ var getInstance = (stdout, createInstance) => {
|
|
|
81042
81847
|
// node_modules/ink/build/components/Static.js
|
|
81043
81848
|
var import_react11 = __toESM(require_react(), 1);
|
|
81044
81849
|
function Static(props) {
|
|
81045
|
-
const { items, children:
|
|
81850
|
+
const { items, children: render3, style: customStyle } = props;
|
|
81046
81851
|
const [index, setIndex] = (0, import_react11.useState)(0);
|
|
81047
81852
|
const itemsToRender = (0, import_react11.useMemo)(() => {
|
|
81048
81853
|
return items.slice(index);
|
|
@@ -81051,7 +81856,7 @@ function Static(props) {
|
|
|
81051
81856
|
setIndex(items.length);
|
|
81052
81857
|
}, [items.length]);
|
|
81053
81858
|
const children = itemsToRender.map((item, itemIndex) => {
|
|
81054
|
-
return
|
|
81859
|
+
return render3(item, index + itemIndex);
|
|
81055
81860
|
});
|
|
81056
81861
|
const style = (0, import_react11.useMemo)(() => ({
|
|
81057
81862
|
position: "absolute",
|
|
@@ -81353,9 +82158,9 @@ var import_react21 = __toESM(require_react(), 1);
|
|
|
81353
82158
|
|
|
81354
82159
|
// src/app.jsx
|
|
81355
82160
|
var import_react24 = __toESM(require_react(), 1);
|
|
81356
|
-
import
|
|
81357
|
-
import
|
|
81358
|
-
import
|
|
82161
|
+
import fs4 from "node:fs";
|
|
82162
|
+
import os5 from "node:os";
|
|
82163
|
+
import path3 from "node:path";
|
|
81359
82164
|
|
|
81360
82165
|
// node_modules/ink-spinner/build/index.js
|
|
81361
82166
|
var import_react22 = __toESM(require_react(), 1);
|
|
@@ -83584,124 +84389,16 @@ var MASCOT = [
|
|
|
83584
84389
|
var MASCOT_WIDTH = 10;
|
|
83585
84390
|
|
|
83586
84391
|
// src/banner.js
|
|
83587
|
-
function bannerLines(ev, homeRel2 = (p) => p) {
|
|
84392
|
+
function bannerLines(ev, homeRel2 = (p) => p, mine = "") {
|
|
83588
84393
|
const state = ev.state && ev.state !== "new" && ev.state !== "idle" ? ` \xB7 ${ev.state}` : "";
|
|
84394
|
+
const drift = mine && ev.version && mine !== ev.version ? ` \xB7 you installed ${mine}` : "";
|
|
83589
84395
|
const where = `${homeRel2(ev.cwd || "")}${ev.workspace ? ` \xB7 ${ev.workspace}` : ""}`;
|
|
83590
84396
|
const agents = ev.agents_model ? ` \xB7 agents on ${ev.agents_model}` : "";
|
|
83591
|
-
return [`hum ${ev.version || ""}`.trim() + state, `${ev.model || ""}${agents}${ev.user ? ` \xB7 ${ev.user}` : ""}`, where];
|
|
84397
|
+
return [`hum ${ev.version || ""}`.trim() + drift + state, `${ev.model || ""}${agents}${ev.user ? ` \xB7 ${ev.user}` : ""}`, where];
|
|
83592
84398
|
}
|
|
83593
84399
|
|
|
83594
|
-
// src/
|
|
83595
|
-
|
|
83596
|
-
import os3 from "node:os";
|
|
83597
|
-
import path from "node:path";
|
|
83598
|
-
import { spawn, spawnSync } from "node:child_process";
|
|
83599
|
-
var dist = (env3 = process.env) => (env3.HUM_DIST || "https://storage.googleapis.com/hum-dist").replace(/\/+$/, "");
|
|
83600
|
-
var humHome = (env3 = process.env) => env3.HUM_HOME || path.join(os3.homedir(), ".hum");
|
|
83601
|
-
var win = () => process.platform === "win32";
|
|
83602
|
-
async function latestVersion(fetchImpl = globalThis.fetch, env3 = process.env) {
|
|
83603
|
-
if (env3.HUM_NO_UPDATE_CHECK || typeof fetchImpl !== "function") return "";
|
|
83604
|
-
try {
|
|
83605
|
-
const r = await fetchImpl(`${dist(env3)}/releases/latest`, { signal: AbortSignal.timeout(2500) });
|
|
83606
|
-
if (!r.ok) return "";
|
|
83607
|
-
const v = (await r.text()).trim();
|
|
83608
|
-
return /^\d+\.\d+\.\d+$/.test(v) ? v : "";
|
|
83609
|
-
} catch {
|
|
83610
|
-
return "";
|
|
83611
|
-
}
|
|
83612
|
-
}
|
|
83613
|
-
var newer = (a, b) => {
|
|
83614
|
-
const pa = String(a).split(".").map(Number), pb = String(b).split(".").map(Number);
|
|
83615
|
-
for (let i = 0; i < 3; i += 1) {
|
|
83616
|
-
if ((pa[i] || 0) !== (pb[i] || 0)) return (pa[i] || 0) > (pb[i] || 0);
|
|
83617
|
-
}
|
|
83618
|
-
return false;
|
|
83619
|
-
};
|
|
83620
|
-
function installLayout(execPath = process.execPath, env3 = process.env) {
|
|
83621
|
-
const exe = String(execPath).split(/[\\/]/).pop();
|
|
83622
|
-
if (/^(node|bun)(\.exe)?$/i.test(exe)) return { kind: env3.HUM_ENGINE_PORT ? "python" : "npm" };
|
|
83623
|
-
let real = execPath;
|
|
83624
|
-
try {
|
|
83625
|
-
real = fs2.realpathSync(execPath);
|
|
83626
|
-
} catch {
|
|
83627
|
-
}
|
|
83628
|
-
return { kind: "native", exe, dir: path.dirname(real), base: path.dirname(path.dirname(real)) };
|
|
83629
|
-
}
|
|
83630
|
-
var updateCommand = (layout = installLayout(), platform2 = process.platform) => {
|
|
83631
|
-
if (layout.kind === "native") return platform2 === "win32" ? `irm ${dist()}/install.ps1 | iex` : `curl -fsSL ${dist()}/install.sh | sh`;
|
|
83632
|
-
if (layout.kind === "python") return "uv tool upgrade hum-cli (or: pip install -U hum-cli)";
|
|
83633
|
-
return "npm i -g @metaphi-ai/hum@latest";
|
|
83634
|
-
};
|
|
83635
|
-
var readyVersion = (layout, version) => layout.kind === "native" && version && fs2.existsSync(path.join(layout.base, version, layout.exe)) ? version : "";
|
|
83636
|
-
var stateFile = (env3 = process.env) => path.join(humHome(env3), "update.json");
|
|
83637
|
-
var readState = (env3 = process.env) => {
|
|
83638
|
-
try {
|
|
83639
|
-
return JSON.parse(fs2.readFileSync(stateFile(env3), "utf8"));
|
|
83640
|
-
} catch {
|
|
83641
|
-
return {};
|
|
83642
|
-
}
|
|
83643
|
-
};
|
|
83644
|
-
var writeState = (s, env3 = process.env) => {
|
|
83645
|
-
try {
|
|
83646
|
-
fs2.mkdirSync(humHome(env3), { recursive: true });
|
|
83647
|
-
fs2.writeFileSync(stateFile(env3), JSON.stringify(s));
|
|
83648
|
-
} catch {
|
|
83649
|
-
}
|
|
83650
|
-
};
|
|
83651
|
-
function installerArgv(version, platform2 = process.platform) {
|
|
83652
|
-
const base = dist();
|
|
83653
|
-
if (platform2 === "win32") return ["powershell", ["-NoProfile", "-ExecutionPolicy", "Bypass", "-Command", `irm ${base}/install.ps1 | iex`]];
|
|
83654
|
-
return ["/bin/sh", ["-c", `curl -fsSL "${base}/install.sh" | sh`]];
|
|
83655
|
-
}
|
|
83656
|
-
function startBackgroundUpdate(version, { env: env3 = process.env, now = Date.now(), spawnImpl = spawn } = {}) {
|
|
83657
|
-
if (env3.HUM_NO_AUTO_UPDATE) return false;
|
|
83658
|
-
const s = readState(env3);
|
|
83659
|
-
if (s.version === version && now - (s.started || 0) < 30 * 60 * 1e3) return false;
|
|
83660
|
-
const log = path.join(humHome(env3), "update.log");
|
|
83661
|
-
let out = "ignore";
|
|
83662
|
-
try {
|
|
83663
|
-
fs2.mkdirSync(humHome(env3), { recursive: true });
|
|
83664
|
-
out = fs2.openSync(log, "w");
|
|
83665
|
-
} catch {
|
|
83666
|
-
}
|
|
83667
|
-
const [bin, args2] = installerArgv(version);
|
|
83668
|
-
try {
|
|
83669
|
-
const child = spawnImpl(bin, args2, {
|
|
83670
|
-
detached: true,
|
|
83671
|
-
stdio: ["ignore", out, out],
|
|
83672
|
-
windowsHide: true,
|
|
83673
|
-
env: { ...env3, HUM_VERSION: version, HUM_DIST: dist(env3) }
|
|
83674
|
-
});
|
|
83675
|
-
child.unref();
|
|
83676
|
-
writeState({ version, started: now }, env3);
|
|
83677
|
-
return true;
|
|
83678
|
-
} catch {
|
|
83679
|
-
return false;
|
|
83680
|
-
}
|
|
83681
|
-
}
|
|
83682
|
-
async function updateNotice(mine, { env: env3 = process.env, fetchImpl = globalThis.fetch, layout = installLayout(process.execPath, env3), spawnImpl = spawn } = {}) {
|
|
83683
|
-
const latest = await latestVersion(fetchImpl, env3);
|
|
83684
|
-
if (!latest || !newer(latest, mine)) return "";
|
|
83685
|
-
if (layout.kind !== "native") return `hum ${latest} is out (this is ${mine}) \xB7 ${updateCommand(layout)}`;
|
|
83686
|
-
if (readyVersion(layout, latest)) return `hum ${latest} is ready \xB7 restart hum to use it`;
|
|
83687
|
-
if (startBackgroundUpdate(latest, { env: env3, spawnImpl })) return `hum ${latest} is downloading in the background \xB7 it takes effect the next time you start hum`;
|
|
83688
|
-
const s = readState(env3);
|
|
83689
|
-
if (s.version === latest && !env3.HUM_NO_AUTO_UPDATE) return `hum ${latest} is still installing in the background (${path.join(humHome(env3), "update.log")} has the details)`;
|
|
83690
|
-
return `hum ${latest} is out (this is ${mine}) \xB7 ${updateCommand(layout)}`;
|
|
83691
|
-
}
|
|
83692
|
-
function updateNow(layout = installLayout()) {
|
|
83693
|
-
if (layout.kind === "native") {
|
|
83694
|
-
const [bin, args2] = installerArgv();
|
|
83695
|
-
return spawnSync(bin, args2, { stdio: "inherit", env: { ...process.env, HUM_DIST: dist() } }).status ?? 1;
|
|
83696
|
-
}
|
|
83697
|
-
if (layout.kind === "python") {
|
|
83698
|
-
process.stdout.write(`update with your package manager: ${updateCommand(layout)}
|
|
83699
|
-
`);
|
|
83700
|
-
return 0;
|
|
83701
|
-
}
|
|
83702
|
-
const r = spawnSync(win() ? "npm.cmd" : "npm", ["i", "-g", "@metaphi-ai/hum@latest"], { stdio: "inherit", shell: win() });
|
|
83703
|
-
return r.status ?? 1;
|
|
83704
|
-
}
|
|
84400
|
+
// src/app.jsx
|
|
84401
|
+
init_update();
|
|
83705
84402
|
|
|
83706
84403
|
// src/input.jsx
|
|
83707
84404
|
var import_react23 = __toESM(require_react(), 1);
|
|
@@ -83844,6 +84541,7 @@ var input_default = MultilineInput;
|
|
|
83844
84541
|
|
|
83845
84542
|
// src/app.jsx
|
|
83846
84543
|
var import_jsx_runtime2 = __toESM(require_jsx_runtime(), 1);
|
|
84544
|
+
var MINE = true ? "0.1.30" : "";
|
|
83847
84545
|
var fmtDur = (s) => s < 60 ? `${Math.max(1, Math.round(s))}s` : `${Math.floor(s / 60)}m ${Math.round(s % 60)}s`;
|
|
83848
84546
|
var plural = (n, w) => `${n} ${w}${n === 1 ? "" : "s"}`;
|
|
83849
84547
|
var firstResp = (e) => e.first_response_s ? ` \xB7 first response ${e.first_response_s.toFixed(1)}s` : "";
|
|
@@ -83851,7 +84549,7 @@ var shortSession = (name) => (name || "").replace(/\.jsonl$/, "");
|
|
|
83851
84549
|
var PICKER_ROWS = 8;
|
|
83852
84550
|
var sessionRows = (p, here) => {
|
|
83853
84551
|
const q = p.query.trim().toLowerCase();
|
|
83854
|
-
const all = p.all.map((it) => ({ ...it, dir: it.cwd ?
|
|
84552
|
+
const all = p.all.map((it) => ({ ...it, dir: it.cwd ? path3.basename(it.cwd) : "" }));
|
|
83855
84553
|
const inHere = all.filter((it) => it.cwd && here && it.cwd === here);
|
|
83856
84554
|
const scope = p.scope === "here" && inHere.length ? "here" : "all";
|
|
83857
84555
|
let rows = all;
|
|
@@ -83865,8 +84563,15 @@ var sessionRows = (p, here) => {
|
|
|
83865
84563
|
if (q) rows = rows.filter((it) => [it.instruction, it.dir, it.name, it.model].some((v) => (v || "").toLowerCase().includes(q)));
|
|
83866
84564
|
return { rows, scope };
|
|
83867
84565
|
};
|
|
84566
|
+
var ago = (at) => {
|
|
84567
|
+
const secs = Math.max(0, Date.now() / 1e3 - (at || 0));
|
|
84568
|
+
if (secs < 90) return "just now";
|
|
84569
|
+
if (secs < 3600) return `${Math.floor(secs / 60)}m ago`;
|
|
84570
|
+
if (secs < 86400) return `${Math.floor(secs / 3600)}h ago`;
|
|
84571
|
+
return `${Math.floor(secs / 86400)}d ago`;
|
|
84572
|
+
};
|
|
83868
84573
|
var homeRel = (p) => {
|
|
83869
|
-
const h =
|
|
84574
|
+
const h = os5.homedir();
|
|
83870
84575
|
return p && h && p.startsWith(h) ? "~" + p.slice(h.length) : p;
|
|
83871
84576
|
};
|
|
83872
84577
|
var handEdit = (stat) => {
|
|
@@ -83877,11 +84582,11 @@ var handEdit = (stat) => {
|
|
|
83877
84582
|
${lines.join("\n ")}`;
|
|
83878
84583
|
};
|
|
83879
84584
|
var fmtCost = (c) => c >= 0.01 ? `$${c.toFixed(2)}` : c > 0 ? `$${c.toFixed(4)}` : "$0";
|
|
83880
|
-
var HISTORY_PATH =
|
|
84585
|
+
var HISTORY_PATH = path3.join(os5.homedir(), ".hum", "history.json");
|
|
83881
84586
|
var HISTORY_MAX = 300;
|
|
83882
84587
|
var loadHistory = () => {
|
|
83883
84588
|
try {
|
|
83884
|
-
const a = JSON.parse(
|
|
84589
|
+
const a = JSON.parse(fs4.readFileSync(HISTORY_PATH, "utf8"));
|
|
83885
84590
|
return Array.isArray(a) ? a.filter((x) => typeof x === "string") : [];
|
|
83886
84591
|
} catch {
|
|
83887
84592
|
return [];
|
|
@@ -83889,8 +84594,8 @@ var loadHistory = () => {
|
|
|
83889
84594
|
};
|
|
83890
84595
|
var saveHistory = (arr) => {
|
|
83891
84596
|
try {
|
|
83892
|
-
|
|
83893
|
-
|
|
84597
|
+
fs4.mkdirSync(path3.dirname(HISTORY_PATH), { recursive: true });
|
|
84598
|
+
fs4.writeFileSync(HISTORY_PATH, JSON.stringify(arr.slice(-HISTORY_MAX)));
|
|
83894
84599
|
} catch {
|
|
83895
84600
|
}
|
|
83896
84601
|
};
|
|
@@ -83901,8 +84606,10 @@ var tail = (s, n) => {
|
|
|
83901
84606
|
};
|
|
83902
84607
|
var COMMANDS = [
|
|
83903
84608
|
{ name: "/resume", desc: "pick a past session to continue (this machine or any other)" },
|
|
83904
|
-
{ name: "/compact", desc: "summarise and restart the context now" },
|
|
84609
|
+
{ name: "/compact", desc: "summarise and restart the context now (/compact <what the note should attend to>)" },
|
|
83905
84610
|
{ name: "/model", desc: "switch between the models you can use; /model <name> switches straight away" },
|
|
84611
|
+
{ name: "/diff", desc: "what has changed since this session began (/diff last: the last exchange; /diff <path>: one file)" },
|
|
84612
|
+
{ name: "/rewind", desc: "go back to something you said: the files, the conversation, or both (esc esc opens it too)" },
|
|
83906
84613
|
{ name: "/cost", desc: "tokens and cost so far" },
|
|
83907
84614
|
{ name: "/approve", desc: "approvals on|off \u2014 whether every change and command waits for you first (leaving the sandbox always asks)" },
|
|
83908
84615
|
{ name: "/continue", desc: "after a pause: let the agent carry on" },
|
|
@@ -83916,8 +84623,16 @@ var COMMANDS = [
|
|
|
83916
84623
|
{ name: "/quit", desc: "leave; the session keeps running (hum resume brings you back)" },
|
|
83917
84624
|
{ name: "/stop", desc: "end this session for good (the record is saved)" }
|
|
83918
84625
|
];
|
|
83919
|
-
var HELP = "!cmd runs a command as you \xB7 esc interrupts the model (what it had is kept) \xB7 type while it works to steer \xB7 edit files in your editor any time (recorded as your turn) \xB7 ctrl+o shows the full output of the last tool result \xB7 ctrl+v pastes a screenshot from the clipboard \xB7 @path.png or /image <path> attaches an image file \xB7 commands run in a sandbox (writes in the working directory, no network); leaving it asks you first (enter approves, a typed reason rejects) \xB7 /approve makes every change and command wait for you; at the panel, a allows that shape for the session and p writes it into the project \xB7 /permissions lists the rules in force \xB7 /mcp lists the tool servers \xB7 /resume picks a past session (a running one attaches) \xB7 /compact restarts the context from a summary \xB7 ctrl+c twice leaves and the session keeps running (`hum resume` brings you back) \xB7 /stop ends it";
|
|
84626
|
+
var HELP = "!cmd runs a command as you \xB7 esc interrupts the model (what it had is kept) \xB7 esc twice while it is idle opens the rewind picker \xB7 type while it works to steer \xB7 edit files in your editor any time (recorded as your turn) \xB7 ctrl+o shows the full output of the last tool result \xB7 ctrl+v pastes a screenshot from the clipboard \xB7 @path.png or /image <path> attaches an image file \xB7 commands run in a sandbox (writes in the working directory, no network); leaving it asks you first (enter approves, a typed reason rejects) \xB7 /approve makes every change and command wait for you; at the panel, a allows that shape for the session and p writes it into the project \xB7 /permissions lists the rules in force \xB7 /diff shows what has changed since the session began \xB7 /rewind takes the files or the conversation back to something you said \xB7 /mcp lists the tool servers \xB7 /resume picks a past session (a running one attaches) \xB7 /compact restarts the context from a summary \xB7 ctrl+c twice leaves and the session keeps running (`hum resume` brings you back) \xB7 /stop ends it";
|
|
83920
84627
|
var DIFF_TAIL_LINES = 20;
|
|
84628
|
+
var PATCH_LINES = 200;
|
|
84629
|
+
var ESC_ESC_MS = 800;
|
|
84630
|
+
var REWIND_ROWS = 8;
|
|
84631
|
+
var REWIND_CHOICES = [
|
|
84632
|
+
{ key: "files", label: "restore the files", desc: "the workspace goes back to how it was then" },
|
|
84633
|
+
{ key: "chat", label: "restore the conversation", desc: "hum carries on from what you said, on a new branch; nothing is deleted" },
|
|
84634
|
+
{ key: "both", label: "both", desc: "" }
|
|
84635
|
+
];
|
|
83921
84636
|
var OUTPUT_MAX_LINES = 200;
|
|
83922
84637
|
var ERR_TAIL_LINES = 5;
|
|
83923
84638
|
function App2({ engine: engine2, task, resume, images = [] }) {
|
|
@@ -83944,6 +84659,7 @@ function App2({ engine: engine2, task, resume, images = [] }) {
|
|
|
83944
84659
|
const [qAnswers, setQAnswers] = (0, import_react24.useState)({});
|
|
83945
84660
|
const [qPicks, setQPicks] = (0, import_react24.useState)([]);
|
|
83946
84661
|
const [qCursor, setQCursor] = (0, import_react24.useState)(0);
|
|
84662
|
+
const [confirm, setConfirm] = (0, import_react24.useState)(null);
|
|
83947
84663
|
const [gate, setGate] = (0, import_react24.useState)("off");
|
|
83948
84664
|
const [paused, setPaused] = (0, import_react24.useState)(false);
|
|
83949
84665
|
const attachRef = (0, import_react24.useRef)([]);
|
|
@@ -83961,6 +84677,9 @@ function App2({ engine: engine2, task, resume, images = [] }) {
|
|
|
83961
84677
|
const lastOutRef = (0, import_react24.useRef)(null);
|
|
83962
84678
|
const helloRef = (0, import_react24.useRef)(false);
|
|
83963
84679
|
const startedRef = (0, import_react24.useRef)(false);
|
|
84680
|
+
const escRef = (0, import_react24.useRef)(0);
|
|
84681
|
+
const rewindRef = (0, import_react24.useRef)({ files: true, conversation: true });
|
|
84682
|
+
const wantRow = (0, import_react24.useRef)(null);
|
|
83964
84683
|
const preHello = (0, import_react24.useRef)([]);
|
|
83965
84684
|
const [meter, setMeter] = (0, import_react24.useState)({ tokens: 0, cap: 0, input: 0, output: 0 });
|
|
83966
84685
|
const setPhaseBoth = (p) => {
|
|
@@ -84005,6 +84724,7 @@ function App2({ engine: engine2, task, resume, images = [] }) {
|
|
|
84005
84724
|
setQCursor(0);
|
|
84006
84725
|
setPaused(false);
|
|
84007
84726
|
setPicker(null);
|
|
84727
|
+
setConfirm(null);
|
|
84008
84728
|
setSpend(0);
|
|
84009
84729
|
setGoal(null);
|
|
84010
84730
|
setSession(null);
|
|
@@ -84070,7 +84790,7 @@ function App2({ engine: engine2, task, resume, images = [] }) {
|
|
|
84070
84790
|
setGate(ev.gate === "approve" ? "approve" : "off");
|
|
84071
84791
|
if (ev.session) setSession(ev.session);
|
|
84072
84792
|
if (ev.fresh) append({ kind: "wordmark" });
|
|
84073
|
-
append({ kind: "banner", lines: bannerLines(ev, homeRel), instruction: ev.session ? ev.instruction : null });
|
|
84793
|
+
append({ kind: "banner", lines: bannerLines(ev, homeRel, MINE), instruction: ev.session ? ev.instruction : null });
|
|
84074
84794
|
if (ev.note) append({ kind: "warn", text: ev.note });
|
|
84075
84795
|
setGoal(ev.goal || null);
|
|
84076
84796
|
if (ev.goal) append({ kind: "info", text: `goal: ${ev.goal}` });
|
|
@@ -84299,6 +85019,39 @@ function App2({ engine: engine2, task, resume, images = [] }) {
|
|
|
84299
85019
|
setProposal(null);
|
|
84300
85020
|
append({ kind: "info", text: "approvals off: the waiting proposal ran" });
|
|
84301
85021
|
break;
|
|
85022
|
+
case "diff": {
|
|
85023
|
+
const text = String(ev.text || "");
|
|
85024
|
+
if (!text.trim()) {
|
|
85025
|
+
append({ kind: "info", text: ev.scope === "last" ? "nothing changed in the last exchange" : ev.scope ? `nothing changed in ${ev.scope}` : "nothing has changed since this session began" });
|
|
85026
|
+
break;
|
|
85027
|
+
}
|
|
85028
|
+
const ls = text.split("\n");
|
|
85029
|
+
const stat = String(ev.stat || "").split("\n").filter((l) => l.trim()).pop() || "";
|
|
85030
|
+
append({ kind: "patch", lines: ls.slice(0, PATCH_LINES), more: Math.max(0, ls.length - PATCH_LINES), stat });
|
|
85031
|
+
break;
|
|
85032
|
+
}
|
|
85033
|
+
case "rewind_list": {
|
|
85034
|
+
const items2 = ev.items || [];
|
|
85035
|
+
if (!items2.length) {
|
|
85036
|
+
append({ kind: "info", text: "nothing to go back to yet" });
|
|
85037
|
+
break;
|
|
85038
|
+
}
|
|
85039
|
+
const want = items2.findIndex((it) => it.n === wantRow.current);
|
|
85040
|
+
wantRow.current = null;
|
|
85041
|
+
setPicker({ kind: "rewind", items: items2, index: want >= 0 ? want : items2.length - 1, top: 0, choice: null });
|
|
85042
|
+
break;
|
|
85043
|
+
}
|
|
85044
|
+
case "rewind_confirm":
|
|
85045
|
+
setPicker(null);
|
|
85046
|
+
setConfirm({ node: ev.node, said: ev.said || "", stat: ev.stat || "", why: ev.why || "" });
|
|
85047
|
+
break;
|
|
85048
|
+
case "rewind": {
|
|
85049
|
+
setConfirm(null);
|
|
85050
|
+
const did = [ev.files ? "the files" : null, ev.conversation ? "the conversation" : null].filter(Boolean).join(" and ");
|
|
85051
|
+
append({ kind: "info", text: `back to \u201C${(ev.said || "").slice(0, 60)}\u201D \xB7 ${did} restored` });
|
|
85052
|
+
if (ev.stat) append({ kind: "info", text: ` ${String(ev.stat).split("\n").filter((l) => l.trim()).join("\n ")}` });
|
|
85053
|
+
break;
|
|
85054
|
+
}
|
|
84302
85055
|
case "goal":
|
|
84303
85056
|
setGoal(ev.text || null);
|
|
84304
85057
|
append({ kind: "info", text: ev.text ? `goal: ${ev.text}` : "goal cleared" });
|
|
@@ -84375,7 +85128,7 @@ function App2({ engine: engine2, task, resume, images = [] }) {
|
|
|
84375
85128
|
(0, import_react24.useEffect)(() => {
|
|
84376
85129
|
if (!hello) return void 0;
|
|
84377
85130
|
let live = true;
|
|
84378
|
-
updateNotice(
|
|
85131
|
+
updateNotice(MINE || hello.version || "0.0.0", { running: hello.version || "" }).then((line) => {
|
|
84379
85132
|
if (live && line) append({ kind: "info", text: line });
|
|
84380
85133
|
}).catch(() => {
|
|
84381
85134
|
});
|
|
@@ -84423,6 +85176,47 @@ function App2({ engine: engine2, task, resume, images = [] }) {
|
|
|
84423
85176
|
}
|
|
84424
85177
|
return;
|
|
84425
85178
|
}
|
|
85179
|
+
if (confirm && !picker) {
|
|
85180
|
+
if (key.return) {
|
|
85181
|
+
setConfirm(null);
|
|
85182
|
+
engine2.send({ cmd: "rewind", to: confirm.node, ...rewindRef.current, confirm: true });
|
|
85183
|
+
return;
|
|
85184
|
+
}
|
|
85185
|
+
if (key.escape) {
|
|
85186
|
+
setConfirm(null);
|
|
85187
|
+
append({ kind: "info", text: "left as it is" });
|
|
85188
|
+
return;
|
|
85189
|
+
}
|
|
85190
|
+
return;
|
|
85191
|
+
}
|
|
85192
|
+
if (picker && picker.kind === "rewind") {
|
|
85193
|
+
if (picker.choice === null) {
|
|
85194
|
+
const n = picker.items.length;
|
|
85195
|
+
const move = (d) => setPicker((pk) => {
|
|
85196
|
+
const index = (pk.index + d + n) % n;
|
|
85197
|
+
const top = index < pk.top ? index : index >= pk.top + REWIND_ROWS ? index - REWIND_ROWS + 1 : pk.top;
|
|
85198
|
+
return { ...pk, index, top };
|
|
85199
|
+
});
|
|
85200
|
+
if (key.upArrow) move(-1);
|
|
85201
|
+
else if (key.downArrow || key.tab) move(1);
|
|
85202
|
+
else if (key.escape) setPicker(null);
|
|
85203
|
+
else if (key.return) setPicker((pk) => ({ ...pk, choice: 0 }));
|
|
85204
|
+
return;
|
|
85205
|
+
}
|
|
85206
|
+
const pick = (c) => {
|
|
85207
|
+
const it = picker.items[picker.index];
|
|
85208
|
+
setPicker(null);
|
|
85209
|
+
if (!it) return;
|
|
85210
|
+
rewindRef.current = { files: c !== "chat", conversation: c !== "files" };
|
|
85211
|
+
engine2.send({ cmd: "rewind", to: it.node, ...rewindRef.current });
|
|
85212
|
+
};
|
|
85213
|
+
if (key.upArrow) setPicker((pk) => ({ ...pk, choice: (pk.choice + REWIND_CHOICES.length - 1) % REWIND_CHOICES.length }));
|
|
85214
|
+
else if (key.downArrow || key.tab) setPicker((pk) => ({ ...pk, choice: (pk.choice + 1) % REWIND_CHOICES.length }));
|
|
85215
|
+
else if (key.escape) setPicker((pk) => ({ ...pk, choice: null }));
|
|
85216
|
+
else if (key.return) pick(REWIND_CHOICES[picker.choice].key);
|
|
85217
|
+
else if (/^[1-3]$/.test(input)) pick(REWIND_CHOICES[Number(input) - 1].key);
|
|
85218
|
+
return;
|
|
85219
|
+
}
|
|
84426
85220
|
if (proposal && !picker) {
|
|
84427
85221
|
if (key.return && !value.trim()) {
|
|
84428
85222
|
decide("accept");
|
|
@@ -84519,7 +85313,20 @@ function App2({ engine: engine2, task, resume, images = [] }) {
|
|
|
84519
85313
|
else if (key.tab) setValue(menu[Math.min(menuIndex, menu.length - 1)].name + " ");
|
|
84520
85314
|
return;
|
|
84521
85315
|
}
|
|
84522
|
-
if (key.escape
|
|
85316
|
+
if (key.escape) {
|
|
85317
|
+
if (phaseRef.current === "busy") {
|
|
85318
|
+
engine2.send({ cmd: "interrupt" });
|
|
85319
|
+
escRef.current = 0;
|
|
85320
|
+
return;
|
|
85321
|
+
}
|
|
85322
|
+
const now = Date.now();
|
|
85323
|
+
if (now - escRef.current < ESC_ESC_MS) {
|
|
85324
|
+
escRef.current = 0;
|
|
85325
|
+
engine2.send({ cmd: "rewind_list" });
|
|
85326
|
+
return;
|
|
85327
|
+
}
|
|
85328
|
+
escRef.current = now;
|
|
85329
|
+
}
|
|
84523
85330
|
});
|
|
84524
85331
|
(0, import_react24.useEffect)(() => {
|
|
84525
85332
|
setMenuIndex(0);
|
|
@@ -84587,7 +85394,7 @@ function App2({ engine: engine2, task, resume, images = [] }) {
|
|
|
84587
85394
|
engine2.send({ cmd: "sessions" });
|
|
84588
85395
|
break;
|
|
84589
85396
|
case "/compact":
|
|
84590
|
-
engine2.send({ cmd: "compact" });
|
|
85397
|
+
engine2.send(arg ? { cmd: "compact", text: arg } : { cmd: "compact" });
|
|
84591
85398
|
break;
|
|
84592
85399
|
case "/model":
|
|
84593
85400
|
if (arg) {
|
|
@@ -84595,6 +85402,13 @@ function App2({ engine: engine2, task, resume, images = [] }) {
|
|
|
84595
85402
|
engine2.send({ cmd: "model", name: arg });
|
|
84596
85403
|
} else engine2.send({ cmd: "model" });
|
|
84597
85404
|
break;
|
|
85405
|
+
case "/diff":
|
|
85406
|
+
engine2.send({ cmd: "diff", scope: arg });
|
|
85407
|
+
break;
|
|
85408
|
+
case "/rewind":
|
|
85409
|
+
wantRow.current = /^\d+$/.test(arg) ? Number(arg) : null;
|
|
85410
|
+
engine2.send({ cmd: "rewind_list" });
|
|
85411
|
+
break;
|
|
84598
85412
|
case "/cost": {
|
|
84599
85413
|
const ctx = ctxPct > 0 ? ` \xB7 context ${ctxPct}% of the compaction threshold` : "";
|
|
84600
85414
|
append({ kind: "info", text: `${fmtCost(spend)} this session \xB7 ${meter.input.toLocaleString()}+${meter.output.toLocaleString()} tokens${ctx}` });
|
|
@@ -84772,6 +85586,19 @@ function App2({ engine: engine2, task, resume, images = [] }) {
|
|
|
84772
85586
|
)),
|
|
84773
85587
|
item.more > 0 ? /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { dimColor: true, children: `\u2026 +${item.more} more diff lines` }) : null
|
|
84774
85588
|
] }),
|
|
85589
|
+
item.kind === "patch" && /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(Box_default, { flexDirection: "column", paddingLeft: 2, children: [
|
|
85590
|
+
item.lines.map((l, i) => /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(
|
|
85591
|
+
Text,
|
|
85592
|
+
{
|
|
85593
|
+
color: l.startsWith("+") ? "green" : l.startsWith("-") ? "red" : l.startsWith("@@") ? "cyan" : void 0,
|
|
85594
|
+
dimColor: !l.startsWith("+") && !l.startsWith("-"),
|
|
85595
|
+
children: l || " "
|
|
85596
|
+
},
|
|
85597
|
+
i
|
|
85598
|
+
)),
|
|
85599
|
+
item.more > 0 ? /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { dimColor: true, children: `\u2026 +${item.more} more lines \xB7 /diff <path> narrows it` }) : null,
|
|
85600
|
+
item.stat ? /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { dimColor: true, children: item.stat.trim() }) : null
|
|
85601
|
+
] }),
|
|
84775
85602
|
item.kind === "errtail" && /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Box_default, { flexDirection: "column", paddingLeft: 6, children: item.lines.map((l, i) => /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { color: "red", dimColor: true, children: l }, i)) }),
|
|
84776
85603
|
item.kind === "output" && /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(Box_default, { flexDirection: "column", paddingLeft: 4, children: [
|
|
84777
85604
|
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { dimColor: true, children: `full output \xB7 ${item.name}` }),
|
|
@@ -84909,6 +85736,73 @@ function App2({ engine: engine2, task, resume, images = [] }) {
|
|
|
84909
85736
|
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { children: " " }),
|
|
84910
85737
|
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { dimColor: true, children: "Enter to switch \xB7 Esc to cancel" })
|
|
84911
85738
|
] }),
|
|
85739
|
+
confirm && /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(Box_default, { flexDirection: "column", borderStyle: "round", borderColor: "yellow", paddingX: 1, marginTop: 1, children: [
|
|
85740
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(Text, { color: "yellow", bold: true, children: [
|
|
85741
|
+
"\u23EE ",
|
|
85742
|
+
confirm.why || "the workspace has changed since hum last looked"
|
|
85743
|
+
] }),
|
|
85744
|
+
String(confirm.stat || "").split("\n").filter((l) => l.trim()).slice(0, 8).map((l, i) => /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(Text, { dimColor: true, children: [
|
|
85745
|
+
" ",
|
|
85746
|
+
l
|
|
85747
|
+
] }, i)),
|
|
85748
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { dimColor: true, children: "they are kept in this session's history and can be found again \xB7 enter goes back anyway \xB7 esc leaves it as it is" })
|
|
85749
|
+
] }),
|
|
85750
|
+
picker && picker.kind === "rewind" && (() => {
|
|
85751
|
+
const it = picker.items[picker.index];
|
|
85752
|
+
if (picker.choice !== null) {
|
|
85753
|
+
return /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(Box_default, { flexDirection: "column", paddingX: 1, marginTop: 1, children: [
|
|
85754
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(Text, { color: ACCENT, bold: true, children: [
|
|
85755
|
+
"Rewind to ",
|
|
85756
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { color: "white", children: `\u201C${(it?.said || "").slice(0, width - 24)}\u201D` })
|
|
85757
|
+
] }),
|
|
85758
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { children: " " }),
|
|
85759
|
+
REWIND_CHOICES.map((c, i) => /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(Box_default, { children: [
|
|
85760
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { color: ACCENT, children: i === picker.choice ? "\u276F " : " " }),
|
|
85761
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(Text, { bold: i === picker.choice, children: [
|
|
85762
|
+
i + 1,
|
|
85763
|
+
". ",
|
|
85764
|
+
c.label.padEnd(26)
|
|
85765
|
+
] }),
|
|
85766
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { dimColor: true, children: c.desc })
|
|
85767
|
+
] }, c.key)),
|
|
85768
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { children: " " }),
|
|
85769
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { dimColor: true, children: "Enter to go back \xB7 Esc for the list again" })
|
|
85770
|
+
] });
|
|
85771
|
+
}
|
|
85772
|
+
const top = Math.min(picker.top, Math.max(0, picker.items.length - REWIND_ROWS));
|
|
85773
|
+
return /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(Box_default, { flexDirection: "column", paddingX: 1, marginTop: 1, children: [
|
|
85774
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(Text, { color: ACCENT, bold: true, children: [
|
|
85775
|
+
"Rewind ",
|
|
85776
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { dimColor: true, children: `(${picker.index + 1} of ${picker.items.length})` })
|
|
85777
|
+
] }),
|
|
85778
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { dimColor: true, children: "Every checkpoint is something you said. Nothing is deleted: what you go back past stays in the session." }),
|
|
85779
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { children: " " }),
|
|
85780
|
+
picker.items.slice(top, top + REWIND_ROWS).map((c, j) => {
|
|
85781
|
+
const i = top + j;
|
|
85782
|
+
const sel = i === picker.index;
|
|
85783
|
+
const meta = [`${c.steps} ${c.steps === 1 ? "step" : "steps"}`, c.files ? `${c.files} ${c.files === 1 ? "file" : "files"} changed since` : null].filter(Boolean).join(" \xB7 ");
|
|
85784
|
+
const said = (c.said || "(nothing said)").replace(/\s+/g, " ");
|
|
85785
|
+
const room = Math.max(16, width - 26);
|
|
85786
|
+
return /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(Box_default, { flexDirection: "column", children: [
|
|
85787
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(Text, { children: [
|
|
85788
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { color: ACCENT, children: sel ? "\u276F " : " " }),
|
|
85789
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(Text, { dimColor: true, children: [
|
|
85790
|
+
String(ago(c.at)).padStart(9),
|
|
85791
|
+
" "
|
|
85792
|
+
] }),
|
|
85793
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { bold: sel, color: sel ? ACCENT : void 0, children: said.length > room ? said.slice(0, room - 1) + "\u2026" : said })
|
|
85794
|
+
] }),
|
|
85795
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(Text, { dimColor: true, children: [
|
|
85796
|
+
" ",
|
|
85797
|
+
meta
|
|
85798
|
+
] })
|
|
85799
|
+
] }, c.node);
|
|
85800
|
+
}),
|
|
85801
|
+
top + REWIND_ROWS < picker.items.length ? /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { dimColor: true, children: `\u2193 ${picker.items.length - top - REWIND_ROWS} more` }) : null,
|
|
85802
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { children: " " }),
|
|
85803
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(Text, { dimColor: true, children: "Enter to choose what comes back \xB7 Esc to cancel" })
|
|
85804
|
+
] });
|
|
85805
|
+
})(),
|
|
84912
85806
|
picker && picker.kind === "session" && (() => {
|
|
84913
85807
|
const { rows, scope } = sessionRows(picker, hello?.cwd);
|
|
84914
85808
|
const top = Math.min(picker.top, Math.max(0, rows.length - PICKER_ROWS));
|
|
@@ -84970,7 +85864,7 @@ function App2({ engine: engine2, task, resume, images = [] }) {
|
|
|
84970
85864
|
value,
|
|
84971
85865
|
onChange: setValue,
|
|
84972
85866
|
onSubmit,
|
|
84973
|
-
focus: phase !== "dead" && !picker,
|
|
85867
|
+
focus: phase !== "dead" && !picker && !confirm,
|
|
84974
85868
|
navActive: menu.length === 0,
|
|
84975
85869
|
history: historyRef.current,
|
|
84976
85870
|
mask: !!(step && step.secret),
|
|
@@ -84999,293 +85893,48 @@ function App2({ engine: engine2, task, resume, images = [] }) {
|
|
|
84999
85893
|
] });
|
|
85000
85894
|
}
|
|
85001
85895
|
|
|
85002
|
-
// src/engine.js
|
|
85003
|
-
import fs4 from "node:fs";
|
|
85004
|
-
import net from "node:net";
|
|
85005
|
-
import os5 from "node:os";
|
|
85006
|
-
import path3 from "node:path";
|
|
85007
|
-
import crypto from "node:crypto";
|
|
85008
|
-
import { spawn as spawn2, spawnSync as spawnSync2 } from "node:child_process";
|
|
85009
|
-
var runDir = () => path3.join(process.env.HUM_HOME || path3.join(os5.homedir(), ".hum"), "run");
|
|
85010
|
-
var readRun = (id) => {
|
|
85011
|
-
try {
|
|
85012
|
-
return JSON.parse(fs4.readFileSync(path3.join(runDir(), `${id}.json`), "utf8"));
|
|
85013
|
-
} catch {
|
|
85014
|
-
return null;
|
|
85015
|
-
}
|
|
85016
|
-
};
|
|
85017
|
-
var EngineError = class extends Error {
|
|
85018
|
-
};
|
|
85019
|
-
var win2 = process.platform === "win32";
|
|
85020
|
-
var exists = (p) => {
|
|
85021
|
-
try {
|
|
85022
|
-
fs4.accessSync(p);
|
|
85023
|
-
return true;
|
|
85024
|
-
} catch {
|
|
85025
|
-
return false;
|
|
85026
|
-
}
|
|
85027
|
-
};
|
|
85028
|
-
function uvToolDirs() {
|
|
85029
|
-
const dirs = [];
|
|
85030
|
-
if (process.env.UV_TOOL_DIR) dirs.push(process.env.UV_TOOL_DIR);
|
|
85031
|
-
if (win2) {
|
|
85032
|
-
for (const base of [process.env.APPDATA, process.env.LOCALAPPDATA]) if (base) dirs.push(path3.join(base, "uv", "tools"));
|
|
85033
|
-
} else dirs.push(path3.join(process.env.XDG_DATA_HOME || path3.join(os5.homedir(), ".local", "share"), "uv", "tools"));
|
|
85034
|
-
if (!dirs.some(exists)) {
|
|
85035
|
-
for (const uv of ["uv", path3.join(os5.homedir(), ".local", "bin", win2 ? "uv.exe" : "uv")]) {
|
|
85036
|
-
try {
|
|
85037
|
-
const r = spawnSync2(uv, ["tool", "dir"], { encoding: "utf8", windowsHide: true });
|
|
85038
|
-
if (r.status === 0 && r.stdout.trim()) {
|
|
85039
|
-
dirs.push(r.stdout.trim());
|
|
85040
|
-
break;
|
|
85041
|
-
}
|
|
85042
|
-
} catch {
|
|
85043
|
-
}
|
|
85044
|
-
}
|
|
85045
|
-
}
|
|
85046
|
-
return dirs;
|
|
85047
|
-
}
|
|
85048
|
-
function enginePython(dirs = uvToolDirs()) {
|
|
85049
|
-
for (const dir of dirs) for (const name of ["hum-cli", "hum"]) {
|
|
85050
|
-
const py = win2 ? path3.join(dir, name, "Scripts", "python.exe") : path3.join(dir, name, "bin", "python");
|
|
85051
|
-
if (exists(py)) return py;
|
|
85052
|
-
}
|
|
85053
|
-
return null;
|
|
85054
|
-
}
|
|
85055
|
-
function siblingEngine(execPath = process.execPath) {
|
|
85056
|
-
let dir;
|
|
85057
|
-
try {
|
|
85058
|
-
dir = path3.dirname(fs4.realpathSync(execPath));
|
|
85059
|
-
} catch {
|
|
85060
|
-
return null;
|
|
85061
|
-
}
|
|
85062
|
-
const p = path3.join(dir, "engine", win2 ? "hum-engine.exe" : "hum-engine");
|
|
85063
|
-
return exists(p) ? p : null;
|
|
85064
|
-
}
|
|
85065
|
-
function homeEngine(env3 = process.env) {
|
|
85066
|
-
const home = env3.HUM_HOME || path3.join(os5.homedir(), ".hum");
|
|
85067
|
-
const py = win2 ? path3.join(home, "engine", "Scripts", "python.exe") : path3.join(home, "engine", "bin", "python");
|
|
85068
|
-
return exists(py) ? py : null;
|
|
85069
|
-
}
|
|
85070
|
-
function engineCandidates(env3 = process.env) {
|
|
85071
|
-
const out = [];
|
|
85072
|
-
if (env3.HUM_ENGINE) {
|
|
85073
|
-
const [bin, ...args2] = env3.HUM_ENGINE.split(" ");
|
|
85074
|
-
out.push({ bin, args: args2, where: "HUM_ENGINE" });
|
|
85075
|
-
}
|
|
85076
|
-
const sib = siblingEngine();
|
|
85077
|
-
if (sib) out.push({ bin: sib, args: ["engine"], where: "beside hum" });
|
|
85078
|
-
const home = homeEngine(env3);
|
|
85079
|
-
if (home) out.push({ bin: home, args: ["-m", "hum.cli", "engine"], where: "HUM_HOME/engine" });
|
|
85080
|
-
const py = enginePython();
|
|
85081
|
-
if (py) out.push({ bin: py, args: ["-m", "hum.cli", "engine"], where: "the engine's interpreter" });
|
|
85082
|
-
out.push({ bin: "hum-engine", args: [], where: "PATH" });
|
|
85083
|
-
out.push({ bin: path3.join(os5.homedir(), ".local", "bin", win2 ? "hum-engine.exe" : "hum-engine"), args: [], where: "uv's bin dir" });
|
|
85084
|
-
return out;
|
|
85085
|
-
}
|
|
85086
|
-
function engineCommand(argv, candidates = engineCandidates()) {
|
|
85087
|
-
for (const c of candidates) {
|
|
85088
|
-
if (c.args[c.args.length - 1] !== "engine") continue;
|
|
85089
|
-
return { bin: c.bin, args: [...c.args.slice(0, -1), ...argv], where: c.where };
|
|
85090
|
-
}
|
|
85091
|
-
return null;
|
|
85092
|
-
}
|
|
85093
|
-
function startFailure(failures) {
|
|
85094
|
-
const refused = failures.find((f) => f.error && f.error.code !== "ENOENT");
|
|
85095
|
-
if (!refused) {
|
|
85096
|
-
return "Hum's engine is not installed. Run: uv tool install hum-cli (or set HUM_ENGINE to the command that starts it)";
|
|
85097
|
-
}
|
|
85098
|
-
const what = refused.error.code || refused.error.message;
|
|
85099
|
-
const lines = [
|
|
85100
|
-
`Hum's engine is installed (${refused.bin}) but this machine would not start it: ${what}.`
|
|
85101
|
-
];
|
|
85102
|
-
if (win2) {
|
|
85103
|
-
lines.push("On a managed Windows machine that is usually Device Guard / WDAC refusing an executable it does not know.");
|
|
85104
|
-
lines.push(`To see the policy's own message, run: "${refused.bin}" --help`);
|
|
85105
|
-
const dir = uvToolDirs()[0];
|
|
85106
|
-
lines.push(`If uv's environment is elsewhere, point Hum at its interpreter: set HUM_ENGINE=${path3.join(dir || "<uv tool dir>", "hum-cli", "Scripts", "python.exe")} -m hum.cli engine`);
|
|
85107
|
-
} else {
|
|
85108
|
-
lines.push('Set HUM_ENGINE to a command that starts it, e.g. HUM_ENGINE="python -m hum.cli engine"');
|
|
85109
|
-
}
|
|
85110
|
-
return lines.join("\n");
|
|
85111
|
-
}
|
|
85112
|
-
function attempt({ bin, args: args2 }, cwd2, { task, images, resume }) {
|
|
85113
|
-
return new Promise((resolve, reject) => {
|
|
85114
|
-
const runId = crypto.randomBytes(6).toString("hex");
|
|
85115
|
-
fs4.mkdirSync(runDir(), { recursive: true });
|
|
85116
|
-
const logPath = path3.join(runDir(), `${runId}.log`);
|
|
85117
|
-
const log = fs4.openSync(logPath, "a");
|
|
85118
|
-
const argv = [...args2, "-C", cwd2, "--run-id", runId];
|
|
85119
|
-
if (task) argv.push("--task", task);
|
|
85120
|
-
for (const p of images) argv.push("--image", p);
|
|
85121
|
-
if (resume) argv.push("--resume", resume);
|
|
85122
|
-
let settled = false;
|
|
85123
|
-
const settle = (fn) => {
|
|
85124
|
-
if (!settled) {
|
|
85125
|
-
settled = true;
|
|
85126
|
-
fn();
|
|
85127
|
-
}
|
|
85128
|
-
};
|
|
85129
|
-
let child;
|
|
85130
|
-
try {
|
|
85131
|
-
child = spawn2(bin, argv, { stdio: ["ignore", log, log], detached: true, windowsHide: true });
|
|
85132
|
-
} catch (e) {
|
|
85133
|
-
fs4.closeSync(log);
|
|
85134
|
-
reject({ spawn: e });
|
|
85135
|
-
return;
|
|
85136
|
-
}
|
|
85137
|
-
fs4.closeSync(log);
|
|
85138
|
-
let died = false;
|
|
85139
|
-
child.on("error", (e) => settle(() => reject({ spawn: e })));
|
|
85140
|
-
child.on("exit", () => {
|
|
85141
|
-
died = true;
|
|
85142
|
-
});
|
|
85143
|
-
const t0 = Date.now();
|
|
85144
|
-
const poll = () => {
|
|
85145
|
-
if (settled) return;
|
|
85146
|
-
const rec = readRun(runId);
|
|
85147
|
-
if (rec && rec.port) {
|
|
85148
|
-
child.unref();
|
|
85149
|
-
settle(() => resolve(rec));
|
|
85150
|
-
return;
|
|
85151
|
-
}
|
|
85152
|
-
if (rec && rec.error) {
|
|
85153
|
-
settle(() => reject({ failed: rec.error }));
|
|
85154
|
-
return;
|
|
85155
|
-
}
|
|
85156
|
-
if (died && !rec) {
|
|
85157
|
-
settle(() => reject({ died: logPath }));
|
|
85158
|
-
return;
|
|
85159
|
-
}
|
|
85160
|
-
if (Date.now() - t0 > 9e4) {
|
|
85161
|
-
settle(() => reject({ timeout: true }));
|
|
85162
|
-
return;
|
|
85163
|
-
}
|
|
85164
|
-
setTimeout(poll, 50);
|
|
85165
|
-
};
|
|
85166
|
-
poll();
|
|
85167
|
-
});
|
|
85168
|
-
}
|
|
85169
|
-
function failureMessage(error) {
|
|
85170
|
-
return error.message + (error.hint ? `
|
|
85171
|
-
${error.hint}` : "");
|
|
85172
|
-
}
|
|
85173
|
-
function diedMessage(logPath, text = null) {
|
|
85174
|
-
let tail2 = "";
|
|
85175
|
-
try {
|
|
85176
|
-
tail2 = (text ?? fs4.readFileSync(logPath, "utf8")).trim().split("\n").slice(-3).join("\n").trim();
|
|
85177
|
-
} catch {
|
|
85178
|
-
}
|
|
85179
|
-
return `the engine did not start${tail2 ? `:
|
|
85180
|
-
${tail2}` : ""}
|
|
85181
|
-
(its log: ${logPath})`;
|
|
85182
|
-
}
|
|
85183
|
-
async function spawnEngine(cwd2, { task = null, images = [], resume = null, candidates = engineCandidates() } = {}) {
|
|
85184
|
-
const failures = [];
|
|
85185
|
-
for (const cand of candidates) {
|
|
85186
|
-
if (!cand.bin) continue;
|
|
85187
|
-
try {
|
|
85188
|
-
return await attempt(cand, cwd2, { task, images, resume });
|
|
85189
|
-
} catch (f) {
|
|
85190
|
-
if (f && f.spawn) {
|
|
85191
|
-
failures.push({ ...cand, error: f.spawn });
|
|
85192
|
-
continue;
|
|
85193
|
-
}
|
|
85194
|
-
if (f && f.failed) throw new EngineError(failureMessage(f.failed));
|
|
85195
|
-
if (f && f.died) throw new EngineError(diedMessage(f.died));
|
|
85196
|
-
if (f && f.timeout) throw new EngineError("the engine did not start in time");
|
|
85197
|
-
throw f;
|
|
85198
|
-
}
|
|
85199
|
-
}
|
|
85200
|
-
throw new EngineError(startFailure(failures));
|
|
85201
|
-
}
|
|
85202
|
-
var Engine = class {
|
|
85203
|
-
constructor(port2) {
|
|
85204
|
-
this.port = port2;
|
|
85205
|
-
this.handlers = [];
|
|
85206
|
-
this.closed = false;
|
|
85207
|
-
}
|
|
85208
|
-
connect() {
|
|
85209
|
-
return new Promise((resolve, reject) => {
|
|
85210
|
-
const sock = net.createConnection({ host: "127.0.0.1", port: this.port }, () => resolve());
|
|
85211
|
-
this.sock = sock;
|
|
85212
|
-
sock.on("error", (e) => {
|
|
85213
|
-
if (!this.closed && this.sock === sock) reject(new EngineError(`engine: ${e.message}`));
|
|
85214
|
-
});
|
|
85215
|
-
let buf = "";
|
|
85216
|
-
sock.on("data", (d) => {
|
|
85217
|
-
if (this.sock !== sock) return;
|
|
85218
|
-
buf += d.toString();
|
|
85219
|
-
const lines = buf.split("\n");
|
|
85220
|
-
buf = lines.pop();
|
|
85221
|
-
for (const line of lines) {
|
|
85222
|
-
if (!line.trim()) continue;
|
|
85223
|
-
let ev;
|
|
85224
|
-
try {
|
|
85225
|
-
ev = JSON.parse(line);
|
|
85226
|
-
} catch {
|
|
85227
|
-
continue;
|
|
85228
|
-
}
|
|
85229
|
-
for (const h of this.handlers) h(ev);
|
|
85230
|
-
}
|
|
85231
|
-
});
|
|
85232
|
-
sock.on("close", () => {
|
|
85233
|
-
if (this.sock !== sock) return;
|
|
85234
|
-
this.closed = true;
|
|
85235
|
-
for (const h of this.handlers) h({ type: "bye", gone: true });
|
|
85236
|
-
});
|
|
85237
|
-
});
|
|
85238
|
-
}
|
|
85239
|
-
// Attach to another engine (a session running elsewhere on this machine): the old
|
|
85240
|
-
// socket is dropped quietly, the new one greets us with hello and a replay.
|
|
85241
|
-
async reconnect(port2) {
|
|
85242
|
-
const old = this.sock;
|
|
85243
|
-
this.sock = null;
|
|
85244
|
-
this.port = port2;
|
|
85245
|
-
this.closed = false;
|
|
85246
|
-
try {
|
|
85247
|
-
old.destroy();
|
|
85248
|
-
} catch {
|
|
85249
|
-
}
|
|
85250
|
-
await this.connect();
|
|
85251
|
-
}
|
|
85252
|
-
on(handler) {
|
|
85253
|
-
this.handlers.push(handler);
|
|
85254
|
-
}
|
|
85255
|
-
send(cmd) {
|
|
85256
|
-
if (this.closed) return;
|
|
85257
|
-
try {
|
|
85258
|
-
this.sock.write(JSON.stringify(cmd) + "\n");
|
|
85259
|
-
} catch {
|
|
85260
|
-
}
|
|
85261
|
-
}
|
|
85262
|
-
close() {
|
|
85263
|
-
this.closed = true;
|
|
85264
|
-
try {
|
|
85265
|
-
this.sock.end();
|
|
85266
|
-
} catch {
|
|
85267
|
-
}
|
|
85268
|
-
}
|
|
85269
|
-
};
|
|
85270
|
-
|
|
85271
85896
|
// src/cli.jsx
|
|
85897
|
+
init_engine();
|
|
85898
|
+
init_update();
|
|
85899
|
+
init_install();
|
|
85272
85900
|
var import_jsx_runtime3 = __toESM(require_jsx_runtime(), 1);
|
|
85273
|
-
import { spawnSync as
|
|
85901
|
+
import { spawnSync as spawnSync5 } from "node:child_process";
|
|
85902
|
+
var MINE2 = true ? "0.1.30" : "0.0.0";
|
|
85903
|
+
var layout = installLayout();
|
|
85904
|
+
function completeInstall() {
|
|
85905
|
+
if (layout.kind !== "npm" || !needsInstall(MINE2)) return;
|
|
85906
|
+
const say = (m) => process.stderr.write(`hum: ${m}
|
|
85907
|
+
`);
|
|
85908
|
+
say(`updating to ${MINE2} \u2026`);
|
|
85909
|
+
const r = installEngine(MINE2, { say });
|
|
85910
|
+
if (!r.ok) say(`the update did not finish: ${r.error} \xB7 ${npmFix(MINE2)}`);
|
|
85911
|
+
}
|
|
85274
85912
|
var ENGINE_COMMANDS = /* @__PURE__ */ new Set(["run", "login", "logout", "whoami", "model", "key", "sessions", "show", "sync", "skill", "ps", "stop", "hooks", "engine"]);
|
|
85275
85913
|
var argv0 = process.argv.slice(2);
|
|
85276
85914
|
if (argv0[0] === "--version" || argv0[0] === "-V") {
|
|
85277
|
-
process.stdout.write(`hum ${
|
|
85915
|
+
process.stdout.write(`hum ${MINE2}
|
|
85916
|
+
`);
|
|
85917
|
+
if (layout.kind === "npm") {
|
|
85918
|
+
const r = runningVersion();
|
|
85919
|
+
const drift = mismatchLine(MINE2, r ? r.version : "", { layout });
|
|
85920
|
+
if (drift) process.stdout.write(`${drift}
|
|
85278
85921
|
`);
|
|
85922
|
+
}
|
|
85279
85923
|
process.exit(0);
|
|
85280
85924
|
}
|
|
85281
85925
|
if (argv0[0] === "update") process.exit(updateNow());
|
|
85926
|
+
if (argv0[0] === "doctor") {
|
|
85927
|
+
const { doctor: doctor2 } = await Promise.resolve().then(() => (init_doctor(), doctor_exports));
|
|
85928
|
+
process.exit(await doctor2({ json: argv0.includes("--json"), mine: MINE2, layout }));
|
|
85929
|
+
}
|
|
85282
85930
|
if (ENGINE_COMMANDS.has(argv0[0])) {
|
|
85931
|
+
completeInstall();
|
|
85283
85932
|
const cmd = engineCommand(argv0);
|
|
85284
85933
|
if (!cmd) {
|
|
85285
85934
|
process.stderr.write(startFailure([]) + "\n");
|
|
85286
85935
|
process.exit(1);
|
|
85287
85936
|
}
|
|
85288
|
-
const r =
|
|
85937
|
+
const r = spawnSync5(cmd.bin, cmd.args, { stdio: "inherit", windowsHide: true });
|
|
85289
85938
|
if (r.error) {
|
|
85290
85939
|
process.stderr.write(startFailure([{ bin: cmd.bin, error: r.error }]) + "\n");
|
|
85291
85940
|
process.exit(1);
|
|
@@ -85303,7 +85952,7 @@ function parseArgs(argv) {
|
|
|
85303
85952
|
} else if (x === "--image" && argv[i + 1]) {
|
|
85304
85953
|
a.images.push(argv[++i]);
|
|
85305
85954
|
} else if (x === "-h" || x === "--help") {
|
|
85306
|
-
process.stdout.write("usage: hum [task] [--image path] | hum resume [name]\nIn a session: type to talk, !cmd runs a command, esc stops the model, ctrl+v pastes a screenshot, / for commands.\n");
|
|
85955
|
+
process.stdout.write("usage: hum [task] [--image path] | hum resume [name]\nIn a session: type to talk, !cmd runs a command, esc stops the model (twice, while it waits: go back), ctrl+v pastes a screenshot, / for commands.\n");
|
|
85307
85956
|
process.exit(0);
|
|
85308
85957
|
} else if (!x.startsWith("-")) {
|
|
85309
85958
|
a.task = a.task ? `${a.task} ${x}` : x;
|
|
@@ -85320,6 +85969,7 @@ var port = Number(process.env.HUM_ENGINE_PORT || 0);
|
|
|
85320
85969
|
var startedHere = false;
|
|
85321
85970
|
try {
|
|
85322
85971
|
if (!port) {
|
|
85972
|
+
completeInstall();
|
|
85323
85973
|
const rec = await spawnEngine(args.cwd, { task: args.task, images: args.images, resume: args.resume && args.resume !== "pick" ? args.resume : null });
|
|
85324
85974
|
startedHere = true;
|
|
85325
85975
|
port = rec.port;
|