claude-task-worker 0.117.0 → 0.118.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/README.md CHANGED
@@ -4,6 +4,8 @@ GitHub Issues/PRを定期ポーリングし、Claude Codeに処理を委譲す
4
4
 
5
5
  同梱の Claude Code プラグイン(`plugin/`)と組み合わせることで、Issue の実装からPRのレビュー対応、Dependabot PR の対応までを自動化する。CLI 本体(npm パッケージ)とプラグイン(Claude Code マーケットプレイス)は同じリポジトリ・同じ名前で提供される。
6
6
 
7
+ 使い方のマニュアル(ハンズオン形式の導入・カスタムワーカーの作り方・設定のパッケージ化など)は [`docs/`](./docs/README.md) にある。
8
+
7
9
  ## アーキテクチャ
8
10
 
9
11
  CLI が GitHub ラベルを検知してタスクを起動し、プラグインのスキルが実際の処理を担う。
@@ -181,7 +183,7 @@ claude-task-worker exec-issue --cloud
181
183
  claude-task-worker all --cloud
182
184
  ```
183
185
 
184
- **クラウドで実行されるのは `exec-issue` と `fix-review-point` の2ワーカーだけ**で、それ以外は `--cloud` を付けてもローカル実行のまま残る(`all` / `yolo` にそのまま付けられる)。どのワーカーがクラウドで走るかは起動時にログへ出る。
186
+ `--cloud` を付けたプロセスが起動するワーカーはすべてクラウドで実行される。ワーカーごとの向き不向きは [`docs/cloud.md`](./docs/cloud.md) を参照。
185
187
 
186
188
  前提条件:
187
189
 
@@ -213,7 +215,7 @@ npx claude-task-worker cloud-setup
213
215
  - `--cloud` と併用できないコマンド: `init` / `apply-labels` / `install` / `update` / `cloud-setup` / `usage` / `version` / `list-workers`
214
216
  - `--cloud` は `mode`(`default` / `herdr`)に依存しない。クラウドセッションの作成は `script` コマンドの疑似 pty で完結し、herdr のペインを使わないため、どちらの `mode` でも同じ経路を通る
215
217
 
216
- 詳細は [`docs/prd-cloud-worker-execution.md`](./docs/prd-cloud-worker-execution.md) を参照。
218
+ 詳細は [`docs/cloud.md`](./docs/cloud.md) を参照。
217
219
 
218
220
  ### `--debug`
219
221
 
@@ -239,11 +241,14 @@ claude-task-worker init --inherit-config ~/ctw/shared.json # 指定パスへ
239
241
 
240
242
  - 未指定時は従来どおり cwd 直下の `claude-task-worker.json` / `claude-task-worker.local.json` だけを読む
241
243
  - 値自体の相対パスは起動時の cwd 基準。ファイル内の相対パス(`workerFiles` / `uiDesign.designDir`)は**そのファイルの所在ディレクトリ基準**で解決する
244
+ - 配列(`labels` / `workerFiles` など)は置き換えではなく、cwd 側の値を土台の後ろへ追記する(重複は除く)。cwd の `claude-task-worker.json` と `claude-task-worker.local.json` 同士は従来どおり local が丸ごと置き換え、その結果を土台へ追記する
242
245
  - `claude-task-worker.local.json` は常に cwd 直下のものを読む(指定ファイルと同じディレクトリのものは読まない)。cwd 直下の `claude-task-worker.json` は無くてもよい
243
246
  - 指定ファイルが存在しなければエラー終了する(既定ファイルへは倒さない)。`--project` では絶対パスにして各プロジェクトへ転送する
244
247
  - 定期ワーカーの `lastRun` は指定に関わらずリポジトリ直下の `claude-task-worker.json` で読み書きする。リポジトリ直下に同ファイルが無ければ `lastRun` だけを持つファイルが作られる(他のキーを持たないので土台の設定とは衝突しない)。`init` を `--inherit-config` 付きで実行した場合も、未記録のワーカーの `lastRun` はリポジトリ直下へ記録する(セットアップ直後に定期ワーカーが一斉に走らないようにするため)
245
248
  - スキル(`create-ui-design` / `update-design-md` / `triage-created-issue`)はリポジトリ直下の `claude-task-worker.json` を直接読むため、**`uiDesign` の設定は `--inherit-config` のファイルに書いてもスキルには届かない**。`uiDesign` はリポジトリ直下に書くこと
246
249
 
250
+ 設定・カスタムワーカー・スキルを1つのリポジトリにまとめて配る手順は [`docs/config-package.md`](./docs/config-package.md) を参照。
251
+
247
252
  ### Pen CLI のログイン
248
253
 
249
254
  `.pen` を扱うスキルは Pen CLI の認証を必要とする。UIデザイン先行ワークフローを使うなら一度ログインしておく。
@@ -374,7 +379,7 @@ export const myWorker = createIssuePollingWorker({
374
379
  });
375
380
  ```
376
381
 
377
- 起動時に全件を検証し、次のいずれかがあればタスクを1件も起動せず exit 1 する(メッセージにファイルパスと直し方を含む): ファイルが存在しない/読み込み・トランスパイルに失敗/定義が1つも export されていない/`name` がプリセットと衝突/`name` がカスタム同士で衝突。`claude-task-worker list-workers` でロード結果を確認できる。
382
+ 起動時に全件を検証し、次のいずれかがあればタスクを1件も起動せず exit 1 する(メッセージにファイルパスと直し方を含む): ファイルが存在しない/読み込み・トランスパイルに失敗/定義が1つも export されていない/`name` がプリセットと衝突/`name` がカスタム同士で衝突。`claude-task-worker list-workers` でロード結果を確認できる。作り方の詳しい手順は [`docs/custom-worker.md`](./docs/custom-worker.md) を参照。
378
383
 
379
384
  ## ワークフロー
380
385
 
@@ -922,11 +922,15 @@ function resolveWorkerFilePath(entry, configDir, home) {
922
922
  function isPlainObject(val) {
923
923
  return typeof val === "object" && val !== null && !Array.isArray(val);
924
924
  }
925
- function mergeConfigRaw(base, local) {
925
+ function mergeConfigRaw(base, local, appendArrays = false) {
926
926
  const result = { ...base };
927
927
  for (const [key, val] of Object.entries(local)) {
928
928
  const current = result[key];
929
- result[key] = isPlainObject(current) && isPlainObject(val) ? mergeConfigRaw(current, val) : val;
929
+ if (appendArrays && Array.isArray(current) && Array.isArray(val)) {
930
+ result[key] = [...current, ...val.filter((v) => !current.includes(v))];
931
+ } else {
932
+ result[key] = isPlainObject(current) && isPlainObject(val) ? mergeConfigRaw(current, val, appendArrays) : val;
933
+ }
930
934
  }
931
935
  return result;
932
936
  }
@@ -973,7 +977,7 @@ function readCwdRawConfig() {
973
977
  function loadConfig() {
974
978
  const inheritPath = getInheritConfigPath();
975
979
  const cwdRaw = readCwdRawConfig();
976
- const raw = inheritPath ? mergeConfigRaw(readInheritedRawConfig(inheritPath, process.cwd()), cwdRaw) : cwdRaw;
980
+ const raw = inheritPath ? mergeConfigRaw(readInheritedRawConfig(inheritPath, process.cwd()), cwdRaw, true) : cwdRaw;
977
981
  const result = {
978
982
  ...DEFAULT_CONFIG,
979
983
  labels: [],
@@ -1612,7 +1616,7 @@ import { StringDecoder } from "node:string_decoder";
1612
1616
 
1613
1617
  // src/task-result.ts
1614
1618
  var STDERR_TAIL_LIMIT = 8 * 1024;
1615
- var CLOUD_FAILURE_GUIDANCE = "[worker] \u30AF\u30E9\u30A6\u30C9\u5B9F\u884C\u306E\u524D\u63D0\u6761\u4EF6\uFF08GitHub \u9023\u643A / allow_remote_sessions \u7D44\u7E54\u30DD\u30EA\u30B7\u30FC\uFF09\u304C\u6E80\u305F\u3055\u308C\u3066\u3044\u306A\u3044\u53EF\u80FD\u6027\u304C\u3042\u308A\u307E\u3059\u3002\u8A73\u7D30\u306F docs/cloud-prerequisite-checks.md \u3092\u53C2\u7167\u3057\u3066\u304F\u3060\u3055\u3044\u3002";
1619
+ var CLOUD_FAILURE_GUIDANCE = "[worker] \u30AF\u30E9\u30A6\u30C9\u5B9F\u884C\u306E\u524D\u63D0\u6761\u4EF6\uFF08GitHub \u9023\u643A / allow_remote_sessions \u7D44\u7E54\u30DD\u30EA\u30B7\u30FC\uFF09\u304C\u6E80\u305F\u3055\u308C\u3066\u3044\u306A\u3044\u53EF\u80FD\u6027\u304C\u3042\u308A\u307E\u3059\u3002\u8A73\u7D30\u306F docs/cloud.md \u3092\u53C2\u7167\u3057\u3066\u304F\u3060\u3055\u3044\u3002";
1616
1620
  function appendCloudFailureGuidance(result, cloud) {
1617
1621
  if (!cloud || result.status === "completed") return result;
1618
1622
  return { ...result, output: `${CLOUD_FAILURE_GUIDANCE}
@@ -10,6 +10,7 @@ export declare function buildLabelSpecs(custom: string[]): {
10
10
  export declare function applyLabels(): Promise<void>;
11
11
  export declare const ISSUE_TEMPLATE = "name: \"[claude-task-worker] Issue\u4F5C\u6210\u4F9D\u983C\"\ndescription: claude-task-worker\u3067GitHub Issue\u3092\u4F5C\u6210\u3059\u308B\ntitle: \"[claude-task-worker] Issue\u4F5C\u6210\u4F9D\u983C\"\nlabels:\n - cc-triage-scope\n - cc-issue-request\nbody:\n - type: textarea\n id: request\n attributes:\n label: \u4F9D\u983C\u5185\u5BB9\n description: \u4F5C\u6210\u3057\u3066\u307B\u3057\u3044Issue\u306E\u5185\u5BB9\u3092\u8A18\u8FF0\u3057\u3066\u304F\u3060\u3055\u3044\n validations:\n required: true\n";
12
12
  export declare const ASSIGN_CREATOR_WORKFLOW = "name: Assign creator on issue request\n\non:\n issues:\n types: [opened]\n\njobs:\n assign:\n if: contains(github.event.issue.labels.*.name, 'cc-issue-request')\n runs-on: ubuntu-latest\n permissions:\n issues: write\n steps:\n - uses: actions/github-script@v9\n with:\n script: |\n await github.rest.issues.addAssignees({\n owner: context.repo.owner,\n repo: context.repo.repo,\n issue_number: context.issue.number,\n assignees: [context.payload.issue.user.login]\n });\n";
13
+ export declare function buildInitialConfig(now: string): Record<string, unknown>;
13
14
  export declare function seedCwdLastRun(at: Date): void;
14
15
  export declare function isContentMismatch(result: "created" | "overwritten" | "skipped", expected: string, actual: string): boolean;
15
16
  export declare function init(options?: {
package/dist/config.d.ts CHANGED
@@ -60,7 +60,7 @@ export declare function parseLastRunEntry(val: unknown): LastRunLog;
60
60
  export declare function parseLabelsEntry(val: unknown): string[];
61
61
  export declare function parseWorkerFilesEntry(val: unknown): string[];
62
62
  export declare function resolveWorkerFilePath(entry: string, configDir: string, home: string): string;
63
- export declare function mergeConfigRaw(base: Record<string, unknown>, local: Record<string, unknown>): Record<string, unknown>;
63
+ export declare function mergeConfigRaw(base: Record<string, unknown>, local: Record<string, unknown>, appendArrays?: boolean): Record<string, unknown>;
64
64
  export declare function resolveInheritedRelativePaths(raw: Record<string, unknown>, configDir: string, repoRoot: string): Record<string, unknown>;
65
65
  export declare function loadConfig(): Config;
66
66
  export declare function getWorkerConfig(workerName: string): WorkerRuntimeConfig;
package/dist/index.js CHANGED
@@ -64,7 +64,7 @@ import {
64
64
  shutdown,
65
65
  waitForAllProcesses,
66
66
  writeLastRun
67
- } from "./chunk-FAD5CNP4.js";
67
+ } from "./chunk-ULDG6SEE.js";
68
68
  import {
69
69
  captureConsole
70
70
  } from "./chunk-N42YU3GJ.js";
@@ -921,14 +921,18 @@ function logWriteResult(result, path) {
921
921
  else if (result === "overwritten") console.log(`[init] Overwritten: ${path}`);
922
922
  else console.log(`[init] Already exists: ${path}`);
923
923
  }
924
- async function createConfig(force) {
925
- const now = (/* @__PURE__ */ new Date()).toISOString();
926
- const initialConfig = {
927
- ...DEFAULT_CONFIG,
924
+ function buildInitialConfig(now) {
925
+ const { labels: _labels, workerFiles: _workerFiles, ...rest } = DEFAULT_CONFIG;
926
+ return {
927
+ ...rest,
928
928
  uiDesign: { ...DEFAULT_UI_DESIGN_CONFIG },
929
929
  lastRun: Object.fromEntries(SCHEDULED_WORKER_NAMES.map((name) => [name, now])),
930
930
  workers: {}
931
931
  };
932
+ }
933
+ async function createConfig(force) {
934
+ const now = (/* @__PURE__ */ new Date()).toISOString();
935
+ const initialConfig = buildInitialConfig(now);
932
936
  const inheritPath = getInheritConfigPath();
933
937
  const path = inheritPath ?? CONFIG_PATH;
934
938
  const result = await writeFileWithMode(path, JSON.stringify(initialConfig, null, 2), force);
package/dist/lib.js CHANGED
@@ -58,7 +58,7 @@ import {
58
58
  removeWorktreeByBranch,
59
59
  run,
60
60
  syncDefaultBranch
61
- } from "./chunk-FAD5CNP4.js";
61
+ } from "./chunk-ULDG6SEE.js";
62
62
  import "./chunk-N42YU3GJ.js";
63
63
  export {
64
64
  CLOUD_DONE_LABEL,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "claude-task-worker",
3
- "version": "0.117.0",
3
+ "version": "0.118.0",
4
4
  "description": "CLI tool that polls GitHub Issues/PRs and delegates work to Claude CLI",
5
5
  "type": "module",
6
6
  "main": "dist/index.js",