2017-02-21 41 views
0

В настоящее время у меня возникают проблемы при тестировании функции в Laravel. Эта функция является простой функцией сохранения пользователя.Laravel Единичное тестирование Яркая вставка

Текущая структура включает в себя User

class User extends Authenticatable 

Тогда у меня есть UserController

class UserController extends Controller 
{ 
protected $user; 

public function __construct(User $user) 
{ 
    $this->user = $user; 
    $this->middleware('admins'); 
} 

спасбросков функция определена на классе UserController, этот класс только присваивает переменные запроса и использует Eloquent сохранить функция сохранения в базу данных.

Функция подписи является следующее:

public function storeUser($request) 
{ 

    $this->user->name  = $request->name; 
    $this->user->email  = $request->email; 
    $this->user->country_id = $request->country_id; 

    return $this->user->save(); 
} 

Объект NewAccountRequest простирается от запроса и имеет правила проверки для запроса.

class NewAccountRequest extends Request 
{ 
public function authorize() 
{ 
    return true; 
} 

public function rules() 
{ 
    return [ 
     'name' => 'required|max:255', 
     'email' => 'required|email|max:255|unique:user', 
     'password' => 'required|min:6|max:60', 
    ]; 
} 

} 

Моя проблема заключается в том, как я могу протестировать эту функцию storeUser.

У меня есть текущий тест:

public function testSaveUserWithEmptyRequest() 
{ 

    $user = $this->createMock(User::class); 
    $controller = new UserController($user); 

    $request = $this->createMock(NewAccountRequest::class); 
    $store = $controller->storeUser($request); 

    $this->assertFalse($store); 
} 

Я насмешливо как пользователь и NewAccountRequest, проблема в том, что утверждение должно быть ложным, от Eloquent сохранить. Вместо этого я получаю Null. Любая идея о том, как я могу правильно проверить функцию?

+0

Что внутри 'saveUser' функции, вы пропали без вести оператор возврата ? –

+0

@ShadyAtef Обновлен вопрос с помощью кода StoreUser и исправления имени вызова. –

+0

У меня это есть, вы издеваетесь над 'User :: class' .. В PHPUnit' createMock' заменяет все функции объекта с фиктивными, которые ничего не делают и возвращают null. На самом деле, чтобы проверить работу базы данных в laravel, вам нужно использовать одну из двух характеристик, предоставляемых «DatabaseMigrations» или «DatabaseTransactions» –

ответ

0
<?php 
namespace Tests\Unit; 

use Tests\TestCase; 
use Illuminate\Foundation\Testing\DatabaseMigrations; 
use Illuminate\Foundation\Testing\DatabaseTransactions; 

class ExampleTest extends TestCase 
{ 
    use DatabaseTransactions; // Laravel will automatically roll back changes that happens in every test 


    public function testSaveUserWithEmptyRequest() 
    { 

     $user = new User(); 
     $controller = new UserController($user); 

     $request = $this->createMock(NewAccountRequest::class); 
     $store = $controller->storeUser($request); 

     $this->assertFalse($store); 
    } 

} 

Это именно то, что вы пытаетесь сделать, но, к сожалению, это не из-за исключение базы данных ... Дразнящего запрос или даже вручную крафт не будет делать проверку входных данных .. и в вашем пример password поле не обнуляемым и заставит PDOException: SQLSTATE[HY000]: General error: 1364 Field 'password' doesn't have a default value


рекомендуемый способ тестирования функции в зависимости от запроса, чтобы использовать тест-хелперы HTTP, предоставляемые Laravel как $response = $this->post('/user', ['name' => 'Sally']);


Гораздо более эффективным подходом является использование репозитория дизайн шаблона .. это просто означает, сопоставить свои функции базы данных в отдельные классы и вызывать его из контроллеров ..

+0

Попробует попробовать с маршрутами, даст отзыв, когда я это сделаю. благодаря! –

+0

О чем-то еще, что я забыл сказать, вы попробуете '$ this-> expectException (\ PDOException :: class);' в начале теста поймать заброшенное исключение .. –