tmuxでClaude CodeとCodexを連携させて一晩放置でゲームを作らせる(実践編)
前回のおさらい
準備編では、Claude CodeとCodexを連携させるアイデアと基本スクリプトを書いた。
Claude Code(実装)
↓ コード出力
Codex(レビュー)
↓ レビュー結果
Claude Code(修正)
↓ 繰り返し...
今回は実際にこの仕組みを動かしてみた。
使ったスクリプト
実際に使ったスクリプトは4つ。
start-tmux.sh(起動スクリプト)
tmuxセッションを左右分割で起動して、それぞれにワーカーを配置する。
#!/bin/bash
# tmuxセッション起動スクリプト
# 左: Claude Code(実装) / 右: Codex(レビュー)
PROJECT_DIR="$(cd "$(dirname "$0")/.." && pwd)"
SESSION_NAME="my-dev" # 好きな名前に変更
MAX_ROUNDS=${1:-10}
# 既存セッションチェック
if tmux has-session -t "$SESSION_NAME" 2>/dev/null; then
echo "セッション '$SESSION_NAME' は既に存在します"
echo "接続: tmux attach -t $SESSION_NAME"
echo "削除: tmux kill-session -t $SESSION_NAME"
exit 1
fi
# ログディレクトリ作成・シグナルファイルクリア
mkdir -p "$PROJECT_DIR/logs"
rm -f "$PROJECT_DIR/logs/.commit_done" "$PROJECT_DIR/logs/.review_done"
# 実行権限付与
chmod +x "$PROJECT_DIR/scripts/claude-worker.sh"
chmod +x "$PROJECT_DIR/scripts/codex-worker.sh"
# tmuxセッション作成
tmux new-session -d -s "$SESSION_NAME" -c "$PROJECT_DIR"
# 左ペイン: Claude Code ワーカー
tmux send-keys -t "$SESSION_NAME" "./scripts/claude-worker.sh $MAX_ROUNDS" C-m
# 右ペイン: Codex ワーカー
tmux split-window -h -t "$SESSION_NAME" -c "$PROJECT_DIR"
tmux send-keys -t "$SESSION_NAME" "./scripts/codex-worker.sh" C-m
# セッションにアタッチ
echo "tmuxセッション '$SESSION_NAME' を起動します..."
echo "左: Claude Code(実装) / 右: Codex(レビュー)"
tmux attach -t "$SESSION_NAME"
claude-worker.sh(左ペイン)
Claude Codeで実装を進める。1ラウンド1タスクで、コミットしたらCodexを待つ。
#!/bin/bash
# Claude Code ワーカー(左ペイン)
# 実装 → コミット → レビュー待ち → 修正のループ
set -e
PROJECT_DIR="$(cd "$(dirname "$0")/.." && pwd)"
LOG_DIR="$PROJECT_DIR/logs"
CLAUDE_LOG="$LOG_DIR/claude.log"
REVIEW_FILE="$LOG_DIR/review.md"
COMMIT_SIGNAL="$LOG_DIR/.commit_done"
REVIEW_SIGNAL="$LOG_DIR/.review_done"
MAX_ROUNDS=${1:-10}
mkdir -p "$LOG_DIR"
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
CYAN='\033[0;36m'
NC='\033[0m'
cd "$PROJECT_DIR"
# シグナルファイル初期化
rm -f "$COMMIT_SIGNAL" "$REVIEW_SIGNAL"
echo -e "${GREEN}=== Claude Code ワーカー開始 ===${NC}"
for ((round=1; round<=MAX_ROUNDS; round++)); do
echo -e "${YELLOW}=== ラウンド $round/$MAX_ROUNDS ===${NC}"
echo "[$(date '+%Y-%m-%d %H:%M:%S')] ラウンド $round 開始" >> "$CLAUDE_LOG"
# Step 1: 実装
echo -e "${CYAN}[実装中...]${NC}"
claude --dangerously-skip-permissions -p "
あなたは○○の開発を担当しています。(ここに何を作っているか書く)
## 指示
1. docs/todo.md を確認して未完了タスクを把握
2. 次の未完了タスクを1つ選んで実装
3. 実装完了後、docs/progress.md に記録
4. 変更をgit commitする(メッセージは日本語で簡潔に)
5. git pushする
6. docs/todo.md の該当項目を完了にマーク
## 制約
- 質問せず自分で判断して進める
- エラーが出たら自力で修正
- 1ラウンド1タスクに集中
実装を開始してください。
" 2>&1 | tee -a "$CLAUDE_LOG"
# コミット完了シグナル
touch "$COMMIT_SIGNAL"
echo -e "${GREEN}[コミット完了 - Codexレビュー待ち...]${NC}"
# レビュー完了待ち
while [ ! -f "$REVIEW_SIGNAL" ]; do
sleep 2
done
rm -f "$REVIEW_SIGNAL"
# Step 2: レビュー結果確認・修正
if [ -f "$REVIEW_FILE" ] && ! grep -qi "LGTM" "$REVIEW_FILE"; then
echo -e "${CYAN}[レビュー指摘あり - 修正中...]${NC}"
claude --dangerously-skip-permissions -p "
Codexから以下のレビューコメントを受けました。
指摘に従って修正し、再度コミットしてpushしてください。
$(cat "$REVIEW_FILE")
" 2>&1 | tee -a "$CLAUDE_LOG"
else
echo -e "${GREEN}[LGTM - 修正不要]${NC}"
fi
# Step 3: Code Simplifier
echo -e "${CYAN}[Code Simplifier 実行中...]${NC}"
claude --dangerously-skip-permissions -p "
/plugin run code-simplifier
最近変更したコードを整理・簡素化してください。
機能は変えずに、可読性と保守性を向上させてください。
変更があればコミットしてpushしてください。
" 2>&1 | tee -a "$CLAUDE_LOG"
echo "[$(date '+%Y-%m-%d %H:%M:%S')] ラウンド $round 完了" >> "$CLAUDE_LOG"
# 全タスク完了チェック
if ! grep -q "\- \[ \]" "$PROJECT_DIR/docs/todo.md" 2>/dev/null; then
echo -e "${GREEN}全タスク完了!${NC}"
break
fi
sleep 2
done
echo -e "${GREEN}=== Claude Code ワーカー終了 ===${NC}"
codex-worker.sh(右ペイン)
コミットを検知してCodexでレビューする。
#!/bin/bash
# Codex ワーカー(右ペイン)
# コミット検知 → レビュー実行のループ
set -e
PROJECT_DIR="$(cd "$(dirname "$0")/.." && pwd)"
LOG_DIR="$PROJECT_DIR/logs"
CODEX_LOG="$LOG_DIR/codex.log"
REVIEW_FILE="$LOG_DIR/review.md"
COMMIT_SIGNAL="$LOG_DIR/.commit_done"
REVIEW_SIGNAL="$LOG_DIR/.review_done"
mkdir -p "$LOG_DIR"
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
CYAN='\033[0;36m'
NC='\033[0m'
cd "$PROJECT_DIR"
echo -e "${GREEN}=== Codex ワーカー開始 ===${NC}"
echo "コミット待機中..."
while true; do
# コミット完了シグナル待ち
if [ -f "$COMMIT_SIGNAL" ]; then
rm -f "$COMMIT_SIGNAL"
echo -e "${YELLOW}=== 新規コミット検知 ===${NC}"
echo "[$(date '+%Y-%m-%d %H:%M:%S')] レビュー開始" >> "$CODEX_LOG"
echo -e "${CYAN}[レビュー中...]${NC}"
codex review --commit HEAD 2>&1 | tee "$REVIEW_FILE" | tee -a "$CODEX_LOG"
echo "[$(date '+%Y-%m-%d %H:%M:%S')] レビュー完了" >> "$CODEX_LOG"
# レビュー完了シグナル
touch "$REVIEW_SIGNAL"
echo -e "${GREEN}[レビュー完了]${NC}"
echo ""
echo "コミット待機中..."
fi
sleep 2
done
ai-loop.sh(シンプル版)
tmuxを使わないシンプル版。直列で実行する。
#!/bin/bash
# AI自動開発ループスクリプト
# Claude Code 実装 → Codex レビュー → Claude Code 修正
set -e
# 設定
PROJECT_DIR="$(cd "$(dirname "$0")/.." && pwd)"
LOG_DIR="$PROJECT_DIR/logs"
CLAUDE_LOG="$LOG_DIR/claude.log"
CODEX_LOG="$LOG_DIR/codex.log"
REVIEW_FILE="$LOG_DIR/review.md"
MAX_ROUNDS=${1:-10}
# ログディレクトリ作成
mkdir -p "$LOG_DIR"
# 色付き出力
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
CYAN='\033[0;36m'
NC='\033[0m'
echo -e "${GREEN}=== AI自動開発ループ開始 ===${NC}"
echo "プロジェクト: $PROJECT_DIR"
echo "最大ラウンド: $MAX_ROUNDS"
echo ""
cd "$PROJECT_DIR"
for ((round=1; round<=MAX_ROUNDS; round++)); do
echo -e "${YELLOW}=== ラウンド $round/$MAX_ROUNDS ===${NC}"
echo "[$(date '+%Y-%m-%d %H:%M:%S')] ラウンド $round 開始" >> "$CLAUDE_LOG"
# Step 1: Claude Code 実装
echo -e "${CYAN}[Step 1] Claude Code 実装中...${NC}"
claude --dangerously-skip-permissions -p "
あなたは○○の開発を担当しています。(ここに何を作っているか書く)
## 指示
1. docs/todo.md を確認して未完了タスクを把握
2. 次の未完了タスクを1つ選んで実装
3. 実装完了後、docs/progress.md に記録
4. 変更をgit commitする(メッセージは日本語で簡潔に)
5. git pushする
6. docs/todo.md の該当項目を完了にマーク
## 制約
- 質問せず自分で判断して進める
- エラーが出たら自力で修正
- 1ラウンド1タスクに集中
実装を開始してください。
" 2>&1 | tee -a "$CLAUDE_LOG"
# Step 2: Codex レビュー
echo -e "${CYAN}[Step 2] Codex レビュー中...${NC}"
codex review --commit HEAD 2>&1 | tee "$REVIEW_FILE" | tee -a "$CODEX_LOG"
# Step 3: レビュー結果を確認し、修正が必要なら対応
if ! grep -qi "LGTM" "$REVIEW_FILE"; then
echo -e "${CYAN}[Step 3] Claude Code 修正中...${NC}"
claude --dangerously-skip-permissions -p "
Codexから以下のレビューコメントを受けました。
指摘に従って修正し、再度コミットしてpushしてください。
$(cat "$REVIEW_FILE")
" 2>&1 | tee -a "$CLAUDE_LOG"
else
echo -e "${GREEN}[Step 3] レビューOK - 修正不要${NC}"
fi
# Step 4: Code Simplifier でコード整理
echo -e "${CYAN}[Step 4] Code Simplifier 実行中...${NC}"
claude --dangerously-skip-permissions -p "
/plugin run code-simplifier
最近変更したコードを整理・簡素化してください。
機能は変えずに、可読性と保守性を向上させてください。
変更があればコミットしてpushしてください。
" 2>&1 | tee -a "$CLAUDE_LOG"
echo "[$(date '+%Y-%m-%d %H:%M:%S')] ラウンド $round 完了" >> "$CLAUDE_LOG"
echo ""
# 全タスク完了チェック
if ! grep -q "\- \[ \]" "$PROJECT_DIR/docs/todo.md" 2>/dev/null; then
echo -e "${GREEN}全タスク完了!${NC}"
break
fi
# インターバル
sleep 3
done
echo -e "${GREEN}=== ループ終了 ===${NC}"
コピペして使う場合には
claude plugin install code-simplifier
してから使う。なくても動くけど。
動作の様子
tmuxで左右分割して動かしている様子。

左ペインでClaudeが実装してコミット、右ペインでCodexがレビューしてフィードバックを返している。

Codexが「LGTM」を出すとClaudeは修正せず次のタスクに進む。指摘があれば修正してから次へ。
結果
投入した仕様
そば食いゲーム仕様書を投入した。2ゲージ制、座席システム、敵システムなどを含む仕様。
生成されたコード
- 1134行のTypeScript
- Viteプロジェクトとして動作
- ブラウザで遊べる状態
完了したタスク
docs/progress.mdに記録された履歴の一部:
### 基本HTML構造
- [x] ゲーム画面レイアウト実装
- [x] 2ゲージUI(満腹・そば満足)
- [x] タイマー表示
- [x] NEXT表示エリア
- [x] 座席指定表示エリア
### プレイヤー移動
- [x] プレイヤー状態インターフェース定義
- [x] キーボード入力処理(矢印キー・WASD)
- [x] 8方向移動対応
### 食べ物システム
- [x] 食べ物パラメータ設定(そば並/大盛/特盛、うどん、ラーメン、ナポリタン)
- [x] ステージ別出現確率
- [x] カウンターへの配置・取得
### 座席システム
- [x] ステージ別テーブル選択ルール
- [x] テーブル指定システム
- [x] 喫食システム
### 敵システム
- [x] ステージ別敵パラメータ
- [x] プレイヤーと敵の衝突判定
- [x] 運搬中に衝突で食べ物落下
うまくいった点
ファイルベースの履歴管理
CLAUDE.mdで「進捗は docs/progress.md に記録しろ」と指示しておいたのが効いた。Claudeのコンテキストがコンパクトされても、ファイルを読み直せば過去の経緯を把握できる。
作業単位の制御
プロンプトで「1ラウンド1タスクに集中」と指示しているが、Claudeがフェーズと作業単位を1対1にしてる時もあれば、複数タスクをまとめてやる時もある。どういう気分かはわからない。
Codexのバグ検出
Codexが「食べ物落下時に座席が解放されていない」というバグを検出して、Claudeが修正した。これはprogress.mdにも記録されていた:
### バグ修正
- [x] 食べ物落下時の座席解放漏れ修正
- dropCarriedFood()でassignedTableIdに対応する座席のstateを'available'にリセット
- Codexレビュー指摘(P1)への対応
Tips
仕様書の足りない部分は適当に実装される。これを回避するには仕様書をかなり作りこむ必要がある。別窓でAskUserQuestionToolを使って徹底的に質問させて、何も疑問がないようにさせるといい。
このスクリプトだと上限10回なので、回数を変えるときは適宜自己責任で。
各コミット後に都度pushするようにした。理由:
- 進捗の可視化: 離れていても何をしているか把握できる
- 外部からの介入手段:
--dangerously-skip-permissionsでフル権限を渡しているため、エージェントが予期しない動作(外部接続など)をする可能性がある。そのとき外出先からCLAUDE.mdやTODO.mdを修正してGitHubにpushしておけば、エージェントがpushしようとしたときにコンフリクトする。コンフリクト解消のためにpullすると、修正されたCLAUDE.mdを読み込む。1ラウンドごとに新しいClaudeが起動するので、次のラウンドでは必ず最新の指示が反映される
実際、SFTPで外部接続しようとしていたのをこの方法で止めた。
まとめ
Claude Code + Codexの自動ループは動く。仕様書とタスクリストをしっかり用意しておけば自走してくれる。放置しようとしたら1時間弱で終わった。