usebeeline 0.0.108 → 0.0.109
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/usebeeline.mjs +147 -24
- package/package.json +1 -1
package/dist/usebeeline.mjs
CHANGED
|
@@ -8476,7 +8476,7 @@ async function installGoogleTool(options) {
|
|
|
8476
8476
|
return fail("connector type", `${options.connectorType} is not a Google tool connector`);
|
|
8477
8477
|
}
|
|
8478
8478
|
push(step("Google credentials resolved", "running", { output: "resolving\u2026" }));
|
|
8479
|
-
const resolved = options.resolveCredentials ? await options.resolveCredentials() : await (async () => {
|
|
8479
|
+
const resolved = options.resolvedCredentials ? await options.resolvedCredentials : options.resolveCredentials ? await options.resolveCredentials() : await (async () => {
|
|
8480
8480
|
const oneClick = await readGoogleCredentialsFromVault(options.squire);
|
|
8481
8481
|
return oneClick.source === "squire" ? { ...oneClick } : { ...loadManualGoogleCredentials(options.home, options.env) };
|
|
8482
8482
|
})();
|
|
@@ -8515,7 +8515,31 @@ function describe(error) {
|
|
|
8515
8515
|
|
|
8516
8516
|
// apps/body/dist/connector-squire.js
|
|
8517
8517
|
import { execFile, spawn as spawn2 } from "node:child_process";
|
|
8518
|
-
var
|
|
8518
|
+
var SQUIRE_MCP_NAME = "@trusty-squire/mcp";
|
|
8519
|
+
var SQUIRE_CONNECT_PACKAGE = `${SQUIRE_MCP_NAME}@latest`;
|
|
8520
|
+
var activeConnectSession;
|
|
8521
|
+
function isProcessAlive(pid) {
|
|
8522
|
+
if (pid === void 0 || pid <= 0)
|
|
8523
|
+
return false;
|
|
8524
|
+
try {
|
|
8525
|
+
process.kill(pid, 0);
|
|
8526
|
+
return true;
|
|
8527
|
+
} catch (error) {
|
|
8528
|
+
return error?.code === "EPERM";
|
|
8529
|
+
}
|
|
8530
|
+
}
|
|
8531
|
+
function releaseSquireConnectSession(log2) {
|
|
8532
|
+
const claim = activeConnectSession;
|
|
8533
|
+
activeConnectSession = void 0;
|
|
8534
|
+
if (!claim)
|
|
8535
|
+
return;
|
|
8536
|
+
if (isProcessAlive(claim.pid)) {
|
|
8537
|
+
log2?.(`released trusty-squire connect session claim (pid ${String(claim.pid)} still live \u2014 a fresh connect owns the browser now)`);
|
|
8538
|
+
claim.abort();
|
|
8539
|
+
} else {
|
|
8540
|
+
log2?.("cleared dead trusty-squire connect session claim (owner process gone)");
|
|
8541
|
+
}
|
|
8542
|
+
}
|
|
8519
8543
|
var defaultShellRunner = (command, args) => new Promise((resolve31) => {
|
|
8520
8544
|
execFile(command, [...args], { timeout: 12e4, maxBuffer: 4 * 1024 * 1024, encoding: "utf8" }, (error, stdout6, stderr) => {
|
|
8521
8545
|
const code = error?.code;
|
|
@@ -8537,7 +8561,7 @@ var defaultStreamedRunner = (command, args) => new Promise((resolve31) => {
|
|
|
8537
8561
|
const safetyTimer = setTimeout(() => {
|
|
8538
8562
|
if (!resolved) {
|
|
8539
8563
|
resolved = true;
|
|
8540
|
-
resolve31({ stdout: stdout6, stderr, signIn: void 0, abort: () => {
|
|
8564
|
+
resolve31({ stdout: stdout6, stderr, pid: child.pid ?? void 0, signIn: void 0, abort: () => {
|
|
8541
8565
|
} });
|
|
8542
8566
|
}
|
|
8543
8567
|
child.kill();
|
|
@@ -8546,6 +8570,12 @@ var defaultStreamedRunner = (command, args) => new Promise((resolve31) => {
|
|
|
8546
8570
|
clearTimeout(safetyTimer);
|
|
8547
8571
|
child.kill();
|
|
8548
8572
|
};
|
|
8573
|
+
const claim = {
|
|
8574
|
+
pid: child.pid ?? void 0,
|
|
8575
|
+
claimedAt: Date.now(),
|
|
8576
|
+
abort
|
|
8577
|
+
};
|
|
8578
|
+
activeConnectSession = claim;
|
|
8549
8579
|
const finish = (result) => {
|
|
8550
8580
|
if (!resolved) {
|
|
8551
8581
|
resolved = true;
|
|
@@ -8570,11 +8600,11 @@ ${stderr}`;
|
|
|
8570
8600
|
checkOutput();
|
|
8571
8601
|
});
|
|
8572
8602
|
child.on("close", () => {
|
|
8573
|
-
finish({ stdout: stdout6, stderr, signIn: void 0, abort: () => {
|
|
8603
|
+
finish({ stdout: stdout6, stderr, pid: child.pid ?? void 0, signIn: void 0, abort: () => {
|
|
8574
8604
|
} });
|
|
8575
8605
|
});
|
|
8576
8606
|
child.on("error", () => {
|
|
8577
|
-
finish({ stdout: stdout6, stderr, signIn: void 0, abort: () => {
|
|
8607
|
+
finish({ stdout: stdout6, stderr, pid: child.pid ?? void 0, signIn: void 0, abort: () => {
|
|
8578
8608
|
} });
|
|
8579
8609
|
});
|
|
8580
8610
|
});
|
|
@@ -8595,17 +8625,57 @@ function parseConnectOutput(output) {
|
|
|
8595
8625
|
}
|
|
8596
8626
|
return { method: "streamed-page", url };
|
|
8597
8627
|
}
|
|
8598
|
-
async function installedSquireVersion(run2) {
|
|
8599
|
-
const probe = await run2("npx", [
|
|
8628
|
+
async function installedSquireVersion(run2, spec = SQUIRE_CONNECT_PACKAGE, preferOnline = false) {
|
|
8629
|
+
const probe = await run2("npx", [
|
|
8630
|
+
...preferOnline ? ["--prefer-online"] : [],
|
|
8631
|
+
"-y",
|
|
8632
|
+
spec,
|
|
8633
|
+
"--version"
|
|
8634
|
+
]);
|
|
8600
8635
|
const version = probe.stdout.match(/\d+\.\d+\.\d+[^\s]*/)?.[0];
|
|
8601
8636
|
return version;
|
|
8602
8637
|
}
|
|
8638
|
+
async function currentSquireRelease(run2) {
|
|
8639
|
+
const probe = await run2("npm", ["view", SQUIRE_MCP_NAME, "version"]);
|
|
8640
|
+
if (probe.code !== 0)
|
|
8641
|
+
return void 0;
|
|
8642
|
+
return probe.stdout.match(/\d+\.\d+\.\d+[^\s]*/)?.[0];
|
|
8643
|
+
}
|
|
8644
|
+
async function resolveSquireConnectSpec(run2) {
|
|
8645
|
+
const currentRelease = await currentSquireRelease(run2);
|
|
8646
|
+
const first = await installedSquireVersion(run2);
|
|
8647
|
+
if (currentRelease === void 0 || first === currentRelease) {
|
|
8648
|
+
return {
|
|
8649
|
+
npxArgs: ["-y", SQUIRE_CONNECT_PACKAGE],
|
|
8650
|
+
...first !== void 0 ? { resolvedVersion: first } : {},
|
|
8651
|
+
...currentRelease !== void 0 ? { currentRelease } : {},
|
|
8652
|
+
reResolved: false
|
|
8653
|
+
};
|
|
8654
|
+
}
|
|
8655
|
+
const fresh = await installedSquireVersion(run2, SQUIRE_CONNECT_PACKAGE, true);
|
|
8656
|
+
if (fresh === currentRelease) {
|
|
8657
|
+
return {
|
|
8658
|
+
npxArgs: ["--prefer-online", "-y", SQUIRE_CONNECT_PACKAGE],
|
|
8659
|
+
resolvedVersion: fresh,
|
|
8660
|
+
currentRelease,
|
|
8661
|
+
reResolved: true
|
|
8662
|
+
};
|
|
8663
|
+
}
|
|
8664
|
+
return {
|
|
8665
|
+
npxArgs: ["-y", `${SQUIRE_MCP_NAME}@${currentRelease}`],
|
|
8666
|
+
...fresh !== void 0 ? { resolvedVersion: fresh } : {},
|
|
8667
|
+
currentRelease,
|
|
8668
|
+
reResolved: true
|
|
8669
|
+
};
|
|
8670
|
+
}
|
|
8603
8671
|
function parseSignedInAs(output) {
|
|
8604
8672
|
return output.match(/signed in as ([^\s,;]+)/i)?.[1];
|
|
8605
8673
|
}
|
|
8606
8674
|
async function installSquire(options) {
|
|
8607
8675
|
const run2 = options.run ?? defaultShellRunner;
|
|
8608
8676
|
const streamRun = options.streamRun ?? defaultStreamedRunner;
|
|
8677
|
+
const log2 = options.log ?? (() => {
|
|
8678
|
+
});
|
|
8609
8679
|
const steps = [step2("helper reached", "done")];
|
|
8610
8680
|
const emit = () => options.onProgress?.([...steps]);
|
|
8611
8681
|
const push = (next) => {
|
|
@@ -8618,9 +8688,13 @@ async function installSquire(options) {
|
|
|
8618
8688
|
return { status: "error", steps, errorMessage: reason };
|
|
8619
8689
|
};
|
|
8620
8690
|
emit();
|
|
8691
|
+
releaseSquireConnectSession(log2);
|
|
8692
|
+
const resolution = await resolveSquireConnectSpec(run2);
|
|
8693
|
+
if (resolution.reResolved) {
|
|
8694
|
+
log2(`trusty-squire stale copy ${resolution.resolvedVersion ?? "unknown"} re-resolved against current release ${resolution.currentRelease}`);
|
|
8695
|
+
}
|
|
8621
8696
|
const install = await streamRun("npx", [
|
|
8622
|
-
|
|
8623
|
-
SQUIRE_CONNECT_PACKAGE,
|
|
8697
|
+
...resolution.npxArgs,
|
|
8624
8698
|
"connect",
|
|
8625
8699
|
"--force-relogin=google",
|
|
8626
8700
|
"--target=codex",
|
|
@@ -8631,7 +8705,7 @@ async function installSquire(options) {
|
|
|
8631
8705
|
push(step2("trusty-squire installed", "failed", stderr || "connect printed no sign-in URL"));
|
|
8632
8706
|
return fail(stderr || "the trusty-squire connect command printed no sign-in surface");
|
|
8633
8707
|
}
|
|
8634
|
-
const version =
|
|
8708
|
+
const version = resolution.resolvedVersion;
|
|
8635
8709
|
push(step2(`trusty-squire${version ? ` ${version}` : ""} installed`, "done"));
|
|
8636
8710
|
const signIn = install.signIn;
|
|
8637
8711
|
const signedInAs = parseSignedInAs(`${install.stdout}
|
|
@@ -8788,9 +8862,10 @@ var StdioSquireMcpClient = class {
|
|
|
8788
8862
|
}
|
|
8789
8863
|
initialize() {
|
|
8790
8864
|
const child = (this.options.spawn ?? spawn3)(this.options.command ?? "npx", [
|
|
8791
|
-
// `@
|
|
8792
|
-
//
|
|
8793
|
-
|
|
8865
|
+
// `@latest`: the current release, never a source-level version pin
|
|
8866
|
+
// (captain). Only the vault MCP server the agent spawns; the connect
|
|
8867
|
+
// install path verifies freshness itself (connector-squire.ts).
|
|
8868
|
+
...this.options.args ?? ["-y", "@trusty-squire/mcp@latest"]
|
|
8794
8869
|
]);
|
|
8795
8870
|
this.child = child;
|
|
8796
8871
|
this.buffer = "";
|
|
@@ -8899,7 +8974,12 @@ var ConnectorAssignmentLoop = class {
|
|
|
8899
8974
|
this.log = options.log ?? (() => {
|
|
8900
8975
|
});
|
|
8901
8976
|
this.install = options.install ?? installSquire;
|
|
8902
|
-
this.installGoogle = options.installGoogle ?? ((connectorType, onProgress) => installGoogleTool({
|
|
8977
|
+
this.installGoogle = options.installGoogle ?? ((connectorType, onProgress, sharedCredentials) => installGoogleTool({
|
|
8978
|
+
connectorType,
|
|
8979
|
+
home: this.googleHome(),
|
|
8980
|
+
onProgress,
|
|
8981
|
+
resolvedCredentials: sharedCredentials ? sharedCredentials() : this.resolveGoogleCredentials()
|
|
8982
|
+
}));
|
|
8903
8983
|
this.googleHomeDir = options.googleHome ?? process.env.BEELINE_AGENT_HOME ?? process.cwd();
|
|
8904
8984
|
this.readVaultFn = options.readVault ?? readVault;
|
|
8905
8985
|
this.revokeGrantsFn = options.revokeGrants ?? revokeGrants;
|
|
@@ -8941,15 +9021,60 @@ var ConnectorAssignmentLoop = class {
|
|
|
8941
9021
|
this.log(`connector assignments unavailable: ${describe2(error)}`);
|
|
8942
9022
|
return;
|
|
8943
9023
|
}
|
|
9024
|
+
let googleBatch;
|
|
8944
9025
|
for (const assignment of assignments) {
|
|
8945
9026
|
const key = `${assignment.kind}:${assignment.connectorId}`;
|
|
8946
9027
|
if (assignment.kind === "uninstall")
|
|
8947
9028
|
continue;
|
|
9029
|
+
if (assignment.kind === "install" && isGoogleToolConnectorType(assignment.connectorType)) {
|
|
9030
|
+
if (this.inFlight.has(key))
|
|
9031
|
+
continue;
|
|
9032
|
+
this.inFlight.add(key);
|
|
9033
|
+
(googleBatch ??= []).push(assignment);
|
|
9034
|
+
continue;
|
|
9035
|
+
}
|
|
8948
9036
|
if (this.inFlight.has(key))
|
|
8949
9037
|
continue;
|
|
8950
9038
|
this.inFlight.add(key);
|
|
8951
9039
|
void this.handle(assignment).catch((error) => this.log(`connector assignment ${key} failed: ${describe2(error)}`)).finally(() => this.inFlight.delete(key));
|
|
8952
9040
|
}
|
|
9041
|
+
if (googleBatch)
|
|
9042
|
+
this.flushGoogleBatch(googleBatch);
|
|
9043
|
+
}
|
|
9044
|
+
flushGoogleBatch(batch) {
|
|
9045
|
+
const keys = batch.map((a2) => `${a2.kind}:${a2.connectorId}`);
|
|
9046
|
+
void this.runGoogleBatch(batch).catch((error) => this.log(`google connector installs failed: ${describe2(error)}`)).finally(() => {
|
|
9047
|
+
for (const key of keys)
|
|
9048
|
+
this.inFlight.delete(key);
|
|
9049
|
+
});
|
|
9050
|
+
}
|
|
9051
|
+
/** The Google tool connectors ride ONE grant: every install in the batch
|
|
9052
|
+
* shares one credential resolution (the single Google consent) and the
|
|
9053
|
+
* installs run one at a time. Each tool still verifies and fails
|
|
9054
|
+
* independently — a grant that cannot serve one tool's scope refuses that
|
|
9055
|
+
* tool alone, never its siblings. */
|
|
9056
|
+
async runGoogleBatch(batch) {
|
|
9057
|
+
let shared;
|
|
9058
|
+
const sharedCredentials = () => shared ??= this.resolveGoogleCredentials();
|
|
9059
|
+
for (const assignment of batch) {
|
|
9060
|
+
await this.runGoogleInstall(assignment.connectorId, assignment.connectorType, sharedCredentials);
|
|
9061
|
+
}
|
|
9062
|
+
}
|
|
9063
|
+
/** The ONE grant resolution shared by every Google tool install of a
|
|
9064
|
+
* drain: the Squire one-click vault path first, then the manual
|
|
9065
|
+
* credentials path. Never rejects — a failure resolves as an unusable
|
|
9066
|
+
* grant each install reports through its own steps. */
|
|
9067
|
+
resolveGoogleCredentials() {
|
|
9068
|
+
return (async () => {
|
|
9069
|
+
try {
|
|
9070
|
+
const oneClick = await readGoogleCredentialsFromVault(this.squire());
|
|
9071
|
+
if (oneClick.source === "squire")
|
|
9072
|
+
return oneClick;
|
|
9073
|
+
} catch (error) {
|
|
9074
|
+
this.log(`google one-click grant lookup failed: ${describe2(error)}`);
|
|
9075
|
+
}
|
|
9076
|
+
return loadManualGoogleCredentials(this.googleHome(), process.env);
|
|
9077
|
+
})();
|
|
8953
9078
|
}
|
|
8954
9079
|
squire() {
|
|
8955
9080
|
this.mcp ??= defaultSquireMcpClient();
|
|
@@ -8957,11 +9082,7 @@ var ConnectorAssignmentLoop = class {
|
|
|
8957
9082
|
}
|
|
8958
9083
|
async handle(assignment) {
|
|
8959
9084
|
if (assignment.kind === "install") {
|
|
8960
|
-
|
|
8961
|
-
await this.runGoogleInstall(assignment.connectorId, assignment.connectorType);
|
|
8962
|
-
} else {
|
|
8963
|
-
await this.runInstall(assignment.connectorId);
|
|
8964
|
-
}
|
|
9085
|
+
await this.runInstall(assignment.connectorId);
|
|
8965
9086
|
} else if (assignment.kind === "sync")
|
|
8966
9087
|
await this.runSync();
|
|
8967
9088
|
else if (assignment.kind === "revoke-grants")
|
|
@@ -8971,8 +9092,9 @@ var ConnectorAssignmentLoop = class {
|
|
|
8971
9092
|
googleHome() {
|
|
8972
9093
|
return this.googleHomeDir;
|
|
8973
9094
|
}
|
|
8974
|
-
/** Install one Google tool connector (Gmail/Calendar/Drive/YouTube)
|
|
8975
|
-
|
|
9095
|
+
/** Install one Google tool connector (Gmail/Calendar/Drive/YouTube),
|
|
9096
|
+
* riding the drain's shared grant resolution. */
|
|
9097
|
+
async runGoogleInstall(connectorId, connectorType, sharedCredentials) {
|
|
8976
9098
|
const report = async (steps) => {
|
|
8977
9099
|
try {
|
|
8978
9100
|
await this.api.execute("postConnectorStatus", { agentId: this.agentId, connectorId, steps });
|
|
@@ -8980,7 +9102,7 @@ var ConnectorAssignmentLoop = class {
|
|
|
8980
9102
|
this.log(`step report failed: ${describe2(error)}`);
|
|
8981
9103
|
}
|
|
8982
9104
|
};
|
|
8983
|
-
const result = await this.installGoogle(connectorType, report);
|
|
9105
|
+
const result = await this.installGoogle(connectorType, report, sharedCredentials);
|
|
8984
9106
|
if (result.status === "error") {
|
|
8985
9107
|
await this.api.execute("postConnectorStatus", {
|
|
8986
9108
|
agentId: this.agentId,
|
|
@@ -9008,7 +9130,8 @@ var ConnectorAssignmentLoop = class {
|
|
|
9008
9130
|
const result = await this.install({
|
|
9009
9131
|
workspaceId: this.agentId,
|
|
9010
9132
|
mcp: this.squire(),
|
|
9011
|
-
onProgress: report
|
|
9133
|
+
onProgress: report,
|
|
9134
|
+
log: (message) => this.log(`[trusty-squire] ${message}`)
|
|
9012
9135
|
});
|
|
9013
9136
|
if (result.status === "error") {
|
|
9014
9137
|
await this.api.execute("postConnectorStatus", {
|
|
@@ -19412,7 +19535,7 @@ Then take exactly one action:
|
|
|
19412
19535
|
}
|
|
19413
19536
|
|
|
19414
19537
|
// apps/body/dist/external-mcp-capabilities.js
|
|
19415
|
-
var SQUIRE_MCP_VERSION = "
|
|
19538
|
+
var SQUIRE_MCP_VERSION = "latest";
|
|
19416
19539
|
var SQUIRE_MCP_PACKAGE = `@trusty-squire/mcp@${SQUIRE_MCP_VERSION}`;
|
|
19417
19540
|
function isTrustySquireMcpLaunch(command, args = []) {
|
|
19418
19541
|
return [command, ...args].some((value) => {
|