Flaskでカバレッジ測定をする方法解説
2024年7月11日
こんにちは!
今回の記事では、Flaskでカバレッジ測定をする方法について解説します。
Webアプリケーションの品質を保ち、コードの信頼性を高めるためには、単体テストが重要です。
さらに、テストのカバレッジを測定することで、テストがコードのどの部分を網羅しているかを確認し、テストの不足を発見できます。
今回の記事では、Flaskアプリケーションにおけるテストカバレッジの測定方法について詳しく解説します。
カバレッジとは?
まずは、カバレッジについて説明します。
カバレッジ(Coverage)とは、テストがコードベースをどの程度網羅しているかを示す指標です。カバレッジを測定することで、未テストのコード部分を発見し、テストの品質を向上させることができます。
カバレッジ測定には主に以下の指標が使われます。
指標 | 説明 |
---|---|
ステートメントカバレッジ | 実行されたコード行の割合 |
ブランチカバレッジ | 実行された条件分岐の割合 |
関数カバレッジ | 実行された関数の割合 |
行カバレッジ | 実行されたコード行の詳細な割合 |
他にもさまざまな指標があり、網羅的にテストを行うためにカバレッジを使います。
カバレッジ測定を行う
それでは、Flaskでカバレッジ測定を行う方法について解説します。
まずは、Flaskのアプリケーションと、テストコードの準備をおこないます。
テストについては、こちらの記事で詳しく解説しています。また、今回のFlaskアプリのコードもこちらの記事から流用しています。
【関連記事】Flaskで単体テストを実装する方法を解説
Flaskアプリケーションの準備
まず、必要なパッケージをインストールします。
pip install Flask Flask-SQLAlchemy pytest Flask-Testing
次に、アプリケーションの実装を行います。
from flask import Flask, jsonify, request
from flask_sqlalchemy import SQLAlchemy
app = Flask(__name__)
app.config['SQLALCHEMY_DATABASE_URI'] = 'sqlite:///example.db'
db = SQLAlchemy(app)
class User(db.Model):
id = db.Column(db.Integer, primary_key=True)
username = db.Column(db.String(80), unique=True, nullable=False)
@app.route('/user', methods=['POST'])
def add_user():
username = request.json['username']
user = User(username=username)
db.session.add(user)
db.session.commit()
return jsonify({'id': user.id, 'username': user.username}), 201
@app.route('/hello', methods=['GET'])
def hello():
return jsonify({'message': 'Hello, World!'})
if __name__ == '__main__':
app.run(debug=True)
このFlaskアプリケーションは、SQLiteデータベースを使用してユーザー情報を管理します。
以下の2つのエンドポイントを提供します
- /user(POSTメソッド):リクエストのJSONペイロードから
username
を取得し、新しいユーザーをデータベースに追加します。成功すると、新規ユーザーのid
とusername
を含むJSONレスポンスを返し、HTTPステータスコード201を返します。 - /hello(GETメソッド):固定メッセージ”Hello, World!”を含むJSONレスポンスを返します。
テストコードの準備
次にテストコードを準備します。tests/test_app.pyファイルに以下のように記述します。
import unittest
from flask_testing import TestCase
from app import app, db, User
class UserTest(TestCase):
def create_app(self):
app.config['TESTING'] = True
app.config['SQLALCHEMY_DATABASE_URI'] = 'sqlite:///:memory:'
app.config['SQLALCHEMY_TRACK_MODIFICATIONS'] = False
return app
def setUp(self):
db.create_all()
def tearDown(self):
db.session.remove()
db.drop_all()
def test_add_user(self):
response = self.client.post('/user', json={'username': 'testuser'})
self.assertEqual(response.status_code, 201)
self.assertIn('id', response.json)
self.assertEqual(response.json['username'], 'testuser')
def test_hello(self):
response = self.client.get('/hello')
self.assertEqual(response.status_code, 200)
self.assertEqual(response.json, {'message': 'Hello, World!'})
if __name__ == '__main__':
unittest.main()
このコードは、Flaskアプリケーションのユーザー追加機能と固定メッセージ出力機能をテストするためのユニットテストを定義しています。
/userエンドポイントと/helloエンドポイントの正しい動作を確認します。
テストを実行して正しくどうさするか確認してみましょう。
python -m unittest discover -s tests
カバレッジの測定
続いてカバレッジの測定をしてみましょう。
カバレッジの測定には、coverageというパッケージを使います。以下のコマンドを実行してインストールしましょう。
pip install coverage
テストカバレッジを測定するために、まずcoverage
ツールを使ってテストを実行します。以下のコマンドを使用します。
coverage run -m unittest discover -s tests
このコマンドは、testsディレクトリ内のすべてのテストを実行し、そのカバレッジを測定します。
テスト実行後、カバレッジレポートを生成します。
coverage report -m
コマンドを実行すると、以下のように表示されます。どのファイルのどの行が実行されたかを含む詳細なレポートが表示されます。
カバレッジレポートの見方
カバレッジレポートは、以下のような項目が表示されます。
これらには、どのような意味があるのでしょうか?
Stmts (Statements)
Stmtsは、コードの中で実行可能なステートメント(命令文)の総数を示します。
つまり、テスト対象のファイル内に存在する実行可能な行の数です。
Miss (Missed)
Missは、テストによって実行されなかったステートメントの数を示します。
これは、テストがそのコード行を通らなかったことを意味します。
Cover (Coverage)
Coverは、テストによって実行されたステートメントの割合を示します。
具体的には、全体のステートメント数に対して、実行されたステートメントの割合です。
例えば、Cover が 90% と表示される場合、そのファイル内の90%のステートメントがテストによって実行されたことを意味します。
Missing
Missingは、実行されなかったステートメントの行番号をリストします。このリストを見ることで、どの部分がテストでカバーされていないかを具体的に知ることができます。
HTMLレポートの生成
カバレッジレポートをより見やすくするために、HTML形式で出力することもできます。
以下のコマンドを使用します。
coverage html
htmlcovディレクトリにHTMLレポートを生成します。
ブラウザでhtmlcov/index.html
を開くと、視覚的にカバレッジを確認できます。
まとめ
今回の記事では、Flaskでカバレッジ測定をする方法について解説しました。
カバレッジは、テストを網羅的に実施できているかを測定するためのものです。単体テストの導入をおこなったら、カバレッジの測定もあわせて行いましょう。
今回の記事が、あなたのWeb開発の助けになれば幸いです。
ここまでお読みいただきありがとうございました。
Pythonの基礎から応用まで学べる
Python WebAcademy
Python WebAcademyでは、Pythonの基礎からアーキテクチャなどの応用的な内容まで幅広く学べます。また、ブラウザ上で直接Pythonコードを試すことができ、実践的なスキルを身につけることが可能です。
Pythonの学習を始めるインフラの学習はInfraAcademy
おすすめの記事