@looplia/looplia-cli 0.6.8 → 0.6.9
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
CHANGED
|
@@ -243,11 +243,12 @@ async function getPluginPaths() {
|
|
|
243
243
|
return await getProdPluginPaths();
|
|
244
244
|
}
|
|
245
245
|
|
|
246
|
-
// ../../packages/provider/dist/chunk-
|
|
246
|
+
// ../../packages/provider/dist/chunk-5W3I2MT7.js
|
|
247
247
|
import { execSync } from "child_process";
|
|
248
248
|
import { existsSync as existsSync3 } from "fs";
|
|
249
|
+
import { createRequire } from "module";
|
|
249
250
|
import { homedir as homedir3 } from "os";
|
|
250
|
-
import { join as join4 } from "path";
|
|
251
|
+
import { dirname as dirname3, join as join4 } from "path";
|
|
251
252
|
|
|
252
253
|
// ../../node_modules/zod-to-json-schema/dist/esm/Options.js
|
|
253
254
|
var ignoreOverride = /* @__PURE__ */ Symbol("Let zodToJsonSchema decide on which parser to use");
|
|
@@ -5574,7 +5575,7 @@ var zodToJsonSchema = (schema, options) => {
|
|
|
5574
5575
|
return combined;
|
|
5575
5576
|
};
|
|
5576
5577
|
|
|
5577
|
-
// ../../node_modules/@anthropic-ai/claude-agent-sdk/sdk.mjs
|
|
5578
|
+
// ../../packages/provider/node_modules/@anthropic-ai/claude-agent-sdk/sdk.mjs
|
|
5578
5579
|
import { join as join5 } from "path";
|
|
5579
5580
|
import { fileURLToPath as fileURLToPath23 } from "url";
|
|
5580
5581
|
import { setMaxListeners } from "events";
|
|
@@ -27369,7 +27370,7 @@ function query({
|
|
|
27369
27370
|
return queryInstance;
|
|
27370
27371
|
}
|
|
27371
27372
|
|
|
27372
|
-
// ../../packages/provider/dist/chunk-
|
|
27373
|
+
// ../../packages/provider/dist/chunk-5W3I2MT7.js
|
|
27373
27374
|
import { appendFileSync as appendFileSync3, mkdirSync as mkdirSync3, writeFileSync as writeFileSync2 } from "fs";
|
|
27374
27375
|
import { join as join23 } from "path";
|
|
27375
27376
|
import {
|
|
@@ -27385,6 +27386,22 @@ import { join as join32 } from "path";
|
|
|
27385
27386
|
import { cp as cp2, mkdir as mkdir22, readFile as readFile22, rm as rm22, stat as stat2, writeFile as writeFile22 } from "fs/promises";
|
|
27386
27387
|
import { homedir as homedir32 } from "os";
|
|
27387
27388
|
import { isAbsolute, join as join42, normalize, resolve } from "path";
|
|
27389
|
+
var LINE_SPLIT_REGEX = /\r?\n/;
|
|
27390
|
+
function findSdkBundledCliPath() {
|
|
27391
|
+
try {
|
|
27392
|
+
const require2 = createRequire(import.meta.url);
|
|
27393
|
+
const sdkPackagePath = require2.resolve(
|
|
27394
|
+
"@anthropic-ai/claude-agent-sdk/package.json"
|
|
27395
|
+
);
|
|
27396
|
+
const sdkDir = dirname3(sdkPackagePath);
|
|
27397
|
+
const cliPath = join4(sdkDir, "cli.js");
|
|
27398
|
+
if (existsSync3(cliPath)) {
|
|
27399
|
+
return cliPath;
|
|
27400
|
+
}
|
|
27401
|
+
} catch {
|
|
27402
|
+
}
|
|
27403
|
+
return;
|
|
27404
|
+
}
|
|
27388
27405
|
var CLAUDE_CODE_PATHS = [
|
|
27389
27406
|
// User's local bin (npm global install location)
|
|
27390
27407
|
join4(homedir3(), ".local", "bin", "claude"),
|
|
@@ -27395,36 +27412,42 @@ var CLAUDE_CODE_PATHS = [
|
|
|
27395
27412
|
// Windows (if applicable)
|
|
27396
27413
|
join4(homedir3(), "AppData", "Local", "Programs", "claude", "claude.exe")
|
|
27397
27414
|
];
|
|
27415
|
+
var cachedClaudeCodePath;
|
|
27398
27416
|
function findClaudeCodePath() {
|
|
27417
|
+
if (cachedClaudeCodePath !== void 0) {
|
|
27418
|
+
return cachedClaudeCodePath ?? void 0;
|
|
27419
|
+
}
|
|
27399
27420
|
const envPath = process.env.CLAUDE_CODE_PATH;
|
|
27400
27421
|
if (envPath && existsSync3(envPath)) {
|
|
27401
|
-
|
|
27422
|
+
cachedClaudeCodePath = envPath;
|
|
27423
|
+
return cachedClaudeCodePath;
|
|
27402
27424
|
}
|
|
27403
27425
|
for (const path3 of CLAUDE_CODE_PATHS) {
|
|
27404
27426
|
if (existsSync3(path3)) {
|
|
27405
|
-
|
|
27427
|
+
cachedClaudeCodePath = path3;
|
|
27428
|
+
return cachedClaudeCodePath;
|
|
27406
27429
|
}
|
|
27407
27430
|
}
|
|
27408
27431
|
try {
|
|
27409
|
-
const
|
|
27432
|
+
const pathLookupCommand = process.platform === "win32" ? "where claude" : "which claude";
|
|
27433
|
+
const rawResult = execSync(pathLookupCommand, {
|
|
27410
27434
|
encoding: "utf-8",
|
|
27411
27435
|
stdio: ["pipe", "pipe", "pipe"]
|
|
27412
27436
|
}).trim();
|
|
27413
|
-
|
|
27414
|
-
|
|
27437
|
+
const firstResult = rawResult.split(LINE_SPLIT_REGEX).find((line) => line.trim().length > 0) ?? "";
|
|
27438
|
+
if (firstResult && existsSync3(firstResult)) {
|
|
27439
|
+
cachedClaudeCodePath = firstResult;
|
|
27440
|
+
return cachedClaudeCodePath;
|
|
27415
27441
|
}
|
|
27416
27442
|
} catch {
|
|
27417
27443
|
}
|
|
27418
|
-
|
|
27419
|
-
|
|
27420
|
-
|
|
27421
|
-
|
|
27422
|
-
|
|
27423
|
-
|
|
27424
|
-
|
|
27425
|
-
|
|
27426
|
-
More info: https://docs.anthropic.com/claude-code`
|
|
27427
|
-
);
|
|
27444
|
+
const sdkCliPath = findSdkBundledCliPath();
|
|
27445
|
+
if (sdkCliPath) {
|
|
27446
|
+
cachedClaudeCodePath = sdkCliPath;
|
|
27447
|
+
return cachedClaudeCodePath;
|
|
27448
|
+
}
|
|
27449
|
+
cachedClaudeCodePath = null;
|
|
27450
|
+
return;
|
|
27428
27451
|
}
|
|
27429
27452
|
var DEFAULT_CONFIG = {
|
|
27430
27453
|
model: "claude-haiku-4-5-20251001",
|
|
@@ -27489,7 +27512,7 @@ var DEFAULT_SETTINGS = {
|
|
|
27489
27512
|
},
|
|
27490
27513
|
agents: {
|
|
27491
27514
|
main: "claude-haiku-4-5-20251001",
|
|
27492
|
-
executor: "haiku"
|
|
27515
|
+
executor: "claude-haiku-4-5-20251001"
|
|
27493
27516
|
}
|
|
27494
27517
|
};
|
|
27495
27518
|
var PRESETS = {
|
|
@@ -27498,13 +27521,19 @@ var PRESETS = {
|
|
|
27498
27521
|
name: "Anthropic Claude Haiku",
|
|
27499
27522
|
apiProvider: "anthropic",
|
|
27500
27523
|
mainModel: "claude-haiku-4-5-20251001",
|
|
27501
|
-
executorModel: "haiku"
|
|
27524
|
+
executorModel: "claude-haiku-4-5-20251001",
|
|
27525
|
+
haikuModel: "claude-haiku-4-5-20251001",
|
|
27526
|
+
sonnetModel: "claude-haiku-4-5-20251001",
|
|
27527
|
+
opusModel: "claude-haiku-4-5-20251001"
|
|
27502
27528
|
},
|
|
27503
27529
|
ANTHROPIC_CLAUDE_SONNET: {
|
|
27504
27530
|
name: "Anthropic Claude Sonnet",
|
|
27505
27531
|
apiProvider: "anthropic",
|
|
27506
27532
|
mainModel: "claude-sonnet-4-5-20250514",
|
|
27507
|
-
executorModel: "
|
|
27533
|
+
executorModel: "claude-sonnet-4-5-20250514",
|
|
27534
|
+
haikuModel: "claude-sonnet-4-5-20250514",
|
|
27535
|
+
sonnetModel: "claude-sonnet-4-5-20250514",
|
|
27536
|
+
opusModel: "claude-sonnet-4-5-20250514"
|
|
27508
27537
|
},
|
|
27509
27538
|
// ZenMux Presets
|
|
27510
27539
|
ZENMUX_ANTHROPIC_HAIKU45: {
|
|
@@ -27512,98 +27541,140 @@ var PRESETS = {
|
|
|
27512
27541
|
apiProvider: "zenmux",
|
|
27513
27542
|
baseUrl: "https://zenmux.ai/api/anthropic",
|
|
27514
27543
|
mainModel: "anthropic/claude-haiku-4.5",
|
|
27515
|
-
executorModel: "anthropic/claude-haiku-4.5"
|
|
27544
|
+
executorModel: "anthropic/claude-haiku-4.5",
|
|
27545
|
+
haikuModel: "anthropic/claude-haiku-4.5",
|
|
27546
|
+
sonnetModel: "anthropic/claude-haiku-4.5",
|
|
27547
|
+
opusModel: "anthropic/claude-haiku-4.5"
|
|
27516
27548
|
},
|
|
27517
27549
|
ZENMUX_ZAI_GLM47: {
|
|
27518
27550
|
name: "ZenMux GLM-4.7",
|
|
27519
27551
|
apiProvider: "zenmux",
|
|
27520
27552
|
baseUrl: "https://zenmux.ai/api/anthropic",
|
|
27521
27553
|
mainModel: "z-ai/glm-4.7",
|
|
27522
|
-
executorModel: "z-ai/glm-4.7"
|
|
27554
|
+
executorModel: "z-ai/glm-4.7",
|
|
27555
|
+
haikuModel: "z-ai/glm-4.7",
|
|
27556
|
+
sonnetModel: "z-ai/glm-4.7",
|
|
27557
|
+
opusModel: "z-ai/glm-4.7"
|
|
27523
27558
|
},
|
|
27524
27559
|
ZENMUX_MINIMAX_M21: {
|
|
27525
27560
|
name: "ZenMux MiniMax-M2.1",
|
|
27526
27561
|
apiProvider: "zenmux",
|
|
27527
27562
|
baseUrl: "https://zenmux.ai/api/anthropic",
|
|
27528
27563
|
mainModel: "minimax/minimax-m2.1",
|
|
27529
|
-
executorModel: "minimax/minimax-m2.1"
|
|
27564
|
+
executorModel: "minimax/minimax-m2.1",
|
|
27565
|
+
haikuModel: "minimax/minimax-m2.1",
|
|
27566
|
+
sonnetModel: "minimax/minimax-m2.1",
|
|
27567
|
+
opusModel: "minimax/minimax-m2.1"
|
|
27530
27568
|
},
|
|
27531
27569
|
ZENMUX_GOOGLE_GEMINI3FLASH: {
|
|
27532
27570
|
name: "ZenMux Gemini-3-Flash",
|
|
27533
27571
|
apiProvider: "zenmux",
|
|
27534
27572
|
baseUrl: "https://zenmux.ai/api/anthropic",
|
|
27535
27573
|
mainModel: "google/gemini-3-flash-preview",
|
|
27536
|
-
executorModel: "google/gemini-3-flash-preview"
|
|
27574
|
+
executorModel: "google/gemini-3-flash-preview",
|
|
27575
|
+
haikuModel: "google/gemini-3-flash-preview",
|
|
27576
|
+
sonnetModel: "google/gemini-3-flash-preview",
|
|
27577
|
+
opusModel: "google/gemini-3-flash-preview"
|
|
27537
27578
|
},
|
|
27538
27579
|
ZENMUX_GOOGLE_GEMINI3FLASH_FREE: {
|
|
27539
27580
|
name: "ZenMux Gemini-3-Flash (Free)",
|
|
27540
27581
|
apiProvider: "zenmux",
|
|
27541
27582
|
baseUrl: "https://zenmux.ai/api/anthropic",
|
|
27542
27583
|
mainModel: "google/gemini-3-flash-preview-free",
|
|
27543
|
-
executorModel: "google/gemini-3-flash-preview-free"
|
|
27584
|
+
executorModel: "google/gemini-3-flash-preview-free",
|
|
27585
|
+
haikuModel: "google/gemini-3-flash-preview-free",
|
|
27586
|
+
sonnetModel: "google/gemini-3-flash-preview-free",
|
|
27587
|
+
opusModel: "google/gemini-3-flash-preview-free"
|
|
27544
27588
|
},
|
|
27545
27589
|
ZENMUX_XIAOMI_MIMOV2FLASH: {
|
|
27546
27590
|
name: "ZenMux MiMo-v2-Flash",
|
|
27547
27591
|
apiProvider: "zenmux",
|
|
27548
27592
|
baseUrl: "https://zenmux.ai/api/anthropic",
|
|
27549
27593
|
mainModel: "xiaomi/mimo-v2-flash",
|
|
27550
|
-
executorModel: "xiaomi/mimo-v2-flash"
|
|
27594
|
+
executorModel: "xiaomi/mimo-v2-flash",
|
|
27595
|
+
haikuModel: "xiaomi/mimo-v2-flash",
|
|
27596
|
+
sonnetModel: "xiaomi/mimo-v2-flash",
|
|
27597
|
+
opusModel: "xiaomi/mimo-v2-flash"
|
|
27551
27598
|
},
|
|
27552
27599
|
ZENMUX_XAI_GROK41FAST: {
|
|
27553
27600
|
name: "ZenMux Grok-4.1-Fast",
|
|
27554
27601
|
apiProvider: "zenmux",
|
|
27555
27602
|
baseUrl: "https://zenmux.ai/api/anthropic",
|
|
27556
27603
|
mainModel: "x-ai/grok-4.1-fast",
|
|
27557
|
-
executorModel: "x-ai/grok-4.1-fast"
|
|
27604
|
+
executorModel: "x-ai/grok-4.1-fast",
|
|
27605
|
+
haikuModel: "x-ai/grok-4.1-fast",
|
|
27606
|
+
sonnetModel: "x-ai/grok-4.1-fast",
|
|
27607
|
+
opusModel: "x-ai/grok-4.1-fast"
|
|
27558
27608
|
},
|
|
27559
27609
|
ZENMUX_DEEPSEEK_V32: {
|
|
27560
27610
|
name: "ZenMux DeepSeek-v3.2",
|
|
27561
27611
|
apiProvider: "zenmux",
|
|
27562
27612
|
baseUrl: "https://zenmux.ai/api/anthropic",
|
|
27563
27613
|
mainModel: "deepseek/deepseek-v3.2",
|
|
27564
|
-
executorModel: "deepseek/deepseek-v3.2"
|
|
27614
|
+
executorModel: "deepseek/deepseek-v3.2",
|
|
27615
|
+
haikuModel: "deepseek/deepseek-v3.2",
|
|
27616
|
+
sonnetModel: "deepseek/deepseek-v3.2",
|
|
27617
|
+
opusModel: "deepseek/deepseek-v3.2"
|
|
27565
27618
|
},
|
|
27566
27619
|
ZENMUX_DEEPSEEK_REASONER: {
|
|
27567
27620
|
name: "ZenMux DeepSeek-Reasoner",
|
|
27568
27621
|
apiProvider: "zenmux",
|
|
27569
27622
|
baseUrl: "https://zenmux.ai/api/anthropic",
|
|
27570
27623
|
mainModel: "deepseek/deepseek-reasoner",
|
|
27571
|
-
executorModel: "deepseek/deepseek-reasoner"
|
|
27624
|
+
executorModel: "deepseek/deepseek-reasoner",
|
|
27625
|
+
haikuModel: "deepseek/deepseek-reasoner",
|
|
27626
|
+
sonnetModel: "deepseek/deepseek-reasoner",
|
|
27627
|
+
opusModel: "deepseek/deepseek-reasoner"
|
|
27572
27628
|
},
|
|
27573
27629
|
ZENMUX_VOLCENGINE_DOUBAO_SEED: {
|
|
27574
27630
|
name: "ZenMux Doubao-Seed-1.8",
|
|
27575
27631
|
apiProvider: "zenmux",
|
|
27576
27632
|
baseUrl: "https://zenmux.ai/api/anthropic",
|
|
27577
27633
|
mainModel: "volcengine/doubao-seed-1.8",
|
|
27578
|
-
executorModel: "volcengine/doubao-seed-1.8"
|
|
27634
|
+
executorModel: "volcengine/doubao-seed-1.8",
|
|
27635
|
+
haikuModel: "volcengine/doubao-seed-1.8",
|
|
27636
|
+
sonnetModel: "volcengine/doubao-seed-1.8",
|
|
27637
|
+
opusModel: "volcengine/doubao-seed-1.8"
|
|
27579
27638
|
},
|
|
27580
27639
|
ZENMUX_MISTRAL_LARGE2512: {
|
|
27581
27640
|
name: "ZenMux Mistral-Large-2512",
|
|
27582
27641
|
apiProvider: "zenmux",
|
|
27583
27642
|
baseUrl: "https://zenmux.ai/api/anthropic",
|
|
27584
27643
|
mainModel: "mistralai/mistral-large-2512",
|
|
27585
|
-
executorModel: "mistralai/mistral-large-2512"
|
|
27644
|
+
executorModel: "mistralai/mistral-large-2512",
|
|
27645
|
+
haikuModel: "mistralai/mistral-large-2512",
|
|
27646
|
+
sonnetModel: "mistralai/mistral-large-2512",
|
|
27647
|
+
opusModel: "mistralai/mistral-large-2512"
|
|
27586
27648
|
},
|
|
27587
27649
|
ZENMUX_ZAI_GLM46VFLASH: {
|
|
27588
27650
|
name: "ZenMux GLM-4.6v-Flash",
|
|
27589
27651
|
apiProvider: "zenmux",
|
|
27590
27652
|
baseUrl: "https://zenmux.ai/api/anthropic",
|
|
27591
27653
|
mainModel: "z-ai/glm-4.6v-flash",
|
|
27592
|
-
executorModel: "z-ai/glm-4.6v-flash"
|
|
27654
|
+
executorModel: "z-ai/glm-4.6v-flash",
|
|
27655
|
+
haikuModel: "z-ai/glm-4.6v-flash",
|
|
27656
|
+
sonnetModel: "z-ai/glm-4.6v-flash",
|
|
27657
|
+
opusModel: "z-ai/glm-4.6v-flash"
|
|
27593
27658
|
},
|
|
27594
27659
|
ZENMUX_ZAI_GLM46V: {
|
|
27595
27660
|
name: "ZenMux GLM-4.6v",
|
|
27596
27661
|
apiProvider: "zenmux",
|
|
27597
27662
|
baseUrl: "https://zenmux.ai/api/anthropic",
|
|
27598
27663
|
mainModel: "z-ai/glm-4.6v",
|
|
27599
|
-
executorModel: "z-ai/glm-4.6v"
|
|
27664
|
+
executorModel: "z-ai/glm-4.6v",
|
|
27665
|
+
haikuModel: "z-ai/glm-4.6v",
|
|
27666
|
+
sonnetModel: "z-ai/glm-4.6v",
|
|
27667
|
+
opusModel: "z-ai/glm-4.6v"
|
|
27600
27668
|
},
|
|
27601
27669
|
ZENMUX_OPENAI_GPT51CODEXMINI: {
|
|
27602
27670
|
name: "ZenMux GPT-5.1 Codex Mini",
|
|
27603
27671
|
apiProvider: "zenmux",
|
|
27604
27672
|
baseUrl: "https://zenmux.ai/api/anthropic",
|
|
27605
27673
|
mainModel: "openai/gpt-5.1-codex-mini",
|
|
27606
|
-
executorModel: "openai/gpt-5.1-codex-mini"
|
|
27674
|
+
executorModel: "openai/gpt-5.1-codex-mini",
|
|
27675
|
+
haikuModel: "openai/gpt-5.1-codex-mini",
|
|
27676
|
+
sonnetModel: "openai/gpt-5.1-codex-mini",
|
|
27677
|
+
opusModel: "openai/gpt-5.1-codex-mini"
|
|
27607
27678
|
}
|
|
27608
27679
|
};
|
|
27609
27680
|
var CONFIG_FILE = "looplia.setting.json";
|
|
@@ -27643,23 +27714,33 @@ async function writeLoopliaSettings(settings) {
|
|
|
27643
27714
|
async function removeLoopliaSettings() {
|
|
27644
27715
|
await rm2(getConfigPath(), { force: true });
|
|
27645
27716
|
}
|
|
27717
|
+
function setEnvIfNotSet(key, value) {
|
|
27718
|
+
if (!process.env[key]) {
|
|
27719
|
+
process.env[key] = value;
|
|
27720
|
+
}
|
|
27721
|
+
}
|
|
27722
|
+
function injectModelTierEnv(mainModel, executorModel) {
|
|
27723
|
+
setEnvIfNotSet("ANTHROPIC_DEFAULT_HAIKU_MODEL", mainModel);
|
|
27724
|
+
setEnvIfNotSet("ANTHROPIC_DEFAULT_SONNET_MODEL", mainModel);
|
|
27725
|
+
setEnvIfNotSet("ANTHROPIC_DEFAULT_OPUS_MODEL", mainModel);
|
|
27726
|
+
setEnvIfNotSet("LOOPLIA_AGENT_MODEL_MAIN", mainModel);
|
|
27727
|
+
setEnvIfNotSet("LOOPLIA_AGENT_MODEL_EXECUTOR", executorModel);
|
|
27728
|
+
}
|
|
27646
27729
|
function injectLoopliaSettingsEnv(settings) {
|
|
27647
27730
|
if (settings.apiProvider.type !== "anthropic") {
|
|
27648
27731
|
if (settings.apiProvider.baseUrl && !process.env.ANTHROPIC_BASE_URL) {
|
|
27649
27732
|
process.env.ANTHROPIC_BASE_URL = settings.apiProvider.baseUrl;
|
|
27650
27733
|
}
|
|
27651
|
-
if (settings.apiProvider.
|
|
27652
|
-
process.env.ANTHROPIC_API_KEY = process.env.ZENMUX_API_KEY;
|
|
27653
|
-
} else if (!process.env.ANTHROPIC_API_KEY && settings.apiProvider.authToken) {
|
|
27734
|
+
if (settings.apiProvider.authToken) {
|
|
27654
27735
|
process.env.ANTHROPIC_API_KEY = settings.apiProvider.authToken;
|
|
27736
|
+
} else {
|
|
27737
|
+
const isZenmuxEndpoint = settings.apiProvider.type === "zenmux" || settings.apiProvider.baseUrl?.includes("zenmux.ai");
|
|
27738
|
+
if (isZenmuxEndpoint && process.env.ZENMUX_API_KEY) {
|
|
27739
|
+
process.env.ANTHROPIC_API_KEY = process.env.ZENMUX_API_KEY;
|
|
27740
|
+
}
|
|
27655
27741
|
}
|
|
27656
27742
|
}
|
|
27657
|
-
|
|
27658
|
-
process.env.LOOPLIA_AGENT_MODEL_MAIN = settings.agents.main;
|
|
27659
|
-
}
|
|
27660
|
-
if (!process.env.LOOPLIA_AGENT_MODEL_EXECUTOR) {
|
|
27661
|
-
process.env.LOOPLIA_AGENT_MODEL_EXECUTOR = settings.agents.executor;
|
|
27662
|
-
}
|
|
27743
|
+
injectModelTierEnv(settings.agents.main, settings.agents.executor);
|
|
27663
27744
|
}
|
|
27664
27745
|
function getSettingsDisplayInfo(settings) {
|
|
27665
27746
|
if (!settings) {
|
|
@@ -28495,14 +28576,10 @@ async function initializeAndValidateApiKey(config2) {
|
|
|
28495
28576
|
"API key is required. Set ANTHROPIC_API_KEY or CLAUDE_CODE_OAUTH_TOKEN environment variable"
|
|
28496
28577
|
);
|
|
28497
28578
|
}
|
|
28498
|
-
|
|
28499
|
-
return { apiKey, isProxyProvider };
|
|
28579
|
+
return apiKey;
|
|
28500
28580
|
}
|
|
28501
|
-
function
|
|
28502
|
-
return
|
|
28503
|
-
mainModel: process.env.LOOPLIA_AGENT_MODEL_MAIN ?? DEFAULT_SETTINGS.agents.main,
|
|
28504
|
-
executorModel: process.env.LOOPLIA_AGENT_MODEL_EXECUTOR ?? DEFAULT_SETTINGS.agents.executor
|
|
28505
|
-
};
|
|
28581
|
+
function getMainModel() {
|
|
28582
|
+
return process.env.LOOPLIA_AGENT_MODEL_MAIN ?? DEFAULT_SETTINGS.agents.main;
|
|
28506
28583
|
}
|
|
28507
28584
|
function* processEvent(event, progressTracker, context) {
|
|
28508
28585
|
if (event.type === "tool_start" && event.tool === "Skill") {
|
|
@@ -28518,8 +28595,8 @@ function* processEvent(event, progressTracker, context) {
|
|
|
28518
28595
|
}
|
|
28519
28596
|
async function* executeAgenticQueryStreaming(prompt, jsonSchema, config2) {
|
|
28520
28597
|
const resolvedConfig = resolveConfig(config2);
|
|
28521
|
-
|
|
28522
|
-
const
|
|
28598
|
+
await initializeAndValidateApiKey(config2);
|
|
28599
|
+
const mainModel = getMainModel();
|
|
28523
28600
|
try {
|
|
28524
28601
|
const workspace = config2?.workspace ?? await getOrInitWorkspace(
|
|
28525
28602
|
resolvedConfig.workspace,
|
|
@@ -28547,54 +28624,24 @@ async function* executeAgenticQueryStreaming(prompt, jsonSchema, config2) {
|
|
|
28547
28624
|
const context = createTransformContext(
|
|
28548
28625
|
resolvedConfig.model
|
|
28549
28626
|
);
|
|
28550
|
-
const pluginPaths = await getPluginPaths();
|
|
28627
|
+
const pluginPaths = process.env.LOOPLIA_NO_PLUGINS === "true" ? [] : await getPluginPaths();
|
|
28628
|
+
if (process.env.LOOPLIA_DEBUG === "true") {
|
|
28629
|
+
console.error(
|
|
28630
|
+
"[LOOPLIA_DEBUG] Plugin paths:",
|
|
28631
|
+
JSON.stringify(pluginPaths)
|
|
28632
|
+
);
|
|
28633
|
+
}
|
|
28551
28634
|
const userCwd = process.cwd();
|
|
28552
|
-
const loopliaHome = getLoopliaPluginPath();
|
|
28553
|
-
|
|
28554
|
-
|
|
28555
|
-
|
|
28556
|
-
|
|
28557
|
-
When executing looplia workflows (/run commands), use the "workflow-executor-inline" skill.
|
|
28558
|
-
Execute all workflow steps INLINE without spawning Task subagents.
|
|
28559
|
-
This ensures compatibility with your current API provider.` : "";
|
|
28560
|
-
const agents = isProxyProvider ? void 0 : {
|
|
28561
|
-
"skill-executor": {
|
|
28562
|
-
description: "Universal skill orchestrator for looplia workflow steps. Executes a single workflow step by invoking skills.",
|
|
28563
|
-
prompt: `You are the looplia skill-executor. Execute ONE workflow step by invoking the specified skill.
|
|
28564
|
-
|
|
28565
|
-
## Execution Protocol
|
|
28566
|
-
1. Read input files (if provided)
|
|
28567
|
-
2. Invoke the skill using the Skill tool
|
|
28568
|
-
3. Execute the mission with skill context
|
|
28569
|
-
4. Write JSON output to the specified path using Write tool
|
|
28570
|
-
|
|
28571
|
-
## CRITICAL: Output Writing is MANDATORY
|
|
28572
|
-
YOU MUST CALL THE WRITE TOOL before completing. If you don't write the file, the workflow fails.
|
|
28573
|
-
|
|
28574
|
-
## Rules
|
|
28575
|
-
- ALWAYS invoke the specified skill using Skill tool
|
|
28576
|
-
- ALWAYS write output to the exact path using Write tool
|
|
28577
|
-
- NEVER return results as text - always write JSON to output file
|
|
28578
|
-
- NEVER spawn Task subagents - execute skills directly
|
|
28579
|
-
- ALWAYS include contentId in JSON outputs`,
|
|
28580
|
-
tools: [
|
|
28581
|
-
"Read",
|
|
28582
|
-
"Write",
|
|
28583
|
-
"Skill",
|
|
28584
|
-
"Glob",
|
|
28585
|
-
"Grep",
|
|
28586
|
-
"WebSearch",
|
|
28587
|
-
"WebFetch"
|
|
28588
|
-
],
|
|
28589
|
-
model: executorModel
|
|
28590
|
-
}
|
|
28591
|
-
};
|
|
28635
|
+
const loopliaHome = process.env.LOOPLIA_WORKSPACE_PATH ?? getLoopliaPluginPath();
|
|
28636
|
+
if (process.env.LOOPLIA_DEBUG === "true") {
|
|
28637
|
+
console.error("[LOOPLIA_DEBUG] loopliaHome:", loopliaHome);
|
|
28638
|
+
}
|
|
28592
28639
|
const claudeCodePath = findClaudeCodePath();
|
|
28593
28640
|
const result = query({
|
|
28594
28641
|
prompt,
|
|
28595
28642
|
options: {
|
|
28596
|
-
// v0.6.8: Use system-installed Claude Code
|
|
28597
|
-
pathToClaudeCodeExecutable: claudeCodePath,
|
|
28643
|
+
// v0.6.8: Use system-installed Claude Code if available, otherwise SDK uses built-in
|
|
28644
|
+
...claudeCodePath && { pathToClaudeCodeExecutable: claudeCodePath },
|
|
28598
28645
|
// v0.6.6: Use configured main model
|
|
28599
28646
|
model: mainModel,
|
|
28600
28647
|
// v0.6.5: SDK works relative to ~/.looplia (sandbox, workflows, etc.)
|
|
@@ -28604,7 +28651,7 @@ YOU MUST CALL THE WRITE TOOL before completing. If you don't write the file, the
|
|
|
28604
28651
|
// v0.6.5: Load plugins from local paths instead of project settings
|
|
28605
28652
|
plugins: pluginPaths,
|
|
28606
28653
|
// v0.6.5: Append looplia system prompt + user context to claude_code preset
|
|
28607
|
-
// v0.6.
|
|
28654
|
+
// v0.6.9: Removed provider-aware hint - unified subagent strategy for all providers
|
|
28608
28655
|
systemPrompt: {
|
|
28609
28656
|
type: "preset",
|
|
28610
28657
|
preset: "claude_code",
|
|
@@ -28614,7 +28661,7 @@ YOU MUST CALL THE WRITE TOOL before completing. If you don't write the file, the
|
|
|
28614
28661
|
|
|
28615
28662
|
User Working Directory: ${userCwd}
|
|
28616
28663
|
|
|
28617
|
-
When processing --file arguments or user file paths, resolve them against the User Working Directory above
|
|
28664
|
+
When processing --file arguments or user file paths, resolve them against the User Working Directory above.`
|
|
28618
28665
|
},
|
|
28619
28666
|
// v0.6.0: Enable Task for subagent spawning, Write/Glob for file operations
|
|
28620
28667
|
// v0.6.3: Added WebSearch/WebFetch for input-less search skill
|
|
@@ -28627,9 +28674,8 @@ When processing --file arguments or user file paths, resolve them against the Us
|
|
|
28627
28674
|
"WebSearch",
|
|
28628
28675
|
"WebFetch"
|
|
28629
28676
|
],
|
|
28630
|
-
outputFormat: { type: "json_schema", schema: jsonSchema }
|
|
28631
|
-
// v0.6.
|
|
28632
|
-
agents
|
|
28677
|
+
outputFormat: { type: "json_schema", schema: jsonSchema }
|
|
28678
|
+
// v0.6.9: No custom agents - using built-in general-purpose for workflow steps
|
|
28633
28679
|
}
|
|
28634
28680
|
});
|
|
28635
28681
|
let finalResult;
|
|
@@ -28658,6 +28704,25 @@ When processing --file arguments or user file paths, resolve them against the Us
|
|
|
28658
28704
|
error: { type: "unknown", message: "No result received" }
|
|
28659
28705
|
};
|
|
28660
28706
|
} catch (error2) {
|
|
28707
|
+
if (process.env.LOOPLIA_DEBUG === "true") {
|
|
28708
|
+
const debugInfo = {
|
|
28709
|
+
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
28710
|
+
errorType: error2 instanceof Error ? error2.constructor.name : typeof error2,
|
|
28711
|
+
errorMessage: error2 instanceof Error ? error2.message : String(error2),
|
|
28712
|
+
errorStack: error2 instanceof Error ? error2.stack : void 0,
|
|
28713
|
+
cwd: process.cwd(),
|
|
28714
|
+
loopliaHome: getLoopliaPluginPath(),
|
|
28715
|
+
env: {
|
|
28716
|
+
LOOPLIA_DEBUG: process.env.LOOPLIA_DEBUG,
|
|
28717
|
+
NODE_ENV: process.env.NODE_ENV,
|
|
28718
|
+
HOME: process.env.HOME
|
|
28719
|
+
}
|
|
28720
|
+
};
|
|
28721
|
+
console.error(
|
|
28722
|
+
"[LOOPLIA_DEBUG] SDK Error:",
|
|
28723
|
+
JSON.stringify(debugInfo, null, 2)
|
|
28724
|
+
);
|
|
28725
|
+
}
|
|
28661
28726
|
return mapException(error2);
|
|
28662
28727
|
}
|
|
28663
28728
|
}
|
|
@@ -32614,11 +32679,11 @@ async function runConfigCommand(args) {
|
|
|
32614
32679
|
}
|
|
32615
32680
|
|
|
32616
32681
|
// src/commands/init.ts
|
|
32617
|
-
import { dirname as
|
|
32682
|
+
import { dirname as dirname4, join as join7 } from "path";
|
|
32618
32683
|
import { createInterface as createInterface2 } from "readline";
|
|
32619
32684
|
import { fileURLToPath as fileURLToPath3 } from "url";
|
|
32620
32685
|
function getCliBundledPluginsPath() {
|
|
32621
|
-
const currentFile = typeof __dirname !== "undefined" ? __dirname :
|
|
32686
|
+
const currentFile = typeof __dirname !== "undefined" ? __dirname : dirname4(fileURLToPath3(import.meta.url));
|
|
32622
32687
|
return join7(currentFile, "..", "plugins");
|
|
32623
32688
|
}
|
|
32624
32689
|
function printInitHelp() {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@looplia/looplia-cli",
|
|
3
|
-
"version": "0.6.
|
|
3
|
+
"version": "0.6.9",
|
|
4
4
|
"description": "Looplia CLI - AI-powered workflow automation tool",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "Elastic-2.0",
|
|
@@ -30,7 +30,7 @@
|
|
|
30
30
|
"scripts": {
|
|
31
31
|
"build": "tsup",
|
|
32
32
|
"dev": "tsup --watch",
|
|
33
|
-
"start": "node dist/
|
|
33
|
+
"start": "node dist/cli.js",
|
|
34
34
|
"test": "bun run build && bun test",
|
|
35
35
|
"test:watch": "bun test --watch",
|
|
36
36
|
"test:unit": "bun test commands/",
|
|
@@ -76,6 +76,6 @@ LOCK_FILE="${VALIDATION_JSON}.lock"
|
|
|
76
76
|
# Update validation.json to mark step as validated (v0.6.0 uses "steps")
|
|
77
77
|
jq --arg art "$ARTIFACT" '.steps[$art].validated = true' "$VALIDATION_JSON" > "${VALIDATION_JSON}.tmp"
|
|
78
78
|
mv "${VALIDATION_JSON}.tmp" "$VALIDATION_JSON"
|
|
79
|
-
echo "✓ Validated: $ARTIFACT.json"
|
|
79
|
+
echo "✓ Validated: $ARTIFACT.json" >&2
|
|
80
80
|
|
|
81
81
|
) 200>"$LOCK_FILE"
|
|
@@ -6,14 +6,14 @@ description: |
|
|
|
6
6
|
"execute this looplia pipeline", "/run writing-kit", "start the looplia automation", or
|
|
7
7
|
"process these workflow steps".
|
|
8
8
|
|
|
9
|
-
Architecture: One workflow step triggers one
|
|
10
|
-
invokes
|
|
11
|
-
per-step
|
|
9
|
+
Architecture: One workflow step triggers one general-purpose subagent call, which then
|
|
10
|
+
invokes skills to accomplish the step's mission. Each step = separate context window.
|
|
11
|
+
Handles sandbox management, per-step orchestration, and validation state tracking.
|
|
12
12
|
|
|
13
|
-
v0.6.
|
|
13
|
+
v0.6.9: Unified general-purpose subagent strategy for all providers (context offload).
|
|
14
14
|
---
|
|
15
15
|
|
|
16
|
-
# Workflow Executor Skill (v0.6.
|
|
16
|
+
# Workflow Executor Skill (v0.6.9)
|
|
17
17
|
|
|
18
18
|
Execute looplia workflows defined in `workflows/*.md` files using the skills-first architecture.
|
|
19
19
|
|
|
@@ -26,17 +26,17 @@ Use this skill when:
|
|
|
26
26
|
|
|
27
27
|
---
|
|
28
28
|
|
|
29
|
-
## CRITICAL:
|
|
29
|
+
## CRITICAL: Task Invocation with general-purpose Subagent
|
|
30
30
|
|
|
31
|
-
**v0.6.
|
|
31
|
+
**v0.6.9:** Using built-in `general-purpose` subagent for ALL workflow steps (all providers).
|
|
32
32
|
|
|
33
33
|
When executing a step with `skill: {name}` and `mission:`:
|
|
34
34
|
|
|
35
35
|
```json
|
|
36
36
|
{
|
|
37
|
-
"subagent_type": "
|
|
37
|
+
"subagent_type": "general-purpose",
|
|
38
38
|
"description": "Execute step: {step.id}",
|
|
39
|
-
"prompt": "Execute skill '{step.skill}' for step '{step.id}'.\n\
|
|
39
|
+
"prompt": "Execute skill '{step.skill}' for step '{step.id}'.\n\n## Mission\n{step.mission}\n\n## Execution Protocol\n1. Read input files (if provided)\n2. Invoke the skill using Skill tool\n3. Execute the mission with skill context\n4. Write JSON output to the specified path using Write tool\n\n## CRITICAL: Output Writing is MANDATORY\nYOU MUST CALL THE WRITE TOOL before completing. If you don't write the file, the workflow fails.\n\n## Rules\n- ALWAYS invoke the specified skill using Skill tool\n- ALWAYS write output to the exact path using Write tool\n- NEVER return results as text - always write JSON to output file\n- NEVER spawn Task subagents - execute skills directly\n- ALWAYS include contentId in JSON outputs\n\nInput: {resolved input path}\nOutput: {step.output}\nValidation: {step.validate JSON}"
|
|
40
40
|
}
|
|
41
41
|
```
|
|
42
42
|
|
|
@@ -54,23 +54,22 @@ When executing a step with `skill: {name}` and `mission:`:
|
|
|
54
54
|
**Task tool call:**
|
|
55
55
|
```json
|
|
56
56
|
{
|
|
57
|
-
"subagent_type": "
|
|
57
|
+
"subagent_type": "general-purpose",
|
|
58
58
|
"description": "Execute step: analyze-content",
|
|
59
|
-
"prompt": "Execute skill 'media-reviewer' for step 'analyze-content'.\n\
|
|
59
|
+
"prompt": "Execute skill 'media-reviewer' for step 'analyze-content'.\n\n## Mission\nDeep analysis of video transcript. Extract key themes, important quotes, and narrative structure.\n\n## Execution Protocol\n1. Read input files (if provided)\n2. Invoke the skill using Skill tool\n3. Execute the mission with skill context\n4. Write JSON output to the specified path using Write tool\n\n## CRITICAL: Output Writing is MANDATORY\nYOU MUST CALL THE WRITE TOOL before completing. If you don't write the file, the workflow fails.\n\n## Rules\n- ALWAYS invoke the specified skill using Skill tool\n- ALWAYS write output to the exact path using Write tool\n- NEVER return results as text - always write JSON to output file\n- NEVER spawn Task subagents - execute skills directly\n- ALWAYS include contentId in JSON outputs\n\nInput: sandbox/video-2025-01-15-abc123/inputs/content.md\nOutput: sandbox/video-2025-01-15-abc123/outputs/analysis.json\nValidation: {\"required_fields\":[\"contentId\",\"headline\",\"keyThemes\"]}"
|
|
60
60
|
}
|
|
61
61
|
```
|
|
62
62
|
|
|
63
63
|
### Rules
|
|
64
64
|
|
|
65
|
-
- **ALWAYS** use `subagent_type: "
|
|
65
|
+
- **ALWAYS** use `subagent_type: "general-purpose"` for ALL workflow steps
|
|
66
66
|
- **NEVER** use custom subagent_type per step (removed in v0.6.1)
|
|
67
|
-
- **NEVER** use `subagent_type: "general-purpose"` for workflow steps
|
|
68
67
|
- **VALIDATE** that step has both `skill:` and `mission:` fields
|
|
69
68
|
- **REJECT** steps using deprecated `run:` syntax
|
|
70
69
|
|
|
71
70
|
### Why Per-Step Task Calls (Context Isolation)
|
|
72
71
|
|
|
73
|
-
Each `Task(
|
|
72
|
+
Each `Task(general-purpose)` creates a **separate context window**:
|
|
74
73
|
- Isolates step processing from main agent context
|
|
75
74
|
- Prevents context pollution across steps
|
|
76
75
|
- Enables focused execution with only relevant inputs
|
|
@@ -249,7 +248,7 @@ Computed order: [analyze-content, generate-ideas, build-writing-kit]
|
|
|
249
248
|
**Execute steps ONE AT A TIME (context isolation):**
|
|
250
249
|
|
|
251
250
|
1. Get first unvalidated step from dependency order
|
|
252
|
-
2. Make ONE `Task(
|
|
251
|
+
2. Make ONE `Task(general-purpose)` call for THIS step only
|
|
253
252
|
3. WAIT for Task completion before proceeding
|
|
254
253
|
4. Validate output, update validation.json
|
|
255
254
|
5. REPEAT for next unvalidated step
|
|
@@ -271,10 +270,10 @@ FOR EACH step in dependency order:
|
|
|
271
270
|
┌─────────┐ ┌─────────────────────────────┐
|
|
272
271
|
│ SKIP │ │ 1. INVOKE Task tool: │
|
|
273
272
|
│ (done) │ │ subagent_type: │
|
|
274
|
-
└─────────┘ │ "
|
|
273
|
+
└─────────┘ │ "general-purpose" │
|
|
275
274
|
│ │
|
|
276
|
-
│ 2.
|
|
277
|
-
│
|
|
275
|
+
│ 2. Subagent invokes the │
|
|
276
|
+
│ specified skill │
|
|
278
277
|
│ │
|
|
279
278
|
│ 3. VALIDATE output │
|
|
280
279
|
│ │
|
|
@@ -302,9 +301,9 @@ For step:
|
|
|
302
301
|
Invoke Task tool:
|
|
303
302
|
```json
|
|
304
303
|
{
|
|
305
|
-
"subagent_type": "
|
|
304
|
+
"subagent_type": "general-purpose",
|
|
306
305
|
"description": "Execute step: analyze-content",
|
|
307
|
-
"prompt": "Execute skill 'media-reviewer' for step 'analyze-content'.\n\
|
|
306
|
+
"prompt": "Execute skill 'media-reviewer' for step 'analyze-content'.\n\n## Mission\nDeep analysis of video transcript. Extract key themes, important quotes with timestamps, and narrative structure.\n\n## Execution Protocol\n1. Read input files (if provided)\n2. Invoke the skill using Skill tool\n3. Execute the mission with skill context\n4. Write JSON output to the specified path using Write tool\n\n## CRITICAL: Output Writing is MANDATORY\nYOU MUST CALL THE WRITE TOOL before completing.\n\n## Rules\n- ALWAYS invoke the specified skill using Skill tool\n- ALWAYS write output to the exact path using Write tool\n- NEVER return results as text - always write JSON to output file\n- ALWAYS include contentId in JSON outputs\n\nInput: sandbox/article-2025-12-18-xk7m/inputs/content.md\nOutput: sandbox/article-2025-12-18-xk7m/outputs/analysis.json\nValidation: {\"required_fields\":[\"contentId\",\"headline\",\"keyThemes\"]}"
|
|
308
307
|
}
|
|
309
308
|
```
|
|
310
309
|
|
|
@@ -350,9 +349,9 @@ When step with `final: true` passes validation:
|
|
|
350
349
|
|
|
351
350
|
---
|
|
352
351
|
|
|
353
|
-
## Variable Substitution (v0.6.
|
|
352
|
+
## Variable Substitution (v0.6.9)
|
|
354
353
|
|
|
355
|
-
Resolve variables before passing to
|
|
354
|
+
Resolve variables before passing to general-purpose subagent:
|
|
356
355
|
|
|
357
356
|
| Variable | Resolution | Example |
|
|
358
357
|
|----------|------------|---------|
|
|
@@ -435,21 +434,21 @@ input: ${{ steps.analyze-content.output }}
|
|
|
435
434
|
4. [ORDER] Computed: [analyze-content, generate-ideas, build-writing-kit]
|
|
436
435
|
|
|
437
436
|
5. [STEP] analyze-content
|
|
438
|
-
- Task tool: subagent_type="
|
|
437
|
+
- Task tool: subagent_type="general-purpose"
|
|
439
438
|
- Skill: media-reviewer
|
|
440
439
|
- Output: outputs/analysis.json
|
|
441
440
|
- Validate: PASSED
|
|
442
441
|
- Update: validation.json (analyze-content.validated = true)
|
|
443
442
|
|
|
444
443
|
6. [STEP] generate-ideas
|
|
445
|
-
- Task tool: subagent_type="
|
|
444
|
+
- Task tool: subagent_type="general-purpose"
|
|
446
445
|
- Skill: idea-synthesis
|
|
447
446
|
- Output: outputs/ideas.json
|
|
448
447
|
- Validate: PASSED
|
|
449
448
|
- Update: validation.json (generate-ideas.validated = true)
|
|
450
449
|
|
|
451
450
|
7. [STEP] build-writing-kit
|
|
452
|
-
- Task tool: subagent_type="
|
|
451
|
+
- Task tool: subagent_type="general-purpose"
|
|
453
452
|
- Skill: writing-kit-assembler
|
|
454
453
|
- Output: outputs/writing-kit.json
|
|
455
454
|
- Validate: PASSED
|
|
@@ -463,7 +462,7 @@ input: ${{ steps.analyze-content.output }}
|
|
|
463
462
|
## File References
|
|
464
463
|
|
|
465
464
|
- Workflow definitions: `workflows/*.md`
|
|
466
|
-
-
|
|
465
|
+
- Subagent: Built-in `general-purpose` agent (v0.6.9)
|
|
467
466
|
- Skill definitions: `plugins/*/skills/*/SKILL.md`
|
|
468
467
|
- Sandbox storage: `sandbox/{sandbox-id}/`
|
|
469
468
|
- Validator script: `.claude/skills/workflow-validator/scripts/validate.ts`
|