Проблема функционального тестирования Laravel 5.2 Codeception с запросами PUT/PATCH

У меня проблема с обработкой обновления, обработанной в моих функциональных тестах на Codeception: у меня систематически возникает ошибка 404. Вот подробности.

Все идет хорошо для всех других смоделированных http-запросов, но когда кодецепция пытается выполнить метод обновления в HTTP-запросе put (запрос POST с параметром «_method», имеющим значение «PUT»), никогда не выполняется моим контроллером, что приводит к кодированию на URL-адрес обновления без перенаправления, которое должно произойти после обработки в этом методе обновления. Я попытался перенаправить на свою домашнюю страницу поверх моего метода обновления, чтобы проверить этот факт, и перенаправление никогда не происходит.

Для информации я использую модуль Laravel5. Вот содержимое моего файла functions.suite.yml:

class_name: FunctionalTester
modules:
    enabled:
        - Asserts
        - \Helper\Functional
        - MailCatcher
        - Laravel5:
            environment_file: .env.testing
    config:
        MailCatcher:
            url: 'http://192.168.10.10'
            port: '1080'

Я попытался заменить значение «PUT» параметра «_method» на «PATCH», чтобы увидеть, можно ли увидеть какие-либо изменения, но проблема не устранена, и поведение остается прежним.

Codeception включает приложение Laravel5 для его тестирования. Единственная подсказка, которая у меня есть, заключается в том, что у среды тестирования есть проблема с интерпретацией запроса PUT или PATCH. Для простого запроса POST нет проблем (создание не вызывает никаких проблем).

Я уточняю, что форма HTML верна, обновление происходит правильно в моей локальной среде, а HTTP-запрос содержит правильные параметры. Вот что у меня есть, когда я запускаю его с опцией --debug:

[Uri] http://project/en/permissions/update
[Method] POST
[Parameters] {"_token":"RUx7DjU3b6GEjodnpwXvJJYJIcmQJGbabj23q0yK","_method":"PATCH","_id":"1","name_en":"Administrator","name_fr":"Administrateur","slug":"admin"}
[Page] http://project/en/permissions/update
[Response] 200
[Request Cookies] {"XSRF-TOKEN":"eyJpdiI6InZQV2NVcTRoZHVONXYzZzNLTnBWU1E9PSIsInZhbHVlIjoiWWhWa0kyUGxJNkJRTXIyaEhVcDdHR0tRcklHZStpVWdlTjlDdmRKVmEyVDFPWkxBVmhLc1lra05zeWh1ZWtKMENCc29lWFZTN2lSd3dIbjZyNEo5eWc9PSIsIm1hYyI6ImEzMDNmOWM5OGQzNzE4ZWI5MDg0MTI0ZmQwMTI1ZTk0OTM1OTY4NjA5ZTZjMGFhYTI0MTdlMzMzM2QyMWQ4MzUifQ==","laravel_session":"eyJpdiI6ImF4cVFYYVNUU3J0WUd2VzNRZlhSc3c9PSIsInZhbHVlIjoibDdPd3ZEZVZOdDJwRlBjMVZtc2dNM0I3WUw0REEzK25NVFVWT1FIRjEzR05tRGZLXC9SYUZkRmhEdXlyQVdybURHTWVQVUtucnBkZEwwaTN4NWF6XC9YQT09IiwibWFjIjoiMzliODY4ZWUwYmZjODI1OTVkMTBiYjA4ODY2OWNiODc3ZTI1NzAzZmJhMjg4OTY4Y2MzM2VkMjYyYTkwOTQ2MyJ9"}
[Response Headers] {"cache-control":["no-cache"],"Set-Cookie":[{},{}]}

Как видите, процесс заканчивается на ответе 200, и все. Я протестировал его с несколькими страницами, и проблема везде одинакова.

Я заблокирован этой проблемой уже несколько недель, не найдя решения. Если у кого-то есть ключ, я слушаю!.


EDIT 1: 26/01/2015
Как меня спросили, вот мой файл маршрутов.
Как видите, я использую LaravelLocalization, это многоязычное приложение.
Я показываю вам только маршруты разрешений, но все они управляются таким образом.

Route::group([
'prefix'     => LaravelLocalization::setLocale(),
'middleware' => [
    'auth',
    'localize',
    'localeSessionRedirect',
    'localizationRedirect',
]], function () {

// permissions
Route::get(LaravelLocalization::transRoute('routes.permissions.index'), ['as' => 'permissions.index', 'uses' => 'User\PermissionsController@index']);
Route::get(LaravelLocalization::transRoute('routes.permissions.create'), ['as' => 'permissions.create', 'uses' => 'User\PermissionsController@create']);
Route::post(LaravelLocalization::transRoute('routes.permissions.store'), ['as' => 'permissions.store', 'uses' => 'User\PermissionsController@store']);
Route::get(LaravelLocalization::transRoute('routes.permissions.edit'), ['as' => 'permissions.edit', 'uses' => 'User\PermissionsController@edit']);
Route::put(LaravelLocalization::transRoute('routes.permissions.update'), ['as' => 'permissions.update', 'uses' => 'User\PermissionsController@update']);
Route::delete(LaravelLocalization::transRoute('routes.permissions.destroy'), ['as' => 'permissions.destroy', 'uses' => 'User\PermissionsController@destroy']); 

});


EDIT 2: 29/01/2015
Следуя объяснению решения Lerzenit здесь я попытался поместить в файл test/_bootstrap.php следующий код:

Request::enableHttpMethodParameterOverride();

Это не имело никакого эффекта, у меня все еще есть ответ 200, и метод обновления из моего контроллера никогда не достигается.
Я проверил, был ли параметр $httpMethodParameterOverride передан в true сразу после выполнения метода, и смог убедиться, что он был успешно установлен на true.
Я все еще ищу решение.


РЕДАКТИРОВАТЬ 3: 02.05.2015
У меня есть подсказка о способе расследования: мне удалось выполнить обновление для объекта с именем «Район», и это единственный объект на мой проект, чтобы иметь один и тот же маршрут на английском и французском языках. Как я указывал ранее, я использую плагин LaravelLocalization, и перевод маршрутов может быть причиной неправильной интерпретации параметра _method со значением PUT, которое должно перенаправлять на метод обновления моего контроллера.

Я был бы признателен, если бы кто-то мог помочь мне в этом.


person Okipa    schedule 25.01.2016    source источник
comment
Покажи свой файл маршрутов   -  person mcklayin    schedule 25.01.2016
comment
Привет @mcklayin, я отредактировал свой пост выше, чтобы показать файл маршрутов.   -  person Okipa    schedule 02.02.2016


Ответы (1)


Я наконец нашел решение!

Метод обновления так и не был достигнут, потому что в моих POST-запросах я иногда передавал идентификатор ресурса в запрос, используя скрытые переменные, например, _id.

Laravel ожидает, что идентификатор будет указан в сообщении UPDATEили DELETErequests после косой черты, поэтому методы UPDATE/DELETE никогда не были достигнуты. На самом деле это плохая практика — передавать параметры в запросе на запросы PUT/PATCH/DELETE, потому что целевой ресурс должен быть явно указан в URL-адресе.

Итак, если вы столкнулись с той же проблемой, убедитесь, что вы указали правильный маршрут POST в своей форме, например, route('users.update', ['id' => $user->id]).

Пфиууу, теперь я могу писать свои тесты, чтобы иметь 100% протестированное приложение. Это было болезненное расследование ;)

person Okipa    schedule 16.02.2016