I use the forward-method to forward requests to another Controller action:
$response = $this->forward($menuItemConfig['controller'] . ':' . $actionParams['action'], [
'request' => $request,
]);
This is the action of the Controller - post params are empty.
public function delete(Request $request): Response
{
if ($request->isMethod('POST') == false) {
throw new AccessDeniedException('Only POST allowed for this action.');
}
$postParams = $request->request->all();
dump($postParams);
die;
}
Passing parameters to the action does not work. All not-DI-params of the action are generally empty.
Symfony version 5.2.3
I have noticed that you are missing :, try this:
$response = $this->forward($menuItemConfig['controller'] . '::' . $actionParams['action'], [
'request' => $request,]);
Related
I made a search form in order to get events list. This form is displayed in front/search.html.twig. When I submit the search form, I'd like it leads me to front/events.html.twig.
When I submitted it, it says "category" doesn't exist. I don't have this problem when I replaced
return $this->redirectToRoute('events', $data);
with
return $this->render('front/events.html.twig', $data);
but I wish to use to route "events"...
This is my EventsController.php file :
<?php
namespace App\Controller\Front;
use App\Form\SearchType;
use App\Repository\EventsRepository;
use App\Repository\CategoriesRepository;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\Routing\Annotation\Route;
use Symfony\Component\HttpFoundation\Session\SessionInterface;
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
class EventsController extends AbstractController
{
#[Route('/search', name: 'search')]
public function search(Request $request, SessionInterface $sessionInterface)
{
$data = $request->request->all();
$sessionSearchFormData = $sessionInterface->get('searchFormData');
$form = $this->createForm(SearchType::class, ['data' => $sessionSearchFormData]);
$form->handleRequest($request);
if ($form->isSubmitted() && $form->isValid()) {
$data = $form->getData();
$sessionInterface->set('searchFormData', $data);
return $this->redirectToRoute('events', $data);
}
return $this->renderForm('front/search.html.twig', [
'form' => $form
]);
}
#[Route('/events', name: 'events')]
public function events(
EventsRepository $eventsRepository,
CategoriesRepository $categoriesRepository
){
$events = $eventsRepository->findAll();
$categories = $categoriesRepository->findAll();
return $this->render("front/events.html.twig", ['events' => $events, 'categories' => $categories]);
}
}
Bonjour Emilie,
Your route events does not have parameters. So you can't redirect it using parameters.
you can try something like this :
public function index($name)
{
return $this->redirectToRoute('events', ['max' => 10]);
}
You can forward to another Controller :
public function index($name)
{
$response = $this->forward('App\Controller\OtherController::fancy', [
'name' => $name,
'color' => 'green',
]);
// ... further modify the response or return it directly
return $response;
}
Regards,
hous has found the solution :
The second parameter must be an array :
return $this->redirectToRoute('events', [$data]);
I'm asking myself how to tests with phpunit in symfony roles access.
For example, if i have an indexAction and 5 different roles in my security config, i want to be sure that user A will have a 401, user B a 403, user C a 500...
But it cause an issue: tests are really long to execute, because we have 5 functional tests by action.
Now, i'm doing that kind of thing:
/**
* #covers \App\Bundle\FrontBundle\Controller\DefaultController::indexAction()
*
* #dataProvider rolesAllAccess
*
* #param string $user
* #param integer $expectedCode
*
* #return void
*/
public function testRolesIndexAction($user, $expectedCode)
{
$client = $this->createClientWith($user);
$client->request('GET', '/');
$this->assertEquals($expectedCode, $client->getResponse()->getStatusCode());
}
The function createClientWith authenticate a client that i have defined in my dataProvider before. It makes exactly what i described before.
Do you have any idea on how doing that better or - at least - with better performances ?
Thanks!
Depends on your authentication method. I use JWT. Also, all my web tests extends ApiTestCase that extends WebTestCase. And In all WebTestCases I use a logged user. Logged use log in inside the setup method.
abstract class ApiTestCase extends WebTestCase
{
protected function setUp()
{
$client = static::makeClient();
$client->request(
'POST',
'/tokens', [
'username' => 'username',
'password' => 'password'
], [
// no files here
],
$headers = [
'HTTP_CONTENT_TYPE' => 'application/x-www-form-urlencoded',
'HTTP_ACCEPT' => 'application/json',
]
);
$response = $client->getResponse();
$data = json_decode($response->getContent(), true);
$this->client = static::createClient(
array(),
array(
'HTTP_Authorization' => sprintf('%s %s', 'Bearer', $data['token']),
'HTTP_CONTENT_TYPE' => 'application/json',
'HTTP_ACCEPT' => 'application/json',
)
);
}
}
And here an example of test:
class DivisionControllerTest extends ApiTestCase
{
public function testList()
{
$this->client->request('GET', '/resource');
$response = $this->client->getResponse();
$expectedContent = ' !!! put expected content here !!! ';
$this->assertEquals(
$expectedContent,
$response->getContent()
);
}
}
Your test could be
public function testRolesIndexAction($expectedCode)
{
$this->client->request('GET', '/');
$this->assertEquals($expectedCode, $this->client->getResponse()->getStatusCode());
}
Try to use this to call one time $this->createClientWith. I suggest to look here for more recommandation.
I don't find the reason why my subsequent kernel.response event listener won't modify my response here. Do you encountered this problem too before, or is there a misprint into the lines ?
Context: users will have a 10-items visit history attached to them, under Symfony3.
public function onResponse(FilterResponseEvent $event)
{
$request = $event->getRequest();
if(!$event->isMasterRequest() || !preg_match('#^dm_.*#', $request->get('_route'))){
return;
}
$history = $request->cookies->get('history');
if(!$history)$history = "[]";
$history = json_decode($history, true);
$addon = [
'route' => $request->get('_route'),
'route_params' => $request->attributes->get('_route_params'),
'url' => $request->getRequestUri(),
'date' => new \Datetime
];
$history[] = $addon;
$history = array_slice(
$history,
-10
);
$cookie = new Cookie('history', json_encode($history), time() + 3600);
$response = $event->getResponse();
$response->headers->setCookie($cookie);
}
I added some var_dump()s, to check that event was caught (and it was). I also tested to modify headers elsewhere, and it works fine. So, just here, I don't see why it doesn't.
I want to create a pdf file out of some route-dependant data
{http://example.com/products/123/?action=update}
$app->finish(function (Request $request, Response $response) {
// Make a pdf file, only if:
// - the route is under /products/
// - the action is update
// - the subsequent ProductType form isSubmitted() and isValid()
// - the 'submit' button on the ProductType form isClicked()
});
As a normal form submission process I have:
public function update(Application $app, Request $request)
{
$form = $app['form.factory']->create(ProductType::class, $product);
$form->handleRequest($request);
if ($form->isSubmitted() && $form->isValid()) {
if (!$form->get('submit')->isClicked()) {
return $app->redirect('somewhere');
}
$product = $form->getData();
$app['em']->persist($product);
$app['em']->flush();
return $app->redirect('product_page');
}
return $app['twig']->render('products/update.html.twig', array(
'form' => $form->createView(),
));
}
Questions:
Should I duplicate all of the conditionals in finish middleware?
How to access the Product entity in finish middleware?
Consider having multiple resource types like Products, Services, Users, ...
I want to redirect and send my request to another route but this method is not working.
return $this->redirect($this->generateUrl(
'admin_platform_create',
array('request' => $request)
));
When I arrive into admin_platform_create it doesn't pass that if
public function createAction(Request $request)
{
if ($request->getMethod() == 'POST')
{
Though this is working,
return $this->forward('AdminPlatformBundle:Manage:edit',
array('request' => $request));
It is not what I need as it is not writing the new URL.
Thanks for your help!
If you are using Symfony 2.6 or later, you can do it:
return $this->redirectToRoute('route', [
'request' => $request
], 307);