Claude Codeにテストを書かせる方法|不具合を本当に検出できるかまで確かめる
Claude Codeにテストを書かせるときに、そのテストが本当に不具合を検出できるかまで確かめる方法を解説します。修正前に失敗を確かめる手順、テストが失敗したときの判断、全件PASSでも確かめが必要なことを実例で紹介します。
目次
この記事でわかること
- Claude Codeにテストを書かせる前に決めておくこと
- 再発防止のテストが「本当に効く」ことを確かめる手順
- テストが失敗したときに、実装とテストのどちらを直すかの判断
- 全件のテストが通っても、別に確かめが必要なこと
テストの実行方法をプロジェクトのルールとして残す場所はCLAUDE.mdの書き方、作業の区切りで全件テストを実行する流れはClaude Codeで長期プロジェクトを進める方法で扱っています。この記事は、テストそのものの頼み方と確かめ方が中心です。
「テストがある」と「テストが効く」は違う
Claude Codeは、作業が終わったように見えたところで止まります。公式ドキュメントのベストプラクティスでは、そのためにテストやビルドのような、Claude Codeが自分で実行できる確認の手段を渡すよう勧めています。
テストは強力な確認の手段です。ただし、テストが存在して全部通ったことは、守りたい不具合を見つけられることの証明にはなりません。
| テストがある | テストが効く | |
|---|---|---|
| 確かめたこと | 書いた条件でコードが動く | 守りたい不具合が起きたら、テストが失敗する |
| 確かめ方 | 今のコードでPASSを見る | 壊れた状態でFAIL、直した状態でPASSを見る |
テストが見ている場所と、不具合が起きる場所がずれていれば、テストは何も検出しないまま通り続けます。このサイトでも、実際にそれが起きました(後の節で紹介します)。
Claude Codeにテストを書かせる前に確認すること
何を守りたいかを決める
「テストを書いて」だけでは、何を確かめるテストにするかをClaude Codeが推測することになります。公式ドキュメントも、テストを頼むときは確かめたい動作を具体的に伝えるよう勧めています。対象のファイル、どんな場面か、テストの書き方の好みまで指定する例が紹介されています。
守りたいものは、使う人から見た結果で書くと決めやすくなります。「関数が正しい値を返す」より、「公開ページの本文のリンクを開くと記事が表示される」のような書き方です。
既存のテストを先に読ませる
Claude Codeは、既存のテストファイルを見て、書き方・フレームワーク・確かめ方の形をそろえます。新しいテストを書かせる前に、既存のテストが何を確かめていて、何を確かめていないかを報告させます。
ここで「似たテストがすでにあるのに、不具合は起きた」と分かることがあります。その場合は、テストが見ている場所と、不具合が起きた場所がずれています。新しいテストは、不具合が起きた場所を直接見るように書きます。
再発防止テストを作る流れ
不具合を直すときは、修正の前にテストを書きます。公式ドキュメントでも、症状を伝え、問題を再現する失敗するテストを書いてから直すよう頼む例が紹介されています。
| 順番 | やること | 確かめること |
|---|---|---|
| 1 | 守りたい動作を決める | 何が起きたら不具合とみなすか |
| 2 | 既存のテストを読む | どこまで確かめているか |
| 3 | 不具合の再現条件を整理する | いつ・どこで起きるか |
| 4 | 再発防止のテストを書く | 不具合が起きる場所を見ているか |
| 5 | 修正前のコードで実行する | 新しいテストがFAILする |
| 6 | 修正する | 原因を直しているか |
| 7 | もう一度実行する | 同じテストがPASSする |
| 8 | 全件のテストを実行する | ほかのテストが壊れていない |
修正前にFAILを確認する
いちばん大事なのが5の手順です。修正した後にテストを書いて通っただけでは、そのテストが今回の不具合を検出できるかは分かりません。不具合を見ていないテストでも、PASSは同じように表示されるからです。
修正前のコードで新しいテストが失敗すれば、そのテストは今回の不具合を捕まえられると言えます。失敗しなかったときは、テストが不具合の起きる場所を見ていないことになります。修正に進む前に、テストを見直します。
失敗した理由も確かめます。書き間違いや読み込みのエラーで失敗しているだけなら、不具合を捕まえたことにはなりません。
修正後にPASSを確認し、全件のテストを実行する
修正したら、同じテストがPASSすることを確かめます。そのあと全件のテストを実行し、今回の修正で別の場所が壊れていないかを見ます。これが回帰テスト(前に動いていたものが壊れていないかの確認)です。
Claude Codeには「通りました」とだけ報告させず、実行したコマンドと結果を見せてもらいます。公式ドキュメントも、成功を主張させるのではなく、テストの出力のような証拠を示させるよう勧めています。
わざと壊して、テストが効くか確かめる
新しい機能のテストのように「修正前」がない場合でも、同じ考え方が使えます。テストが守っているものを一時的に壊し、テストが失敗することを確かめてから元に戻します。
このサイトでは、記事ごとのアイキャッチ画像がそろっているかを確かめるテストを作ったとき、画像を一時退避してテストが失敗することを確かめ、元に戻しました。どの記事からもリンクされていない記事がないかを確かめるテストでは、修正前のソースへ戻して実行し、5本の記事を検出して失敗することを確かめています。
この記事で紹介しているのは、手作業で壊れた状態を作って実行する方法です。特別な道具は要らず、テストを書いたその場で確かめられます。
このサイトで実際にあった例:プレビューでは気づけなかった404
このサイトでは、記事の本文中のリンクに開けないものがある、という報告から調査を始めたことがあります。公開中の16記事を巡回して140件のURLを確かめると、13件が同じ形で404になっていました。
このサイトはドメインの直下ではなく、1段下のパスで公開しています。本文のリンクはそのパスを含まない形で書かれていて、公開ページではそのまま出力されたため、存在しないURLになっていました。
確認用のプレビュー画面には、リンクを書き換える処理が別にありました。その副作用でプレビューでは正しいURLになり、公開ページだけで壊れる状態だったため、プレビューの確認では気づけませんでした。
既存のテストも、本文に書かれたリンク先の記事が存在するかは確かめていました。しかし、公開ページに出力されるリンクが正しいかは確かめていませんでした。
対応は次の順で進めました。
- 公開ページとして配信されるHTMLを読み、リンクが正しい形かを確かめるテストを追加した
- 修正前のコードで、そのテストが失敗することを確かめた
- 公開ページのリンクを直した
- サーバーの実際のデータベースで全件のテストを実行し、319件が成功した
- 全記事を巡回し直し、404が0件になったことを確かめた
テストが失敗したときの判断
テストが失敗したときに、Claude Codeへ「テストを通して」とだけ頼むのは危険です。テストを通すいちばん簡単な方法は、期待値を今の動作に合わせて書き換えることだからです。それでは、不具合を見つけたテストを黙らせることになります。
失敗したら、まず原因がどこにあるかを調べます。
| 原因 | 直すもの | 判断の材料 |
|---|---|---|
| 実装の誤り | 実装 | 守りたい動作と実際の動作が違う |
| 意図した仕様の変更 | テストの期待値 | 変わったことが意図どおりだと説明できる |
| テストの書き方の誤り | テスト | 確かめたいことを確かめていない |
| 環境の違い | 実行の条件 | データベースなど必要なものがない |
公式ドキュメントも、ビルドが失敗したときの頼み方の例で、エラーを抑え込まずに根本の原因へ対処するよう求めています。
このサイトでは、期待値を書き換えたこともあります。記事に申し込みへの案内(CTA)がまだないことを確かめていたテストが、案内を設定した後に失敗したときです。案内の設定は意図した変更だったため、テストを「案内が正しく設定されている」ことを確かめる内容に書き換えました。
期待値を変えてよいのは、変わったことが意図どおりだと説明できるときだけです。Claude Codeには原因の調査と直す対象の案までを頼み、どちらを直すかは確認してから決めます。
全件PASSでも確かめが必要なもの
全件のテストが通ったことは、テストが確かめている範囲で問題がない、という意味です。次のようなものは、テストが見ていなければ、全件PASSでも見つかりません。
- テストが通っていない経路(プレビューと公開ページのように、同じ内容でも出力の経路が違う場合)
- 画面での見え方(ブラウザでの表示、スマートフォンの幅)
- 外部のサービス、本番の設定やデータ
- 実行されずにスキップされたテスト
最後の点は見落としやすいところです。pytestの公式ドキュメントでは、データベースのような外部の資源が使えないときにテストをスキップする例が説明されています。スキップされたテストは、成功でも失敗でもありません。
このサイトでも、先ほどのリンクのテストはデータベースが必要なため、データベースのない作業用のパソコンではスキップされます。手元で全件が通っても、そのテストはサーバーの実際のデータベースで実行して確かめています。
カバレッジを測る道具は、どのコードがテストで実行されたかを示してくれます。ただし、実行されたことと、結果が正しいと確かめたことは別です。公式ドキュメントのベストプラクティスも、確かめられないものは出さないよう勧めています。
Claude Codeへの依頼例
不具合を直すときの依頼例です。修正の前に止まり、失敗の結果を確かめられるようにしています。
次の不具合の再発防止テストを書いてください。
まだ実装は修正しないでください。
症状:(どこで、何をすると、何が起きるか)
先に既存のテストを読み、この不具合をどこまで
確かめているかを報告してください。
次に、症状を再現するテストを追加し、
修正前のコードで実行してください。
テストが失敗した理由と、実行したコマンドの出力を
報告して、私の確認を待ってください。
テストが失敗したときの依頼例です。
テストが失敗しました。
まだテストも実装も変更しないでください。
失敗したテストと出力を確かめ、原因が実装・期待値・
テストの書き方・環境のどれにあるかを調べてください。
根拠と、直す対象の案を報告して、私の確認を待ってください。
期待値を書き換えて通すことは、私が確認するまで行わないでください。
まとめ
- テストが「ある」ことと、守りたい不具合を検出できる「効く」ことは違う
- 書かせる前に、守りたい動作と既存のテストを確かめる
- 再発防止のテストは、修正前のFAILと修正後のPASSを見てから、全件のテストを実行する
- テストが失敗したら、実装とテストのどちらを直すかを調べてから決める
- 全件PASSでも、テストが通っていない経路・画面・外部のもの・スキップされたテストは別に確かめる
AIの出力の確かめ方全般はAIの出力をどう確認するか、はじめてClaude Codeを使う場合はClaude Codeの始め方と使い方から読むと流れがつかめます。
よくある質問
Claude Codeに「テストを書いて」とだけ頼んでもよいですか?
動くテストは書いてくれますが、何を確かめるかをClaude Codeが推測することになります。守りたい動作、対象のファイル、どんな場面かを伝えると、確かめたいことに沿ったテストになります。
修正の前にテストを書くのと、修正した後に書くのでは何が違いますか?
修正の前に書けば、不具合のある状態でそのテストが失敗することを確かめられます。修正した後に書いて通っただけでは、そのテストが今回の不具合を検出できるかは分かりません。
テストが失敗したら、Claude Codeに直してもらってよいですか?
直す前に、原因を調べてもらいます。実装の誤り・意図した仕様の変更・テストの書き方の誤り・環境の違いのどれかで、直すものが変わります。期待値の書き換えは、その変更が意図どおりだと確かめてから行います。
全部のテストが通れば、もう確認しなくてよいですか?
テストが確かめている範囲では安心できますが、テストが実行していない経路や画面での見え方、スキップされたテストは確かめられていません。結果の件数では、成功の数だけでなくスキップの数も見ておきます。
テストの実行を毎回必ず行わせる方法はありますか?
依頼のたびに実行を頼む方法のほかに、公式ドキュメントでは、Stop hookで確認のスクリプトを実行し、通るまで作業を終わらせない方法が紹介されています。設定する前に、どのテストをいつ実行するかを決めておきます。