oh-my-customcode 0.68.2 → 0.70.0
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/index.js +167 -29
- package/dist/index.js +101 -13
- package/package.json +1 -1
- package/templates/.claude/hooks/hooks.json +10 -0
- package/templates/.claude/hooks/scripts/omcustom-auto-update.sh +170 -0
- package/templates/.claude/skills/intent-detection/patterns/agent-triggers.yaml +1 -1
- package/templates/.claude/skills/omcustom-feedback/SKILL.md +36 -77
- package/templates/.claude/skills/professor-triage/SKILL.md +196 -89
- package/templates/manifest.json +1 -1
- package/templates/workflows/auto-dev.yaml +1 -1
package/dist/cli/index.js
CHANGED
|
@@ -9325,7 +9325,7 @@ var init_package = __esm(() => {
|
|
|
9325
9325
|
workspaces: [
|
|
9326
9326
|
"packages/*"
|
|
9327
9327
|
],
|
|
9328
|
-
version: "0.
|
|
9328
|
+
version: "0.70.0",
|
|
9329
9329
|
description: "Batteries-included agent harness for Claude Code",
|
|
9330
9330
|
type: "module",
|
|
9331
9331
|
bin: {
|
|
@@ -24826,7 +24826,9 @@ var en_default = {
|
|
|
24826
24826
|
projectLatestSuffix: "(latest)",
|
|
24827
24827
|
newVersionAvailable: "[Info] oh-my-customcode v{{latest}} available (current: v{{current}}). Run 'npm i -g oh-my-customcode' to upgrade.",
|
|
24828
24828
|
rtkMissing: "[RTK] RTK is not installed. Attempting installation...",
|
|
24829
|
-
rtkInstalled: "[RTK] ✓ RTK installed — 60-90% token savings activated"
|
|
24829
|
+
rtkInstalled: "[RTK] ✓ RTK installed — 60-90% token savings activated",
|
|
24830
|
+
codexMissing: "[Codex] Codex CLI is not installed. Attempting installation...",
|
|
24831
|
+
codexInstalled: "[Codex] ✓ Codex CLI installed"
|
|
24830
24832
|
},
|
|
24831
24833
|
list: {
|
|
24832
24834
|
description: "List installed components",
|
|
@@ -24930,6 +24932,10 @@ var en_default = {
|
|
|
24930
24932
|
rtk: {
|
|
24931
24933
|
pass: "RTK installed",
|
|
24932
24934
|
warn: "RTK not installed — token savings unavailable"
|
|
24935
|
+
},
|
|
24936
|
+
codex: {
|
|
24937
|
+
pass: "Codex CLI installed",
|
|
24938
|
+
warn: "Codex CLI not installed — AI-assisted development unavailable"
|
|
24933
24939
|
}
|
|
24934
24940
|
}
|
|
24935
24941
|
},
|
|
@@ -24993,7 +24999,11 @@ var en_default = {
|
|
|
24993
24999
|
rtk_installing: "Installing RTK...",
|
|
24994
25000
|
rtk_success: "RTK installed successfully",
|
|
24995
25001
|
rtk_already: "RTK already installed",
|
|
24996
|
-
rtk_install_failed: "RTK installation failed"
|
|
25002
|
+
rtk_install_failed: "RTK installation failed",
|
|
25003
|
+
codex_installing: "Installing Codex CLI...",
|
|
25004
|
+
codex_success: "Codex CLI installed successfully",
|
|
25005
|
+
codex_already: "Codex CLI already installed",
|
|
25006
|
+
codex_install_failed: "Codex CLI installation failed"
|
|
24997
25007
|
},
|
|
24998
25008
|
init: {
|
|
24999
25009
|
description: "Initialize oh-my-customcode in the current directory",
|
|
@@ -25223,7 +25233,9 @@ var ko_default = {
|
|
|
25223
25233
|
projectLatestSuffix: "(최신)",
|
|
25224
25234
|
newVersionAvailable: "[정보] oh-my-customcode v{{latest}} 사용 가능 (현재: v{{current}}). 'npm i -g oh-my-customcode'를 실행하여 업그레이드하세요.",
|
|
25225
25235
|
rtkMissing: "[RTK] RTK가 설치되지 않았습니다. 설치를 시도합니다...",
|
|
25226
|
-
rtkInstalled: "[RTK] ✓ RTK 설치 완료 — 토큰 60-90% 절감 활성화"
|
|
25236
|
+
rtkInstalled: "[RTK] ✓ RTK 설치 완료 — 토큰 60-90% 절감 활성화",
|
|
25237
|
+
codexMissing: "[Codex] Codex CLI가 설치되지 않았습니다. 설치를 시도합니다...",
|
|
25238
|
+
codexInstalled: "[Codex] ✓ Codex CLI 설치 완료"
|
|
25227
25239
|
},
|
|
25228
25240
|
list: {
|
|
25229
25241
|
description: "설치된 컴포넌트 목록 표시",
|
|
@@ -25327,6 +25339,10 @@ var ko_default = {
|
|
|
25327
25339
|
rtk: {
|
|
25328
25340
|
pass: "RTK 설치됨",
|
|
25329
25341
|
warn: "RTK 미설치 — 토큰 절감 불가"
|
|
25342
|
+
},
|
|
25343
|
+
codex: {
|
|
25344
|
+
pass: "Codex CLI 설치됨",
|
|
25345
|
+
warn: "Codex CLI 미설치 — AI 개발 지원 불가"
|
|
25330
25346
|
}
|
|
25331
25347
|
}
|
|
25332
25348
|
},
|
|
@@ -25390,7 +25406,11 @@ var ko_default = {
|
|
|
25390
25406
|
rtk_installing: "RTK 설치 중...",
|
|
25391
25407
|
rtk_success: "RTK 설치 완료",
|
|
25392
25408
|
rtk_already: "RTK 이미 설치됨",
|
|
25393
|
-
rtk_install_failed: "RTK 설치 실패"
|
|
25409
|
+
rtk_install_failed: "RTK 설치 실패",
|
|
25410
|
+
codex_installing: "Codex CLI 설치 중...",
|
|
25411
|
+
codex_success: "Codex CLI 설치 완료",
|
|
25412
|
+
codex_already: "Codex CLI 이미 설치됨",
|
|
25413
|
+
codex_install_failed: "Codex CLI 설치 실패"
|
|
25394
25414
|
},
|
|
25395
25415
|
init: {
|
|
25396
25416
|
description: "현재 디렉토리에 oh-my-customcode 초기화",
|
|
@@ -25820,9 +25840,9 @@ var $stringify = publicApi.stringify;
|
|
|
25820
25840
|
var $visit = visit.visit;
|
|
25821
25841
|
var $visitAsync = visit.visitAsync;
|
|
25822
25842
|
|
|
25823
|
-
// src/core/
|
|
25824
|
-
|
|
25825
|
-
import {
|
|
25843
|
+
// src/core/codex-installer.ts
|
|
25844
|
+
import { execSync as execSync3 } from "node:child_process";
|
|
25845
|
+
import { platform } from "node:os";
|
|
25826
25846
|
|
|
25827
25847
|
// src/utils/logger.ts
|
|
25828
25848
|
var currentOptions = {
|
|
@@ -26043,7 +26063,77 @@ function success(messageKey, params) {
|
|
|
26043
26063
|
}
|
|
26044
26064
|
}
|
|
26045
26065
|
|
|
26066
|
+
// src/core/codex-installer.ts
|
|
26067
|
+
var defaultDeps = {
|
|
26068
|
+
exec: execSync3,
|
|
26069
|
+
getPlatform: platform
|
|
26070
|
+
};
|
|
26071
|
+
function isCodexInstalled(deps = defaultDeps) {
|
|
26072
|
+
try {
|
|
26073
|
+
deps.exec("which codex", { stdio: "pipe", timeout: 3000 });
|
|
26074
|
+
return true;
|
|
26075
|
+
} catch {
|
|
26076
|
+
return false;
|
|
26077
|
+
}
|
|
26078
|
+
}
|
|
26079
|
+
function getCodexVersion(deps = defaultDeps) {
|
|
26080
|
+
try {
|
|
26081
|
+
return deps.exec("codex --version", {
|
|
26082
|
+
encoding: "utf-8",
|
|
26083
|
+
stdio: "pipe",
|
|
26084
|
+
timeout: 3000
|
|
26085
|
+
}).trim();
|
|
26086
|
+
} catch {
|
|
26087
|
+
return null;
|
|
26088
|
+
}
|
|
26089
|
+
}
|
|
26090
|
+
function installCodex(deps = defaultDeps) {
|
|
26091
|
+
if (process.env.CI || false || false) {
|
|
26092
|
+
return false;
|
|
26093
|
+
}
|
|
26094
|
+
if (isCodexInstalled(deps)) {
|
|
26095
|
+
info("codex.already_installed");
|
|
26096
|
+
return true;
|
|
26097
|
+
}
|
|
26098
|
+
const os = deps.getPlatform();
|
|
26099
|
+
try {
|
|
26100
|
+
if (os === "darwin") {
|
|
26101
|
+
try {
|
|
26102
|
+
info("codex.installing_brew");
|
|
26103
|
+
deps.exec("brew install openai-codex", {
|
|
26104
|
+
stdio: "inherit",
|
|
26105
|
+
timeout: 120000
|
|
26106
|
+
});
|
|
26107
|
+
return isCodexInstalled(deps);
|
|
26108
|
+
} catch {
|
|
26109
|
+
info("codex.installing_npm");
|
|
26110
|
+
deps.exec("npm install -g @openai/codex", {
|
|
26111
|
+
stdio: "inherit",
|
|
26112
|
+
timeout: 120000
|
|
26113
|
+
});
|
|
26114
|
+
return isCodexInstalled(deps);
|
|
26115
|
+
}
|
|
26116
|
+
} else if (os === "linux") {
|
|
26117
|
+
info("codex.installing_npm");
|
|
26118
|
+
deps.exec("npm install -g @openai/codex", {
|
|
26119
|
+
stdio: "inherit",
|
|
26120
|
+
timeout: 120000
|
|
26121
|
+
});
|
|
26122
|
+
return isCodexInstalled(deps);
|
|
26123
|
+
} else {
|
|
26124
|
+
warn("codex.unsupported_os", { os });
|
|
26125
|
+
return false;
|
|
26126
|
+
}
|
|
26127
|
+
} catch (err) {
|
|
26128
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
26129
|
+
warn("codex.install_failed", { error: message });
|
|
26130
|
+
return false;
|
|
26131
|
+
}
|
|
26132
|
+
}
|
|
26133
|
+
|
|
26046
26134
|
// src/core/config.ts
|
|
26135
|
+
init_fs();
|
|
26136
|
+
import { join as join3 } from "node:path";
|
|
26047
26137
|
var CONFIG_FILE = ".omcustomrc.json";
|
|
26048
26138
|
var CURRENT_CONFIG_VERSION = 1;
|
|
26049
26139
|
function getDefaultConfig() {
|
|
@@ -26403,56 +26493,60 @@ async function generateAndWriteLockfileForDir(targetDir) {
|
|
|
26403
26493
|
}
|
|
26404
26494
|
|
|
26405
26495
|
// src/core/rtk-installer.ts
|
|
26406
|
-
import { execSync as
|
|
26407
|
-
import { platform } from "node:os";
|
|
26408
|
-
|
|
26496
|
+
import { execSync as execSync4 } from "node:child_process";
|
|
26497
|
+
import { platform as platform2 } from "node:os";
|
|
26498
|
+
var defaultDeps2 = {
|
|
26499
|
+
exec: execSync4,
|
|
26500
|
+
getPlatform: platform2
|
|
26501
|
+
};
|
|
26502
|
+
function isRtkInstalled(deps = defaultDeps2) {
|
|
26409
26503
|
try {
|
|
26410
|
-
|
|
26504
|
+
deps.exec("which rtk", { stdio: "pipe", timeout: 3000 });
|
|
26411
26505
|
return true;
|
|
26412
26506
|
} catch {
|
|
26413
26507
|
return false;
|
|
26414
26508
|
}
|
|
26415
26509
|
}
|
|
26416
|
-
function getRtkVersion() {
|
|
26510
|
+
function getRtkVersion(deps = defaultDeps2) {
|
|
26417
26511
|
try {
|
|
26418
|
-
return
|
|
26512
|
+
return deps.exec("rtk --version", { encoding: "utf-8", stdio: "pipe", timeout: 3000 }).trim();
|
|
26419
26513
|
} catch {
|
|
26420
26514
|
return null;
|
|
26421
26515
|
}
|
|
26422
26516
|
}
|
|
26423
|
-
function installRtk() {
|
|
26517
|
+
function installRtk(deps = defaultDeps2) {
|
|
26424
26518
|
if (process.env.CI || false || false) {
|
|
26425
26519
|
return false;
|
|
26426
26520
|
}
|
|
26427
|
-
if (isRtkInstalled()) {
|
|
26521
|
+
if (isRtkInstalled(deps)) {
|
|
26428
26522
|
info("rtk.already_installed");
|
|
26429
26523
|
return true;
|
|
26430
26524
|
}
|
|
26431
|
-
const os =
|
|
26525
|
+
const os = deps.getPlatform();
|
|
26432
26526
|
try {
|
|
26433
26527
|
if (os === "darwin") {
|
|
26434
26528
|
try {
|
|
26435
26529
|
info("rtk.installing_brew");
|
|
26436
|
-
|
|
26530
|
+
deps.exec("brew install rtk-ai/tap/rtk", {
|
|
26437
26531
|
stdio: "inherit",
|
|
26438
26532
|
timeout: 120000
|
|
26439
26533
|
});
|
|
26440
26534
|
return true;
|
|
26441
26535
|
} catch {
|
|
26442
26536
|
info("rtk.installing_curl");
|
|
26443
|
-
|
|
26537
|
+
deps.exec("curl -fsSL https://raw.githubusercontent.com/rtk-ai/rtk/refs/heads/master/install.sh | sh", {
|
|
26444
26538
|
stdio: "inherit",
|
|
26445
26539
|
timeout: 120000
|
|
26446
26540
|
});
|
|
26447
|
-
return isRtkInstalled();
|
|
26541
|
+
return isRtkInstalled(deps);
|
|
26448
26542
|
}
|
|
26449
26543
|
} else if (os === "linux") {
|
|
26450
26544
|
info("rtk.installing_curl");
|
|
26451
|
-
|
|
26545
|
+
deps.exec("curl -fsSL https://raw.githubusercontent.com/rtk-ai/rtk/refs/heads/master/install.sh | sh", {
|
|
26452
26546
|
stdio: "inherit",
|
|
26453
26547
|
timeout: 120000
|
|
26454
26548
|
});
|
|
26455
|
-
return isRtkInstalled();
|
|
26549
|
+
return isRtkInstalled(deps);
|
|
26456
26550
|
} else {
|
|
26457
26551
|
warn("rtk.unsupported_os", { os });
|
|
26458
26552
|
return false;
|
|
@@ -26780,6 +26874,23 @@ async function checkRtk() {
|
|
|
26780
26874
|
fixable: false
|
|
26781
26875
|
};
|
|
26782
26876
|
}
|
|
26877
|
+
async function checkCodex() {
|
|
26878
|
+
if (!isCodexInstalled()) {
|
|
26879
|
+
return {
|
|
26880
|
+
name: "Codex",
|
|
26881
|
+
status: "warn",
|
|
26882
|
+
message: "Codex CLI not installed — install manually: npm install -g @openai/codex",
|
|
26883
|
+
fixable: true
|
|
26884
|
+
};
|
|
26885
|
+
}
|
|
26886
|
+
const version = getCodexVersion();
|
|
26887
|
+
return {
|
|
26888
|
+
name: "Codex",
|
|
26889
|
+
status: "pass",
|
|
26890
|
+
message: `Codex CLI OK (${version ?? "unknown version"})`,
|
|
26891
|
+
fixable: false
|
|
26892
|
+
};
|
|
26893
|
+
}
|
|
26783
26894
|
async function checkContexts(targetDir, rootDir = ".claude") {
|
|
26784
26895
|
const contextsDir = path.join(targetDir, rootDir, "contexts");
|
|
26785
26896
|
const exists2 = await isDirectory(contextsDir);
|
|
@@ -26883,7 +26994,8 @@ async function fixSingleIssue(check, targetDir, rootDir = ".claude") {
|
|
|
26883
26994
|
const fixedCount = await fixBrokenSymlinks(targetDir, fullPaths);
|
|
26884
26995
|
return fixedCount > 0;
|
|
26885
26996
|
},
|
|
26886
|
-
RTK: async () => Promise.resolve(installRtk())
|
|
26997
|
+
RTK: async () => Promise.resolve(installRtk()),
|
|
26998
|
+
Codex: async () => Promise.resolve(installCodex())
|
|
26887
26999
|
};
|
|
26888
27000
|
const fixer = fixMap[check.name];
|
|
26889
27001
|
return fixer ? fixer() : false;
|
|
@@ -27032,7 +27144,8 @@ async function runAllChecks(targetDir, layout, packageVersion, includeUpdates) {
|
|
|
27032
27144
|
checkHooks(targetDir, layout.rootDir),
|
|
27033
27145
|
checkContexts(targetDir, layout.rootDir),
|
|
27034
27146
|
checkCustomComponents(targetDir, layout.rootDir),
|
|
27035
|
-
checkRtk()
|
|
27147
|
+
checkRtk(),
|
|
27148
|
+
checkCodex()
|
|
27036
27149
|
]);
|
|
27037
27150
|
const frameworkCheck = await checkFrameworkDrift(targetDir, packageVersion);
|
|
27038
27151
|
const checksWithFramework = frameworkCheck ? [...baseChecks, frameworkCheck] : baseChecks;
|
|
@@ -27693,6 +27806,19 @@ function installRtkIfNeeded(result) {
|
|
|
27693
27806
|
info("install.rtk_already");
|
|
27694
27807
|
}
|
|
27695
27808
|
}
|
|
27809
|
+
function installCodexIfNeeded(result) {
|
|
27810
|
+
if (!isCodexInstalled()) {
|
|
27811
|
+
info("install.codex_installing");
|
|
27812
|
+
const codexInstalled = installCodex();
|
|
27813
|
+
if (codexInstalled) {
|
|
27814
|
+
info("install.codex_success");
|
|
27815
|
+
} else {
|
|
27816
|
+
result.warnings.push("Codex CLI installation failed — install manually: npm install -g @openai/codex");
|
|
27817
|
+
}
|
|
27818
|
+
} else {
|
|
27819
|
+
info("install.codex_already");
|
|
27820
|
+
}
|
|
27821
|
+
}
|
|
27696
27822
|
async function install(options) {
|
|
27697
27823
|
const result = createInstallResult(options.targetDir);
|
|
27698
27824
|
try {
|
|
@@ -27731,6 +27857,7 @@ async function install(options) {
|
|
|
27731
27857
|
info("install.lockfile_generated", { files: String(lockfileResult.fileCount) });
|
|
27732
27858
|
}
|
|
27733
27859
|
installRtkIfNeeded(result);
|
|
27860
|
+
installCodexIfNeeded(result);
|
|
27734
27861
|
result.success = true;
|
|
27735
27862
|
success("install.success");
|
|
27736
27863
|
} catch (err) {
|
|
@@ -27914,7 +28041,7 @@ async function backupExistingInstallation(targetDir) {
|
|
|
27914
28041
|
|
|
27915
28042
|
// src/core/mcp-config.ts
|
|
27916
28043
|
init_fs();
|
|
27917
|
-
import { execSync as
|
|
28044
|
+
import { execSync as execSync5 } from "node:child_process";
|
|
27918
28045
|
import { writeFile } from "node:fs/promises";
|
|
27919
28046
|
import { join as join8 } from "node:path";
|
|
27920
28047
|
async function generateMCPConfig(targetDir) {
|
|
@@ -27926,15 +28053,15 @@ async function generateMCPConfig(targetDir) {
|
|
|
27926
28053
|
return;
|
|
27927
28054
|
}
|
|
27928
28055
|
try {
|
|
27929
|
-
|
|
28056
|
+
execSync5("uv --version", { stdio: "pipe" });
|
|
27930
28057
|
} catch {
|
|
27931
28058
|
warn("uv (Python package manager) not found. Install it with: curl -LsSf https://astral.sh/uv/install.sh | sh");
|
|
27932
28059
|
warn("Skipping ontology-rag MCP configuration. You can set it up manually later.");
|
|
27933
28060
|
return;
|
|
27934
28061
|
}
|
|
27935
28062
|
try {
|
|
27936
|
-
|
|
27937
|
-
|
|
28063
|
+
execSync5("uv venv .venv", { cwd: targetDir, stdio: "pipe" });
|
|
28064
|
+
execSync5('uv pip install "ontology-rag @ git+https://github.com/baekenough/oh-my-customcode.git#subdirectory=packages/ontology-rag"', { cwd: targetDir, stdio: "pipe" });
|
|
27938
28065
|
} catch (error2) {
|
|
27939
28066
|
const msg = error2 instanceof Error ? error2.message : String(error2);
|
|
27940
28067
|
warn(`Failed to setup ontology-rag: ${msg}`);
|
|
@@ -27977,7 +28104,7 @@ async function generateMCPConfig(targetDir) {
|
|
|
27977
28104
|
}
|
|
27978
28105
|
async function checkUvAvailable() {
|
|
27979
28106
|
try {
|
|
27980
|
-
|
|
28107
|
+
execSync5("uv --version", { stdio: "pipe" });
|
|
27981
28108
|
return true;
|
|
27982
28109
|
} catch {
|
|
27983
28110
|
return false;
|
|
@@ -30306,6 +30433,16 @@ function checkAndInstallRtkAfterUpdate() {
|
|
|
30306
30433
|
}
|
|
30307
30434
|
}
|
|
30308
30435
|
}
|
|
30436
|
+
function checkAndInstallCodexAfterUpdate() {
|
|
30437
|
+
if (!isCodexInstalled()) {
|
|
30438
|
+
warn("update.codex_missing");
|
|
30439
|
+
console.log(i18n.t("cli.update.codexMissing"));
|
|
30440
|
+
const codexInstalled = installCodex();
|
|
30441
|
+
if (codexInstalled) {
|
|
30442
|
+
console.log(i18n.t("cli.update.codexInstalled"));
|
|
30443
|
+
}
|
|
30444
|
+
}
|
|
30445
|
+
}
|
|
30309
30446
|
async function update(options) {
|
|
30310
30447
|
const result = createUpdateResult();
|
|
30311
30448
|
try {
|
|
@@ -30354,6 +30491,7 @@ async function update(options) {
|
|
|
30354
30491
|
});
|
|
30355
30492
|
}
|
|
30356
30493
|
checkAndInstallRtkAfterUpdate();
|
|
30494
|
+
checkAndInstallCodexAfterUpdate();
|
|
30357
30495
|
} catch (err) {
|
|
30358
30496
|
const message = err instanceof Error ? err.message : String(err);
|
|
30359
30497
|
result.error = message;
|
package/dist/index.js
CHANGED
|
@@ -914,6 +914,65 @@ import {
|
|
|
914
914
|
} from "node:fs/promises";
|
|
915
915
|
import { basename as basename2, join as join5 } from "node:path";
|
|
916
916
|
|
|
917
|
+
// src/core/codex-installer.ts
|
|
918
|
+
import { execSync } from "node:child_process";
|
|
919
|
+
import { platform } from "node:os";
|
|
920
|
+
var defaultDeps = {
|
|
921
|
+
exec: execSync,
|
|
922
|
+
getPlatform: platform
|
|
923
|
+
};
|
|
924
|
+
function isCodexInstalled(deps = defaultDeps) {
|
|
925
|
+
try {
|
|
926
|
+
deps.exec("which codex", { stdio: "pipe", timeout: 3000 });
|
|
927
|
+
return true;
|
|
928
|
+
} catch {
|
|
929
|
+
return false;
|
|
930
|
+
}
|
|
931
|
+
}
|
|
932
|
+
function installCodex(deps = defaultDeps) {
|
|
933
|
+
if (process.env.CI || false || false) {
|
|
934
|
+
return false;
|
|
935
|
+
}
|
|
936
|
+
if (isCodexInstalled(deps)) {
|
|
937
|
+
info("codex.already_installed");
|
|
938
|
+
return true;
|
|
939
|
+
}
|
|
940
|
+
const os = deps.getPlatform();
|
|
941
|
+
try {
|
|
942
|
+
if (os === "darwin") {
|
|
943
|
+
try {
|
|
944
|
+
info("codex.installing_brew");
|
|
945
|
+
deps.exec("brew install openai-codex", {
|
|
946
|
+
stdio: "inherit",
|
|
947
|
+
timeout: 120000
|
|
948
|
+
});
|
|
949
|
+
return isCodexInstalled(deps);
|
|
950
|
+
} catch {
|
|
951
|
+
info("codex.installing_npm");
|
|
952
|
+
deps.exec("npm install -g @openai/codex", {
|
|
953
|
+
stdio: "inherit",
|
|
954
|
+
timeout: 120000
|
|
955
|
+
});
|
|
956
|
+
return isCodexInstalled(deps);
|
|
957
|
+
}
|
|
958
|
+
} else if (os === "linux") {
|
|
959
|
+
info("codex.installing_npm");
|
|
960
|
+
deps.exec("npm install -g @openai/codex", {
|
|
961
|
+
stdio: "inherit",
|
|
962
|
+
timeout: 120000
|
|
963
|
+
});
|
|
964
|
+
return isCodexInstalled(deps);
|
|
965
|
+
} else {
|
|
966
|
+
warn("codex.unsupported_os", { os });
|
|
967
|
+
return false;
|
|
968
|
+
}
|
|
969
|
+
} catch (err) {
|
|
970
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
971
|
+
warn("codex.install_failed", { error: message });
|
|
972
|
+
return false;
|
|
973
|
+
}
|
|
974
|
+
}
|
|
975
|
+
|
|
917
976
|
// src/core/file-preservation.ts
|
|
918
977
|
init_fs();
|
|
919
978
|
import { basename, join as join3 } from "node:path";
|
|
@@ -1249,49 +1308,53 @@ async function generateAndWriteLockfileForDir(targetDir) {
|
|
|
1249
1308
|
}
|
|
1250
1309
|
|
|
1251
1310
|
// src/core/rtk-installer.ts
|
|
1252
|
-
import { execSync } from "node:child_process";
|
|
1253
|
-
import { platform } from "node:os";
|
|
1254
|
-
|
|
1311
|
+
import { execSync as execSync2 } from "node:child_process";
|
|
1312
|
+
import { platform as platform2 } from "node:os";
|
|
1313
|
+
var defaultDeps2 = {
|
|
1314
|
+
exec: execSync2,
|
|
1315
|
+
getPlatform: platform2
|
|
1316
|
+
};
|
|
1317
|
+
function isRtkInstalled(deps = defaultDeps2) {
|
|
1255
1318
|
try {
|
|
1256
|
-
|
|
1319
|
+
deps.exec("which rtk", { stdio: "pipe", timeout: 3000 });
|
|
1257
1320
|
return true;
|
|
1258
1321
|
} catch {
|
|
1259
1322
|
return false;
|
|
1260
1323
|
}
|
|
1261
1324
|
}
|
|
1262
|
-
function installRtk() {
|
|
1325
|
+
function installRtk(deps = defaultDeps2) {
|
|
1263
1326
|
if (process.env.CI || false || false) {
|
|
1264
1327
|
return false;
|
|
1265
1328
|
}
|
|
1266
|
-
if (isRtkInstalled()) {
|
|
1329
|
+
if (isRtkInstalled(deps)) {
|
|
1267
1330
|
info("rtk.already_installed");
|
|
1268
1331
|
return true;
|
|
1269
1332
|
}
|
|
1270
|
-
const os =
|
|
1333
|
+
const os = deps.getPlatform();
|
|
1271
1334
|
try {
|
|
1272
1335
|
if (os === "darwin") {
|
|
1273
1336
|
try {
|
|
1274
1337
|
info("rtk.installing_brew");
|
|
1275
|
-
|
|
1338
|
+
deps.exec("brew install rtk-ai/tap/rtk", {
|
|
1276
1339
|
stdio: "inherit",
|
|
1277
1340
|
timeout: 120000
|
|
1278
1341
|
});
|
|
1279
1342
|
return true;
|
|
1280
1343
|
} catch {
|
|
1281
1344
|
info("rtk.installing_curl");
|
|
1282
|
-
|
|
1345
|
+
deps.exec("curl -fsSL https://raw.githubusercontent.com/rtk-ai/rtk/refs/heads/master/install.sh | sh", {
|
|
1283
1346
|
stdio: "inherit",
|
|
1284
1347
|
timeout: 120000
|
|
1285
1348
|
});
|
|
1286
|
-
return isRtkInstalled();
|
|
1349
|
+
return isRtkInstalled(deps);
|
|
1287
1350
|
}
|
|
1288
1351
|
} else if (os === "linux") {
|
|
1289
1352
|
info("rtk.installing_curl");
|
|
1290
|
-
|
|
1353
|
+
deps.exec("curl -fsSL https://raw.githubusercontent.com/rtk-ai/rtk/refs/heads/master/install.sh | sh", {
|
|
1291
1354
|
stdio: "inherit",
|
|
1292
1355
|
timeout: 120000
|
|
1293
1356
|
});
|
|
1294
|
-
return isRtkInstalled();
|
|
1357
|
+
return isRtkInstalled(deps);
|
|
1295
1358
|
} else {
|
|
1296
1359
|
warn("rtk.unsupported_os", { os });
|
|
1297
1360
|
return false;
|
|
@@ -1492,6 +1555,19 @@ function installRtkIfNeeded(result) {
|
|
|
1492
1555
|
info("install.rtk_already");
|
|
1493
1556
|
}
|
|
1494
1557
|
}
|
|
1558
|
+
function installCodexIfNeeded(result) {
|
|
1559
|
+
if (!isCodexInstalled()) {
|
|
1560
|
+
info("install.codex_installing");
|
|
1561
|
+
const codexInstalled = installCodex();
|
|
1562
|
+
if (codexInstalled) {
|
|
1563
|
+
info("install.codex_success");
|
|
1564
|
+
} else {
|
|
1565
|
+
result.warnings.push("Codex CLI installation failed — install manually: npm install -g @openai/codex");
|
|
1566
|
+
}
|
|
1567
|
+
} else {
|
|
1568
|
+
info("install.codex_already");
|
|
1569
|
+
}
|
|
1570
|
+
}
|
|
1495
1571
|
async function install(options) {
|
|
1496
1572
|
const result = createInstallResult(options.targetDir);
|
|
1497
1573
|
try {
|
|
@@ -1530,6 +1606,7 @@ async function install(options) {
|
|
|
1530
1606
|
info("install.lockfile_generated", { files: String(lockfileResult.fileCount) });
|
|
1531
1607
|
}
|
|
1532
1608
|
installRtkIfNeeded(result);
|
|
1609
|
+
installCodexIfNeeded(result);
|
|
1533
1610
|
result.success = true;
|
|
1534
1611
|
success("install.success");
|
|
1535
1612
|
} catch (err) {
|
|
@@ -1743,7 +1820,7 @@ var package_default = {
|
|
|
1743
1820
|
workspaces: [
|
|
1744
1821
|
"packages/*"
|
|
1745
1822
|
],
|
|
1746
|
-
version: "0.
|
|
1823
|
+
version: "0.70.0",
|
|
1747
1824
|
description: "Batteries-included agent harness for Claude Code",
|
|
1748
1825
|
type: "module",
|
|
1749
1826
|
bin: {
|
|
@@ -4588,6 +4665,16 @@ function checkAndInstallRtkAfterUpdate() {
|
|
|
4588
4665
|
}
|
|
4589
4666
|
}
|
|
4590
4667
|
}
|
|
4668
|
+
function checkAndInstallCodexAfterUpdate() {
|
|
4669
|
+
if (!isCodexInstalled()) {
|
|
4670
|
+
warn("update.codex_missing");
|
|
4671
|
+
console.log(i18n.t("cli.update.codexMissing"));
|
|
4672
|
+
const codexInstalled = installCodex();
|
|
4673
|
+
if (codexInstalled) {
|
|
4674
|
+
console.log(i18n.t("cli.update.codexInstalled"));
|
|
4675
|
+
}
|
|
4676
|
+
}
|
|
4677
|
+
}
|
|
4591
4678
|
async function update(options) {
|
|
4592
4679
|
const result = createUpdateResult();
|
|
4593
4680
|
try {
|
|
@@ -4636,6 +4723,7 @@ async function update(options) {
|
|
|
4636
4723
|
});
|
|
4637
4724
|
}
|
|
4638
4725
|
checkAndInstallRtkAfterUpdate();
|
|
4726
|
+
checkAndInstallCodexAfterUpdate();
|
|
4639
4727
|
} catch (err) {
|
|
4640
4728
|
const message = err instanceof Error ? err.message : String(err);
|
|
4641
4729
|
result.error = message;
|
package/package.json
CHANGED
|
@@ -116,6 +116,16 @@
|
|
|
116
116
|
}
|
|
117
117
|
],
|
|
118
118
|
"SessionStart": [
|
|
119
|
+
{
|
|
120
|
+
"matcher": "*",
|
|
121
|
+
"hooks": [
|
|
122
|
+
{
|
|
123
|
+
"type": "command",
|
|
124
|
+
"command": ".claude/hooks/scripts/omcustom-auto-update.sh"
|
|
125
|
+
}
|
|
126
|
+
],
|
|
127
|
+
"description": "Interactive oh-my-customcode update check at session start (#752)"
|
|
128
|
+
},
|
|
119
129
|
{
|
|
120
130
|
"matcher": "*",
|
|
121
131
|
"hooks": [
|