agenticmail 0.3.10 → 0.3.12
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.js +146 -16
- package/package.json +1 -1
package/dist/cli.js
CHANGED
|
@@ -4216,21 +4216,6 @@ async function cmdSetup() {
|
|
|
4216
4216
|
await new Promise((r) => setTimeout(r, 800));
|
|
4217
4217
|
log2(` ${c2.bold("Step 4 of 4")} ${c2.dim("\u2014")} ${c2.bold("Connect your email")}`);
|
|
4218
4218
|
log2("");
|
|
4219
|
-
log2(` How should your AI agent send and receive email?`);
|
|
4220
|
-
log2("");
|
|
4221
|
-
log2(` ${c2.cyan("1.")} Use my Gmail or Outlook`);
|
|
4222
|
-
log2(` ${c2.dim("Easiest option \u2014 connect your existing email account.")}`);
|
|
4223
|
-
log2(` ${c2.dim("Your agent emails as you+agent@gmail.com")}`);
|
|
4224
|
-
log2("");
|
|
4225
|
-
log2(` ${c2.cyan("2.")} Use my own domain`);
|
|
4226
|
-
log2(` ${c2.dim("Your agent gets a custom address like agent@yourcompany.com")}`);
|
|
4227
|
-
log2(` ${c2.dim("Requires a Cloudflare account and a domain.")}`);
|
|
4228
|
-
log2("");
|
|
4229
|
-
log2(` ${c2.cyan("3.")} Skip for now`);
|
|
4230
|
-
log2(` ${c2.dim("You can always set this up later.")}`);
|
|
4231
|
-
log2("");
|
|
4232
|
-
const choice = await pick(` ${c2.magenta(">")} `, ["1", "2", "3"]);
|
|
4233
|
-
log2("");
|
|
4234
4219
|
const serverSpinner = new Spinner("server", "Starting the server...");
|
|
4235
4220
|
serverSpinner.start();
|
|
4236
4221
|
let serverReady = false;
|
|
@@ -4281,6 +4266,62 @@ async function cmdSetup() {
|
|
|
4281
4266
|
serverSpinner.fail(`Could not start server: ${err.message}`);
|
|
4282
4267
|
}
|
|
4283
4268
|
}
|
|
4269
|
+
let existingEmail = null;
|
|
4270
|
+
let existingProvider = null;
|
|
4271
|
+
if (serverReady) {
|
|
4272
|
+
try {
|
|
4273
|
+
const base = `http://${result.config.api.host}:${result.config.api.port}`;
|
|
4274
|
+
const statusResp = await fetch(`${base}/api/agenticmail/gateway/status`, {
|
|
4275
|
+
headers: { "Authorization": `Bearer ${result.config.masterKey}` },
|
|
4276
|
+
signal: AbortSignal.timeout(5e3)
|
|
4277
|
+
});
|
|
4278
|
+
if (statusResp.ok) {
|
|
4279
|
+
const status = await statusResp.json();
|
|
4280
|
+
if (status.mode === "relay" && status.relay?.email) {
|
|
4281
|
+
existingEmail = status.relay.email;
|
|
4282
|
+
existingProvider = status.relay.provider || "custom";
|
|
4283
|
+
}
|
|
4284
|
+
}
|
|
4285
|
+
} catch {
|
|
4286
|
+
}
|
|
4287
|
+
}
|
|
4288
|
+
let choice;
|
|
4289
|
+
if (existingEmail) {
|
|
4290
|
+
const provLabel = existingProvider === "gmail" ? "Gmail" : existingProvider === "outlook" ? "Outlook" : existingProvider;
|
|
4291
|
+
log2("");
|
|
4292
|
+
ok2(`Email already connected: ${c2.cyan(existingEmail)} ${c2.dim(`(${provLabel})`)}`);
|
|
4293
|
+
log2("");
|
|
4294
|
+
log2(` ${c2.cyan("1.")} Keep current email`);
|
|
4295
|
+
log2(` ${c2.cyan("2.")} Remove and connect a different email`);
|
|
4296
|
+
log2(` ${c2.cyan("3.")} Set up a custom domain instead`);
|
|
4297
|
+
log2("");
|
|
4298
|
+
const existChoice = await pick(` ${c2.magenta(">")} `, ["1", "2", "3"]);
|
|
4299
|
+
if (existChoice === "1") {
|
|
4300
|
+
choice = "3";
|
|
4301
|
+
log2("");
|
|
4302
|
+
ok2(`Keeping ${c2.cyan(existingEmail)}`);
|
|
4303
|
+
} else if (existChoice === "3") {
|
|
4304
|
+
choice = "2";
|
|
4305
|
+
} else {
|
|
4306
|
+
choice = "1";
|
|
4307
|
+
}
|
|
4308
|
+
} else {
|
|
4309
|
+
log2(` How should your AI agent send and receive email?`);
|
|
4310
|
+
log2("");
|
|
4311
|
+
log2(` ${c2.cyan("1.")} Use my Gmail or Outlook`);
|
|
4312
|
+
log2(` ${c2.dim("Easiest option \u2014 connect your existing email account.")}`);
|
|
4313
|
+
log2(` ${c2.dim("Your agent emails as you+agent@gmail.com")}`);
|
|
4314
|
+
log2("");
|
|
4315
|
+
log2(` ${c2.cyan("2.")} Use my own domain`);
|
|
4316
|
+
log2(` ${c2.dim("Your agent gets a custom address like agent@yourcompany.com")}`);
|
|
4317
|
+
log2(` ${c2.dim("Requires a Cloudflare account and a domain.")}`);
|
|
4318
|
+
log2("");
|
|
4319
|
+
log2(` ${c2.cyan("3.")} Skip for now`);
|
|
4320
|
+
log2(` ${c2.dim("You can always set this up later.")}`);
|
|
4321
|
+
log2("");
|
|
4322
|
+
choice = await pick(` ${c2.magenta(">")} `, ["1", "2", "3"]);
|
|
4323
|
+
}
|
|
4324
|
+
log2("");
|
|
4284
4325
|
if (choice === "1" || choice === "2") {
|
|
4285
4326
|
if (!serverReady) {
|
|
4286
4327
|
info2("You can configure email later by running: agenticmail setup");
|
|
@@ -4294,9 +4335,12 @@ async function cmdSetup() {
|
|
|
4294
4335
|
} else {
|
|
4295
4336
|
await setupDomain(result.config);
|
|
4296
4337
|
}
|
|
4297
|
-
} else {
|
|
4338
|
+
} else if (!existingEmail) {
|
|
4298
4339
|
info2("No problem! You can set up email anytime by running this again.");
|
|
4299
4340
|
}
|
|
4341
|
+
if (serverReady) {
|
|
4342
|
+
await registerWithOpenClaw(result.config);
|
|
4343
|
+
}
|
|
4300
4344
|
printSummary(result, false);
|
|
4301
4345
|
if (serverReady) {
|
|
4302
4346
|
await interactiveShell({ config: result.config, onExit: cleanupChild });
|
|
@@ -4319,6 +4363,92 @@ function printSummary(result, exitAfter) {
|
|
|
4319
4363
|
process.exit(0);
|
|
4320
4364
|
}
|
|
4321
4365
|
}
|
|
4366
|
+
async function registerWithOpenClaw(config) {
|
|
4367
|
+
const openclawConfig = join(homedir(), ".openclaw", "openclaw.json");
|
|
4368
|
+
if (!existsSync2(openclawConfig)) return;
|
|
4369
|
+
try {
|
|
4370
|
+
const raw = readFileSync2(openclawConfig, "utf8");
|
|
4371
|
+
const ocConfig = JSON.parse(raw);
|
|
4372
|
+
if (ocConfig.plugins?.entries?.agenticmail?.config?.apiKey) {
|
|
4373
|
+
ok2(`OpenClaw integration already configured`);
|
|
4374
|
+
return;
|
|
4375
|
+
}
|
|
4376
|
+
let pluginPath = null;
|
|
4377
|
+
try {
|
|
4378
|
+
const resolved = import.meta.resolve("@agenticmail/openclaw");
|
|
4379
|
+
const resolvedPath = fileURLToPath(resolved);
|
|
4380
|
+
pluginPath = dirname(dirname(resolvedPath));
|
|
4381
|
+
} catch {
|
|
4382
|
+
}
|
|
4383
|
+
if (!pluginPath) {
|
|
4384
|
+
const thisDir = dirname(fileURLToPath(import.meta.url));
|
|
4385
|
+
let dir = thisDir;
|
|
4386
|
+
for (let i = 0; i < 10; i++) {
|
|
4387
|
+
const candidate = join(dir, "node_modules", "@agenticmail", "openclaw");
|
|
4388
|
+
if (existsSync2(join(candidate, "package.json"))) {
|
|
4389
|
+
pluginPath = candidate;
|
|
4390
|
+
break;
|
|
4391
|
+
}
|
|
4392
|
+
const parent = dirname(dir);
|
|
4393
|
+
if (parent === dir) break;
|
|
4394
|
+
dir = parent;
|
|
4395
|
+
}
|
|
4396
|
+
}
|
|
4397
|
+
if (!pluginPath) {
|
|
4398
|
+
try {
|
|
4399
|
+
const { execSync } = await import("child_process");
|
|
4400
|
+
const prefix = execSync("npm prefix -g", { timeout: 5e3, stdio: ["ignore", "pipe", "ignore"] }).toString().trim();
|
|
4401
|
+
const globalCandidate = join(prefix, "lib", "node_modules", "@agenticmail", "openclaw");
|
|
4402
|
+
if (existsSync2(join(globalCandidate, "package.json"))) pluginPath = globalCandidate;
|
|
4403
|
+
if (!pluginPath) {
|
|
4404
|
+
const globalCandidate2 = join(prefix, "node_modules", "@agenticmail", "openclaw");
|
|
4405
|
+
if (existsSync2(join(globalCandidate2, "package.json"))) pluginPath = globalCandidate2;
|
|
4406
|
+
}
|
|
4407
|
+
} catch {
|
|
4408
|
+
}
|
|
4409
|
+
}
|
|
4410
|
+
if (!pluginPath) return;
|
|
4411
|
+
try {
|
|
4412
|
+
pluginPath = realpathSync(pluginPath);
|
|
4413
|
+
} catch {
|
|
4414
|
+
}
|
|
4415
|
+
let apiKey = "";
|
|
4416
|
+
try {
|
|
4417
|
+
const base = `http://${config.api.host}:${config.api.port}`;
|
|
4418
|
+
const resp = await fetch(`${base}/api/agenticmail/accounts`, {
|
|
4419
|
+
headers: { "Authorization": `Bearer ${config.masterKey}` },
|
|
4420
|
+
signal: AbortSignal.timeout(5e3)
|
|
4421
|
+
});
|
|
4422
|
+
if (resp.ok) {
|
|
4423
|
+
const data = await resp.json();
|
|
4424
|
+
const agents = data.agents || data || [];
|
|
4425
|
+
if (agents.length > 0) {
|
|
4426
|
+
apiKey = agents[0].apiKey;
|
|
4427
|
+
}
|
|
4428
|
+
}
|
|
4429
|
+
} catch {
|
|
4430
|
+
}
|
|
4431
|
+
if (!apiKey) return;
|
|
4432
|
+
if (!ocConfig.plugins) ocConfig.plugins = {};
|
|
4433
|
+
if (!ocConfig.plugins.load) ocConfig.plugins.load = {};
|
|
4434
|
+
if (!ocConfig.plugins.load.paths) ocConfig.plugins.load.paths = [];
|
|
4435
|
+
if (!ocConfig.plugins.entries) ocConfig.plugins.entries = {};
|
|
4436
|
+
if (!ocConfig.plugins.load.paths.includes(pluginPath)) {
|
|
4437
|
+
ocConfig.plugins.load.paths.push(pluginPath);
|
|
4438
|
+
}
|
|
4439
|
+
ocConfig.plugins.entries.agenticmail = {
|
|
4440
|
+
enabled: true,
|
|
4441
|
+
config: {
|
|
4442
|
+
apiUrl: `http://${config.api.host}:${config.api.port}`,
|
|
4443
|
+
apiKey,
|
|
4444
|
+
masterKey: config.masterKey
|
|
4445
|
+
}
|
|
4446
|
+
};
|
|
4447
|
+
writeFileSync2(openclawConfig, JSON.stringify(ocConfig, null, 2) + "\n", "utf8");
|
|
4448
|
+
ok2(`OpenClaw integration configured \u2014 your agents can now use email!`);
|
|
4449
|
+
} catch {
|
|
4450
|
+
}
|
|
4451
|
+
}
|
|
4322
4452
|
async function setupRelay(config) {
|
|
4323
4453
|
log2(" Which email service do you use?");
|
|
4324
4454
|
log2(` ${c2.cyan("1.")} Gmail`);
|