小規模店舗向けのLaravel雛形を、Claude Codeにほぼ書いてもらいました。その中で、指示の出し方で結果が大きく変わったのが、予約モジュールです。粗すぎても細かすぎても失敗して、うまくいったのは「やらないことと判断基準を渡す」指示でした。
粗すぎる指示: 「予約機能を作って」
この粒度で頼むと、返ってくるのは作れるものを全部盛った設計案になりがちです。たとえば次のようなものです。
- 時間枠のカレンダー
- スタッフの指名
- 外部カレンダーとの同期
けれど、小規模な整体院や美容室が欲しいのは、「希望日時を送ってもらって、店側が手動で確定する」だけ、というケースがほとんどです。AIは「何を作らないか」を知りません。それを決めるのは人間の仕事です。
細かすぎる指示: テーブル定義から書く
reservationsテーブルにname(string)、phone(string, nullable)、reserved_at(datetime)……を追加して、モデルにfillableを設定して、コントローラのstoreで……
これは動きます。ただ、設計を人間が全部書いているので、Claude Codeを使う意味がほとんどありません。しかも、指示した人が見落としている要件(たとえば「同じ日時への重複予約の防止」)は、そのまま抜け落ちます。
うまくいった指示
実際に予約モジュールを作らせたときの指示は、こういう形でした。
予約モジュールを作ってください。
- 対象は小規模店舗(整体院・美容室)。リクエスト制で、店側が管理画面で「確定」か「キャンセル」を選ぶ運用
- 営業時間・空き枠カレンダーは作らない(将来必要になったら追加する)
- 同じ日時への重複予約は防ぐ。ただしキャンセル済みは対象外
- 新規予約が来たらスタッフにメール通知。ContactFormモジュールと同じ仕組みで
- 確定したときはお客様にも確定メールを送る。文面は店側が管理画面で編集できるようにしたい
- 公開ページは認証不要、管理画面は
authミドルウェア。Blogモジュールの構成に揃える
入れているのは、次の4種類です。
| 入れたもの | この指示での例 |
|---|---|
| 対象ユーザー | 小規模店舗(整体院・美容室) |
| やらないこと | 営業時間・空き枠カレンダー |
| 揃える既存コード | ContactFormの通知、Blogモジュールの構成 |
| 判断基準 | リクエスト制、キャンセル済みは重複の対象外 |
返ってきた「要点整理」
実装に入る前に、Claude Codeが「これから何を作るか」を箇条書きで返します。その中に、私が指示していない判断が2つありました。
- 確定メールの文面編集は、Reservationモジュール内ではなくアプリ本体の
message_templatesとして作る。理由: 今後ContactFormなど他モジュールの顧客向けメールでも同じ仕組みが要るため- メールはプレーンテキストにする。理由: 店側が文面を自由に書き換える前提なので、HTMLの崩れを気にせず編集できる方が運用に耐える
どちらも、理由が妥当だったので、そのまま通しました。判断基準を渡すと、Claude Codeは、指示していない部分でも同じ基準で判断してくれる。これが、道具ではなく「社員として使う」感覚の正体だと思っています。
理由つきの判断は、READMEに残す
上の4と5のような判断は、翌週になると私自身が忘れます。そこで、要点整理で出た「理由つきの判断」は、READMEに書かせます。
- 全てプレーンテキストメール(HTML/Markdownメールは使わない方針。
理由: 導入後に運用者(店舗側)が文面変更・キャンペーン文言追加を
自由に行いたいという要望のため、HTMLの見た目崩れを気にせず
編集できるプレーンテキストを採用)
後日、別のセッションで「予約完了メールをおしゃれなHTMLにして」と頼むと、Claude Codeは「READMEにプレーンテキストの方針とその理由があります。変更しますか」と確認してきます。
指示を出す前のチェック
- 対象ユーザーを書いたか
- 作らないものを書いたか
- 既存のどのコードに揃えるかを書いたか
- 迷いそうな箇所の判断基準を書いたか(重複予約はどう扱うか、など)
- 理由つきの判断が返ってきたら、READMEに残す前提にしたか
細かい仕様を書く時間は、「やらないこと」を1行足す時間に変えたほうが、ずっと効きました。
この記事はZennにも投稿しています。