Laravel 5.8 の assertDatabaseHas を使用したさい、日本語（unicode）がエスケープされる問題の修正方法

問題
---


```php:assertDatabaseHasでテストが失敗したとき
$this->call('PATCH', '/api/users/1', ['name' => 'ほげほほげ']);
$this->assertDatabaseHas('users', ['name' => 'ふがふが']);
```

```bash:データベース内のマルチバイトが正しく表示されない
# There was 1 failure:
# 
# 1) Tests\Feature\UsersControllerTest::testUsersUpdate
# Failed asserting that a row in the table [users] matches the attributes {
#     "title": "\u3075\u304c\u3075\u304c"
# }.
# 
# Found: [
#     {
#         "id": 1,
#         "title": "\u307b\u3052\u307b\u307b\u3052",
#         "created_at": "2019-09-29 09:33:59",
#         "updated_at": "2019-09-29 09:33:59"
#     }
# ].
```

結論
---
文字化けの原因は [**class InteractsWithDatabase**](https://github.com/laravel/framework/blob/5.8/src/Illuminate/Foundation/Testing/Concerns/InteractsWithDatabase.php#L21) 内で使用している `json_encode` の第２引数が `JSON_PRETTY_PRINT` のみになっているため。

これは、`./tests/TestCase.php` で `assertDatabaseHas` でオーバーライドして引数を修正できる

```php:./tests/TestCase.php
<?php

namespace Tests;

use Illuminate\Foundation\Testing\TestCase as BaseTestCase;

abstract class TestCase extends BaseTestCase
{
    use CreatesApplication;

    /**
     * @see github.com/laravel/framework/blob/5.8/src/Illuminate/Foundation/Testing/Concerns/InteractsWithDatabase.php#L21
     */
    protected function assertDatabaseHas($table, array $data, $connection = null)
    {
        $this->assertThat(
            $table,
            new HasInDatabaseMb($this->getConnection($connection), $data)
        );

        return $this;
    }
}
```

[`class BaseTestCase > trait InteractsWithDatabase > class HasInDatabase`][1] のような依存で、実際の出力整形は`HasInDatabase`クラスのメソッドが行っているため、json_encodeを使用しているメソッドを上書きして新しいクラス `./tests/HasInDatabaseMb.php` とする。

```php:./tests/HasInDatabaseMb.php
<?php

namespace Tests;

use Illuminate\Foundation\Testing\Constraints\HasInDatabase;

class HasInDatabaseMb extends HasInDatabase
{
    /**
     * @see github.com/laravel/framework/blob/5.8/src/Illuminate/Foundation/Testing/Constraints/HasInDatabase.php#L66
     */
    protected function getAdditionalInfo($table)
    {
        $results = $this->database->table($table)->get();

        if ($results->isEmpty()) {
            return 'The table is empty';
        }

        $description = 'Found: '.json_encode($results->take($this->show), JSON_PRETTY_PRINT | JSON_UNESCAPED_SLASHES | JSON_UNESCAPED_UNICODE);

        if ($results->count() > $this->show) {
            $description .= sprintf(' and %s others', $results->count() - $this->show);
        }

        return $description;
    }

    /**
     * @see github.com/laravel/framework/blob/5.8/src/Illuminate/Foundation/Testing/Constraints/HasInDatabase.php#L84
     */
    public function toString($options = 0): string
    {
        return json_encode($this->data, JSON_PRETTY_PRINT | JSON_UNESCAPED_SLASHES | JSON_UNESCAPED_UNICODE);
    }
}
```
上記はオリジナルのソースコードの `json_encode` の第２引数を

- `JSON_PRETTY_PRINT`

から↓

- `JSON_PRETTY_PRINT | JSON_UNESCAPED_SLASHES | JSON_UNESCAPED_UNICODE`


に変更を行い、それ以外は変更していない。
以上のようにして `assertDatabaseHas` メソッドをオーバーライドすれば、テスト失敗時に日本語が表示されるようになる。

```bash
# Time: 1.69 seconds, Memory: 24.00 MB
# 
# There was 1 failure:
# 
# 1) Tests\Feature\UsersControllerTest::testUsersUpdate
# Failed asserting that a row in the table [users] matches the attributes {
#     "title": "ふがふが"
# }.
# 
# Found: [
#     {
#         "id": 1,
#         "title": "ほげほほげ",
#         "created_at": "2019-09-29 09:50:00",
#         "updated_at": "2019-09-29 09:50:00"
#     }
# ].
```

[1]: https://github.com/laravel/framework/blob/5.8/src/Illuminate/Foundation/Testing/Constraints/HasInDatabase.php#L66-L84