Laravel 使用正则表达式断言重定向
Laravel assert redirect with regular expression
我最近正在尝试使用 laravel 进行 TDD,我想断言重定向是否将用户带到了具有整数参数的 url。
我想知道我是否可以使用正则表达式来捕获所有正整数。
我是 运行 这个应用程序,使用 laravel 5.8 框架,我知道 url 参数是 1 因为我每次测试都会刷新数据库,所以设置重定向url 与 /projects/1
一样有效,但这种硬编码感觉很奇怪。
我附上了我尝试使用正则表达式的代码块,但这不起作用
/** @test */
public function a_user_can_create_projects()
{
// $this->withoutExceptionHandling();
//If i am logged in
$this->signIn(); // A helper fxn in the model
//If i hit the create url, i get a page there
$this->get('/projects/create')->assertStatus(200);
// Assumming the form is ready, if i get the form data
$attributes = [
'title' => $this->faker->sentence,
'description' => $this->faker->paragraph
];
//If we submit the form data, check that we get redirected to the projects path
//$this->post('/projects', $attributes)->assertRedirect('/projects/1');// Currently working
$this->post('/projects', $attributes)->assertRedirect('/^projects/\d+');
// check that the database has the data we just submitted
$this->assertDatabaseHas('projects', $attributes);
// Check that we the title of the project gets rendered on the projects page
$this->get('/projects')->assertSee($attributes['title']);
}
我希望测试将 assertRedirect('/^projects/\d+');
中的参数视为正则表达式,然后通过任何 url 像 /projects/1
到目前为止它以数字结尾,但它将它作为原始字符串并期望 /^projects/\d+
的 url
如有任何帮助,我将不胜感激。
看完 Jeffery Way 的教程后,他谈到了如何处理这个问题。
这是他解决问题的方法
//If we submit the form data,
$response = $this->post('/projects', $attributes);
//Get the project we just created
$project = \App\Project::where($attributes)->first();
// Check that we get redirected to the project's path
$response->assertRedirect('/projects/'.$project->id);
目前还不可能。您需要使用正则表达式测试响应中的 Location
header。
这是个问题,因为您不能使用当前的路由名称。这就是为什么我做了两个函数来为您的测试带来一点可读性。您将像这样使用此功能:
// This will redirect to some route with an numeric ID in the URL.
$response = $this->post(route('groups.create'), [...]);
$this->assertResponseRedirectTo(
$response,
$this->prepareRoute('group.detail', '[0-9]+'),
);
这是实现。
/**
* Assert whether the response is redirecting to a given URI that match the pattern.
*/
public function assertResponseRedirectTo(Illuminate\Testing\TestResponse\TestResponse $response, string $url): void
{
$lastOne = $this->oldURL ?: $url;
$this->oldURL = null;
$newLocation = $response->headers->get('Location');
$this->assertEquals(
1,
preg_match($url, $newLocation),
sprintf('Should redirect to %s, but got: %s', $lastOne, $newLocation),
);
}
/**
* Build the pattern that match the given URL.
*
* @param mixed $params
*/
public function prepareRoute(string $name, $params): string
{
if (! is_array($params)) {
$params = [$params];
}
$prefix = 'lovephp';
$rep = sprintf('%s$&%s', $prefix, $prefix);
$valuesToReplace = [];
foreach ($params as $index => $param) {
$valuesToReplace[$index] = str_replace('$&', $index . '', $rep);
}
$url = preg_quote(route($name, $valuesToReplace), '/');
$this->oldURL = route($name, $params);
foreach ($params as $index => $param) {
$url = str_replace(
sprintf('%s%s%s', $prefix, $index, $prefix),
$param,
$url,
);
}
return sprintf('/%s/', $url);
}
我最近正在尝试使用 laravel 进行 TDD,我想断言重定向是否将用户带到了具有整数参数的 url。 我想知道我是否可以使用正则表达式来捕获所有正整数。
我是 运行 这个应用程序,使用 laravel 5.8 框架,我知道 url 参数是 1 因为我每次测试都会刷新数据库,所以设置重定向url 与 /projects/1
一样有效,但这种硬编码感觉很奇怪。
我附上了我尝试使用正则表达式的代码块,但这不起作用
/** @test */
public function a_user_can_create_projects()
{
// $this->withoutExceptionHandling();
//If i am logged in
$this->signIn(); // A helper fxn in the model
//If i hit the create url, i get a page there
$this->get('/projects/create')->assertStatus(200);
// Assumming the form is ready, if i get the form data
$attributes = [
'title' => $this->faker->sentence,
'description' => $this->faker->paragraph
];
//If we submit the form data, check that we get redirected to the projects path
//$this->post('/projects', $attributes)->assertRedirect('/projects/1');// Currently working
$this->post('/projects', $attributes)->assertRedirect('/^projects/\d+');
// check that the database has the data we just submitted
$this->assertDatabaseHas('projects', $attributes);
// Check that we the title of the project gets rendered on the projects page
$this->get('/projects')->assertSee($attributes['title']);
}
我希望测试将 assertRedirect('/^projects/\d+');
中的参数视为正则表达式,然后通过任何 url 像 /projects/1
到目前为止它以数字结尾,但它将它作为原始字符串并期望 /^projects/\d+
如有任何帮助,我将不胜感激。
看完 Jeffery Way 的教程后,他谈到了如何处理这个问题。 这是他解决问题的方法
//If we submit the form data,
$response = $this->post('/projects', $attributes);
//Get the project we just created
$project = \App\Project::where($attributes)->first();
// Check that we get redirected to the project's path
$response->assertRedirect('/projects/'.$project->id);
目前还不可能。您需要使用正则表达式测试响应中的 Location
header。
这是个问题,因为您不能使用当前的路由名称。这就是为什么我做了两个函数来为您的测试带来一点可读性。您将像这样使用此功能:
// This will redirect to some route with an numeric ID in the URL.
$response = $this->post(route('groups.create'), [...]);
$this->assertResponseRedirectTo(
$response,
$this->prepareRoute('group.detail', '[0-9]+'),
);
这是实现。
/**
* Assert whether the response is redirecting to a given URI that match the pattern.
*/
public function assertResponseRedirectTo(Illuminate\Testing\TestResponse\TestResponse $response, string $url): void
{
$lastOne = $this->oldURL ?: $url;
$this->oldURL = null;
$newLocation = $response->headers->get('Location');
$this->assertEquals(
1,
preg_match($url, $newLocation),
sprintf('Should redirect to %s, but got: %s', $lastOne, $newLocation),
);
}
/**
* Build the pattern that match the given URL.
*
* @param mixed $params
*/
public function prepareRoute(string $name, $params): string
{
if (! is_array($params)) {
$params = [$params];
}
$prefix = 'lovephp';
$rep = sprintf('%s$&%s', $prefix, $prefix);
$valuesToReplace = [];
foreach ($params as $index => $param) {
$valuesToReplace[$index] = str_replace('$&', $index . '', $rep);
}
$url = preg_quote(route($name, $valuesToReplace), '/');
$this->oldURL = route($name, $params);
foreach ($params as $index => $param) {
$url = str_replace(
sprintf('%s%s%s', $prefix, $index, $prefix),
$param,
$url,
);
}
return sprintf('/%s/', $url);
}