How to reset form in Symfony - php

How can I reset the form after submit? It's a simple search form where I show a field on the top and a table in the bottom that shows either the results based on the search or the whole list... but it does not reset, the search key remained...
/**
* #Route("/", name="plazas_index")
*/
public function indexAction(Request $request)
{
$form = $this->createForm('AppBundle\Form\BuscarType');
$form->handleRequest($request);
$repository = $this->getDoctrine()->getRepository('AppBundle:Plaza');
if ($form->isSubmitted() && $form->isValid()) {
$clave = $form['clave']->getData();
$query = $repository->createQueryBuilder('p')
->where('p.nombre LIKE :nombre')
->orWhere('p.localidad LIKE :localidad')
->setParameter('nombre', '%'.$clave.'%')
->setParameter('localidad', '%'.$clave.'%')
->orderBy('p.nombre', 'ASC')
->getQuery();
$plazas = $query->getResult();
$cant = count($plazas);
$this->addFlash($cant ? 'success' : 'warning', 'La búsqueda de '.$clave. ' ha producido '.$cant.' resultados');
//return $this->redirectToRoute('plazas_index');
}
else {
$plazas = $repository->findAll();
}
unset ($form);
$form = $this->createForm('AppBundle\Form\BuscarType');
$form->handleRequest($request);
return $this->render('admin/plazas/index.html.twig', array(
'plazas' => $plazas,
'buscar_form' => $form->createView(),
));
}
I can't redirect because I do the render at the end of the action...
Any help is welcome, thanks!!

Remove the second $form->handleRequest($request); line and you are good to go!
handleRequest takes the submitted POST or GET data and applies it to the form, so if you want a blank form then you shouldn't call that.

Related

Why the URL header takes the wrong parameter?

On a CRUD comment system that I put on posts, I have no problem modifying/deleting said comment by retrieving the post of the id and that of the comment. Here is the method used (which is also used to create a comment):
/**
* #Route("{id}/create", name="createComment")
* #Route("{id}/{comment}/modif", name="modifComment", defaults={"comment"=1}, methods="GET|POST")
*/
public function modification(FilmRepository $film, Comment $comment = null, Request $req, EntityManagerInterface $em, $id)
{
if(!$comment) {
$comment = new Comment();
}
$film = $em->getRepository(Film::class)->findOneBy(array('id' => $id));
$user = $this->getUser();
$form = $this->createForm(CommentType::class, $comment);
$form->handleRequest($req);
dump($film);
dump($comment);
if($form->isSubmitted() && $form->isValid()) {
$comment->setAuthor($user);
$comment->setFilm($film);
$comment->setCreatedAt(new \DateTime());
$em->persist($comment);
$em->flush();
$this->addFlash('success', 'L\'action a bien été effectuée');
return $this->redirectToRoute('home');
}
return $this->render('comment/modif.html.twig', [
"comment" => $comment,
"form" => $form->createView()
]);
}
The problem comes when I try to create a new comment. When I am directed to the form, it considers that the post id corresponds to the comment id (for example, if I am on post 1 and want to add a comment it takes me to the comment form 1). However I specified in my twig request (contrary to modify) that I only took the film.id parameter:
{# Modif comment, with two parameters, functionnal#}
Modif
{# Add comment, with one parameter, unfunctionnal#}
Add
I used the same code as for the CRUD of my posts, and yet he when I want to create a new post returns me an empty form :
/**
* #Route("/admin/create", name="createFilm")
* #Route("/admin/{id}", name="modifFilm", methods="GET|POST")
*/
public function modification(Film $film = null, Request $req, EntityManagerInterface $em)
{
if(!$film) {
$film = new Film();
}
$form = $this->createForm(FilmType::class, $film);
$form->handleRequest($req);
if($form->isSubmitted() && $form->isValid()) {
$em->persist($film);
$em->flush();
$this->addFlash('success', 'L\'action a bien été effectuée');
return $this->redirectToRoute('admin');
}
return $this->render('admin/modif.html.twig', [
"film" => $film,
"form" => $form->createView(),
"admin" => true
]);
}
So the problem comes from the url which takes the id of the film and interprets it as the id of the comment, but I don't understand what is causing this?
In your public function, you have Comment $comment.
You are giving two argument to your Route: id and comment
The Paramconverter will try to find the correct Comment with what you gave him (an id and a comment). It will not check where the value comes from in your twig file.
Indeed, if your argument id comes from a film.id, the Paramconverter will give you the wrong comment.
What you should do is send the comment.id to the argument id.
You can change your Route this way :
#Route("{film}/{id}/modif
For your Twig :
Modif

Pass several parameters correctly to your controller

I have already inquired here and there but nothing more or less corresponds to my problem.
I have a page with information about a movie, which I access with an id parameter:
See comments
The film table having a relation with the table how, I display all the comments specific to the movie thanks to an ArrayCollection :
$filmRepo = $repo->find($id);
$comments = $filmRepo->getComments();
I created a CommentController in which I wrote this method whose goal would be to recover the id of the movie AND the id of the comment in order to be able to make CRUD operations on it:
/**
* #Route("{id}/{comment}/create", name="createComment")
* #Route("{id}/{comment}/modif", name="modifComment", defaults={"comment"=1}, methods="GET|POST")
*/
public function modification(Comment $comment = null, Film $film, Request $req, EntityManagerInterface $em)
{
if(!$comment) {
$comment = new Comment();
}
$user = $this->getUser();
$form = $this->createForm(CommentType::class, $comment);
$form->handleRequest($req);
if($form->isSubmitted() && $form->isValid()) {
$comment->setAuthor($user);
$comment->setFilm($film);
$em->persist($comment);
$em->flush();
$this->addFlash('success', 'L\'action a bien été effectuée');
return $this->redirectToRoute('home');
}
return $this->render('comment/modif.html.twig', [
"comment" => $comment,
"form" => $form->createView()
]);
}
But no matter which comment I select, it takes the default comment, that is to say the one with id 1. So something is wrong with my request. However I pass the two parameters in the twig template:
Modif
The problem comes from a syntax error in the twig template. Instead of :
Modif
Rather do :
Modif

How to get value of the form field in Symfony 4 when validation fails?

I have two dropdowns in my form . Options in second dropdown depend on selected value in the first dropdown. If validation fails I need to get posted value of the first dropdown to set options in the second dropdown. So how to receive posted value in the form type class when validation fails?
$form = $this->createForm(MyFormType::class);
$form->handleRequest($request);
if ($form->isSubmitted() && $form->isValid()) {
/**
* Do your stuff when form is valid
*/
} else {
/**
* Here you can get the input data even failed with $form->getData()
*/
dump($form->getData());
}
$form->getData() gives me the values of input that didn't failed in the else:
array:4 [▼
"first_dropdown" => "hello"
]
$advert = new Advert();
$form = $this->createForm(AdvertType::class, $advert, ['method' => 'POST'])
->handleRequest($request);
if (false === $form->isSubmitted()) {
$form->submit([]);
}
if (false === $form->isValid()) {
return ['form' => $form];
}
$manager = $this->getDoctrine()->getManager();
$this->appendTags($advert);
$manager->persist($advert);
$manager->flush();
return $advert;
I needed something like below, in my form type class eg. DocType in buildForm() method I did:
$request = Request::createFromGlobals();
$myObjectId = $request->request->get('doc')['object']; // selected option of the first dropdown
$object = ($obectId) ? $objectRepository->find($objectId) : null;
Then I could use fetched object, to populate second dropdown, using query builder.

How to loop form/new entity in Symfony

I'm having an issue with looping a form in Symfony using while loop. When the user enters one student period and it matches a registration reiterate the form to let them enter a 2nd student period and then a 3rd. I'm not doing it correctly or could I reiterate entity=new Student(); to let them enter two entities .
public function createAction(Request $request){
$entity = new Student();
$form = $this->createCreateForm($entity);
$form->handleRequest($request);
if ($form->isSubmitted() && $form->isValid()) {
$em = $this->getDoctrine()->getManager();
$student = $em->getRepository('AcmeDemoBundle:Payrollperiod')
->findOneBy([
'begindate'=>$form->get('beginDate')->getData(),
'lastdate'=>$form->get('lastDate')->getData()
]);
$registration = $em->getRepository('AcmeDemoBundle:Payrollweek')
->findBystartdateAndenddate(
$form->get('beginDate')->getData(),
$form->get('lastDate')->getData()
);
$counter = count($registration);
while($counter<=2) {
if ($student){
$this->addFlash('error', 'Duplicate error: Student Period already existed.' );
return $this->redirect($this->generateUrl('student'));
}
elseif ($registration){
foreach ($registration as $reg) {
$reg->setStudentid($entity);
}
$em->persist($entity);
$em->flush();
return $this->redirect($this->generateUrl('payrollperiod'));
}
else{
$this->addFlash('error', ' does not match .');
return $this->redirect($this->generateUrl('student'));
}
}
return array(
'entity' => $entity,
'form' => $form->createView(),
);
}
}
Read the documentation here http://symfony.com/doc/current/reference/forms/types/form.html#allow-extra-fields on adding fields. Your UI/Front-end should created more fields when the user needs to add a second or more periods. I should generate proper Symfony form elements and then when you post, you can handle it like a standard form post, iterating over the Request since the periods will be submitted as an array.
I did something like this in the past I adding a new form row was an AJAX call to a template that described the form input fields so I wasn't having to craft form HTML in Javascript/jQuery. .append() the template results to the form-- post and process the request.

Symfony 2 - Layout embed "no entity/class form" validation isn't working

I'm developing a blog in symfony and i'm stuck with forms that are embed inside the layout. In my case a simple search form.
<div class="b-header-block m-search">
{{ render(controller('YagoQuinoySimpleBlogBundle:Blog:searchArticles')) }}
</div>
To render the form i'm using an embed controller inside the layout twig file.
public function searchArticlesAction(Request $request)
{
$form = $this->createForm(new SearchArticlesType());
$form->handleRequest($request);
if ($form->isValid()) {
// Do stuff here
}
return $this->render('YagoQuinoySimpleBlogBundle:Blog:searchArticles.html.twig', array(
'form' => $form->createView()
));
}
The indexAction is the one that retrieves the form data and filters a list of articles.
public function indexAction(Request $request)
{
$form = $this->createForm(new SearchArticlesType());
$form->handleRequest($request);
if ($form->isValid()) {
$data = $form->getData();
$criteria = array(
'title' => $data['search']
);
} else {
$criteria = array();
}
$articles = $this->getDoctrine()->getRepository('YagoQuinoySimpleBlogBundle:Article')->findBy($criteria, array(
'createDateTime' => 'DESC'
), 5);
return $this->render('YagoQuinoySimpleBlogBundle:Blog:index.html.twig', array('articles' => $articles));
}
SearchArticlesType is a form class
class SearchArticlesType extends AbstractType {
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder->add('search', 'text', array(
'constraints' => new NotBlank()
))
->add('submit', 'submit', array(
'label' => 'Buscar'
));
}
public function getName()
{
return 'searchArticles';
}
}
The problem comes when i submit this form. The indexAction do his part, validating the form and filtering the articles but when the embed controller tries to validate data (just for displaying info or whatever)
$form->handleRequest($request);
if ($form->isValid()) {
// Do stuff here
}
I feel like i'm missing something.
Thank you for your help!
When you call render(controller('your_route')) you are actually making a sub request which means the parameters bags are emptied so your request isn't "handled" by the form.
If you are using 2.4+ you could get the master request from the request stack using ..
/** #var \Symfony\Component\HttpFoundation\RequestStack $requestStack */
$requestStack = $this->get('request_stack');
$masterRequest = $requestStack->getMasterRequest();
And then you could handle that request in your rendered controller as opposed to the current (sub) request like..
$form->handleRequest($masterRequest);
In your: public function searchArticlesAction(Request $request) you're missing second argument on create form
$searchArticle = new SearchArticle(); // I assume this is how you named the Entity, if not just change the entity name
$form = $this->createForm(new SearchArticlesType(), $article);

Categories