今までWebAPIのテストはFrisby + jasmine-nodeで書いていましたが、PHPでも書いてみます。
なお、WebAPIにリクエストするライブラリとしてGuzzleを利用してみたいと思います。Guzzleは直感的でかつ、非同期や様々なオプションに対応していてすばらしいです。
WebUIのテストについてはこちら。
##前提
- composerがインストールされている
- Mac(El capitan)
ホームディレクトリ内にtestというフォルダを作ってその中で作業するものとします。
##準備
###ライブラリのダウンロード
#ディレクトリ作成
cd ~/
mkdir test
cd test
#phpunitとguzzleのインストール
composer require phpunit/phpunit
composer require guzzlehttp/guzzle
guzzeleはVer5以上からguzzle/guzzleからguzzlehttp/guzzleになったそうです。
##テストを書く(テスト対象)
テスト対象のAPIとして下記のようなものを用意してみました。
これを、http://localhost/test/api.phpとして参照できるようにしています。
ポイントとしては、
- POST/GETに対応
- Dataは配列を戻します(DBレスポンスのイメージ)
となっていて、これをどう取得、テストできるか試してみます。
<?php
$name = "xxx";
if(isset($_POST['name'])) $name = $_POST['name'];
if(isset($_GET['name'])) $name = $_GET['name'];
$data = [
['name'=>'hoge','age'=>'30'],
['name'=>'foo','age'=>'20']
];
$response = [];
$response['status'] = "OK";
$response['message'] = "Hello ".$name.".";
$response['data'] = $data;
header('Content-type: application/json');
echo json_encode($response);
こんなJSONが戻ります。
{
"status":"OK",
"message":"Hello xxx.",
"data":
[
{"name":"hoge","age":"30"},
{"name":"foo","age":"20"}
]
}
##テストを書く(テストコード)
Guzzleを利用すると、非常に直感的でわかりやすいコードで書けます。
GETもPOSTもほぼ同じコードでかけることが分かります。
guzzle5まではPOSTのパラメータ名はbodyだったようですが、6からはform_paramsとなっているようです。
<?php
class sampleTest extends PHPUnit_Framework_TestCase
{
public function testWebAPI_GET()
{
//
$client = new GuzzleHttp\Client();
//get
$res = $client->get('http://localhost/test/api.php',[
'query'=>[
'name'=>'POO',
'email'=>'poo@poo.com',
],
]);
//取得 第2引数にtrueつけると連想配列
$obj = json_decode($res->getBody());
//取得
$status = $obj->status;
$message = $obj->message;
$rows = $obj->data;
//loop(参考)
foreach ($rows as $row) {
//echo $row->name;
}
//評価
$this->assertEquals("OK",$status);
$this->assertEquals("Hello POO.",$message);
$this->assertRegExp('/^Hello.+\.$/',$message);
$this->assertCount(2,$rows);
}
public function testWebAPI_POST()
{
//
$client = new GuzzleHttp\Client();
//post
$res = $client->post('http://localhost/test/api.php',[
'form_params'=>[
'name'=>'POO',
'email'=>'poo@poo.com',
],
]);
//取得 第2引数にtrueつけると連想配列
$obj = json_decode($res->getBody());
//取得
$status = $obj->status;
$message = $obj->message;
$rows = $obj->data;
//loop(参考)
foreach ($rows as $row) {
//echo $row->name;
}
//評価
$this->assertEquals("OK",$status);
$this->assertEquals("Hello POO.",$message);
$this->assertRegExp('/^Hello.+\.$/',$message);
$this->assertCount(2,$rows);
}
}
##実行
cd ~/test
./vendor/bin/phpunit --colors tests/
OK (2 tests, 6 assertions)
グリーンで完了しました。
###最低限のassertメソッド
- assertEquals($expect,$var) $expectと$varが等しいか?
- assertRegExp($ptn, $var) 正規表現にマッチするかどうか?
- assertNull($var)
- assertTrue($var)
- assertFalse($var)
- assertCount($num,$array)
- assertEmpty($array)
###LaravelのQueryBuilderやEloquentを使う
UIやAPIのテストを実行した結果、DBに正常に値が書き込まれているかをチェックしたくなります。もちろん普通にPDOでコードを書いてもいいですが、Laravelに慣れてる場合、QueryBuilderやEloquentが使いたくなります。その場合は、こちらを参考にしてください。