From 247f9e6a01bba85ee1031e413907b6b1b39c9cbd Mon Sep 17 00:00:00 2001 From: Hugo PRADIER Date: Wed, 5 Jun 2024 11:36:46 +0200 Subject: [PATCH 01/11] add form species --- composer.json | 2 +- composer.lock | 29 +++++++++++----------- src/Controller/SpeciesController.php | 37 ++++++++++++++++++++++++++++ src/Entity/Species.php | 4 +++ src/Form/SpeciesType.php | 28 +++++++++++++++++++++ templates/species/index.html.twig | 20 +++++++++++++++ templates/species/species.html.twig | 3 +++ 7 files changed, 108 insertions(+), 15 deletions(-) create mode 100644 src/Controller/SpeciesController.php create mode 100644 src/Form/SpeciesType.php create mode 100644 templates/species/index.html.twig create mode 100644 templates/species/species.html.twig diff --git a/composer.json b/composer.json index d59ef97..7fbd14b 100644 --- a/composer.json +++ b/composer.json @@ -106,7 +106,7 @@ "symfony/browser-kit": "7.0.*", "symfony/css-selector": "7.0.*", "symfony/debug-bundle": "7.0.*", - "symfony/maker-bundle": "^1.0", + "symfony/maker-bundle": "^1.59", "symfony/phpunit-bridge": "^7.0", "symfony/stopwatch": "7.0.*", "symfony/web-profiler-bundle": "7.0.*" diff --git a/composer.lock b/composer.lock index 9e8ea25..75b7896 100644 --- a/composer.lock +++ b/composer.lock @@ -4,7 +4,7 @@ "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies", "This file is @generated automatically" ], - "content-hash": "888e1953f86d0f1fe9b271b85aab0ed0", + "content-hash": "c3dc9b5ee79b98f2d1fabe3668860864", "packages": [ { "name": "composer/semver", @@ -3507,16 +3507,16 @@ }, { "name": "symfony/form", - "version": "v7.0.7", + "version": "v7.0.8", "source": { "type": "git", "url": "https://github.com/symfony/form.git", - "reference": "b4df6a399a2b03782a0163807239db342659f54f" + "reference": "1d0128e2f7e80c346ec51fa4d1ce4fec0d435eeb" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/form/zipball/b4df6a399a2b03782a0163807239db342659f54f", - "reference": "b4df6a399a2b03782a0163807239db342659f54f", + "url": "https://api.github.com/repos/symfony/form/zipball/1d0128e2f7e80c346ec51fa4d1ce4fec0d435eeb", + "reference": "1d0128e2f7e80c346ec51fa4d1ce4fec0d435eeb", "shasum": "" }, "require": { @@ -3583,7 +3583,7 @@ "description": "Allows to easily create, process and reuse HTML forms", "homepage": "https://symfony.com", "support": { - "source": "https://github.com/symfony/form/tree/v7.0.7" + "source": "https://github.com/symfony/form/tree/v7.0.8" }, "funding": [ { @@ -3599,7 +3599,7 @@ "type": "tidelift" } ], - "time": "2024-04-28T11:44:19+00:00" + "time": "2024-05-31T14:55:39+00:00" }, { "name": "symfony/framework-bundle", @@ -6887,16 +6887,16 @@ }, { "name": "symfony/validator", - "version": "v7.0.7", + "version": "v7.0.8", "source": { "type": "git", "url": "https://github.com/symfony/validator.git", - "reference": "ab4e75b9d23ba70e78480aecbe4d8da15adf10eb" + "reference": "23af65dff1f4dfee9aab3a0123a243e40fa3d9cf" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/validator/zipball/ab4e75b9d23ba70e78480aecbe4d8da15adf10eb", - "reference": "ab4e75b9d23ba70e78480aecbe4d8da15adf10eb", + "url": "https://api.github.com/repos/symfony/validator/zipball/23af65dff1f4dfee9aab3a0123a243e40fa3d9cf", + "reference": "23af65dff1f4dfee9aab3a0123a243e40fa3d9cf", "shasum": "" }, "require": { @@ -6941,7 +6941,8 @@ "Symfony\\Component\\Validator\\": "" }, "exclude-from-classmap": [ - "/Tests/" + "/Tests/", + "/Resources/bin/" ] }, "notification-url": "https://packagist.org/downloads/", @@ -6961,7 +6962,7 @@ "description": "Provides tools to validate values", "homepage": "https://symfony.com", "support": { - "source": "https://github.com/symfony/validator/tree/v7.0.7" + "source": "https://github.com/symfony/validator/tree/v7.0.8" }, "funding": [ { @@ -6977,7 +6978,7 @@ "type": "tidelift" } ], - "time": "2024-04-28T11:44:19+00:00" + "time": "2024-06-02T15:49:03+00:00" }, { "name": "symfony/var-dumper", diff --git a/src/Controller/SpeciesController.php b/src/Controller/SpeciesController.php new file mode 100644 index 0000000..4cae6ce --- /dev/null +++ b/src/Controller/SpeciesController.php @@ -0,0 +1,37 @@ +createForm(SpeciesType::class, $species); + + $form->handleRequest($request); + if ($form->isSubmitted() && $form->isValid()) { + + $species = $form->getData(); + + $entityManager->persist($species); + $entityManager->flush(); + + return $this->redirectToRoute('_profiler_home'); + } + + return $this->render('species/species.html.twig', [ + 'form' => $form->createView(), + ]); + } +} diff --git a/src/Entity/Species.php b/src/Entity/Species.php index 9243896..2dd9528 100644 --- a/src/Entity/Species.php +++ b/src/Entity/Species.php @@ -6,6 +6,7 @@ use App\Repository\SpeciesRepository; use Doctrine\Common\Collections\ArrayCollection; use Doctrine\Common\Collections\Collection; use Doctrine\ORM\Mapping as ORM; +use Symfony\Component\Validator\Constraints as Assert; #[ORM\Entity(repositoryClass: SpeciesRepository::class)] class Species @@ -16,12 +17,15 @@ class Species private ?int $id = null; #[ORM\Column(length: 255)] + #[Assert\NotBlank] private ?string $scientific_name = null; #[ORM\Column(length: 255)] + #[Assert\NotBlank] private ?string $vernacular_name = null; #[ORM\Column(length: 255)] + #[Assert\NotBlank] private ?string $region = null; /** diff --git a/src/Form/SpeciesType.php b/src/Form/SpeciesType.php new file mode 100644 index 0000000..0d6cab9 --- /dev/null +++ b/src/Form/SpeciesType.php @@ -0,0 +1,28 @@ +add('scientific_name') + ->add('vernacular_name') + ->add('region') + ->add('save', SubmitType::class, ['label' => 'Create Species']); + } + + public function configureOptions(OptionsResolver $resolver): void + { + $resolver->setDefaults([ + 'data_class' => Species::class, + ]); + } +} diff --git a/templates/species/index.html.twig b/templates/species/index.html.twig new file mode 100644 index 0000000..3f56295 --- /dev/null +++ b/templates/species/index.html.twig @@ -0,0 +1,20 @@ +{% extends 'base.html.twig' %} + +{% block title %}Hello SpeciesController!{% endblock %} + +{% block body %} + + +
+

Hello {{ controller_name }}! ✅

+ + This friendly message is coming from: + +
+{% endblock %} diff --git a/templates/species/species.html.twig b/templates/species/species.html.twig new file mode 100644 index 0000000..2727393 --- /dev/null +++ b/templates/species/species.html.twig @@ -0,0 +1,3 @@ +{{ form_start(form, {'attr': {'novalidate': 'novalidate'}}) }} + {{ form_widget(form) }} +{{ form_end(form) }} -- 2.36.3 From 8b9735b75c2aa83b801f0f0b16dbabb7a4419927 Mon Sep 17 00:00:00 2001 From: Hugo PRADIER Date: Wed, 5 Jun 2024 11:39:53 +0200 Subject: [PATCH 02/11] add route valid after success --- src/Controller/SpeciesController.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Controller/SpeciesController.php b/src/Controller/SpeciesController.php index 4cae6ce..9c222a9 100644 --- a/src/Controller/SpeciesController.php +++ b/src/Controller/SpeciesController.php @@ -27,7 +27,7 @@ class SpeciesController extends AbstractController $entityManager->persist($species); $entityManager->flush(); - return $this->redirectToRoute('_profiler_home'); + return $this->redirectToRoute('app_species'); } return $this->render('species/species.html.twig', [ -- 2.36.3 From 1d3ef1bfb8d75b8903b305d3554db1aee7fe8961 Mon Sep 17 00:00:00 2001 From: Hugo PRADIER Date: Wed, 5 Jun 2024 11:58:28 +0200 Subject: [PATCH 03/11] add form post --- src/Controller/PostController.php | 30 +++++++++++++++++++++++- src/Entity/Post.php | 4 ++++ src/Form/PostType.php | 39 +++++++++++++++++++++++++++++++ templates/post/post.html.twig | 3 +++ 4 files changed, 75 insertions(+), 1 deletion(-) create mode 100644 src/Form/PostType.php create mode 100644 templates/post/post.html.twig diff --git a/src/Controller/PostController.php b/src/Controller/PostController.php index 0df3016..93c5db1 100644 --- a/src/Controller/PostController.php +++ b/src/Controller/PostController.php @@ -4,8 +4,12 @@ namespace App\Controller; use App\Repository\PostRepository; use Symfony\Bundle\FrameworkBundle\Controller\AbstractController; -use Symfony\Component\HttpFoundation\Response; use Symfony\Component\Routing\Attribute\Route; +use Symfony\Component\HttpFoundation\Request; +use Symfony\Component\HttpFoundation\Response; +use App\Entity\Post; +use App\Form\PostType; +use Doctrine\ORM\EntityManagerInterface; class PostController extends AbstractController { @@ -17,4 +21,28 @@ class PostController extends AbstractController 'posts' => $posts, ]); } + + #[Route('/posts', name: 'app_posts')] + public function new(Request $request, EntityManagerInterface $entityManager): Response + { + $post = new Post(); + + $form = $this->createForm(PostType::class, $post); + + $form->handleRequest($request); + if ($form->isSubmitted() && $form->isValid()) { + + $post = $form->getData(); + $post->setPublicationDate(new \DateTimeImmutable("now")); + + $entityManager->persist($post); + $entityManager->flush(); + + return $this->redirectToRoute('app_posts'); + } + + return $this->render('post/post.html.twig', [ + 'form' => $form->createView(), + ]); + } } diff --git a/src/Entity/Post.php b/src/Entity/Post.php index 17ce70c..2bd8488 100644 --- a/src/Entity/Post.php +++ b/src/Entity/Post.php @@ -21,15 +21,19 @@ class Post private ?\DateTimeImmutable $publicationDate = null; #[ORM\Column(nullable: true)] + #[Assert\NotBlank] private ?float $latitude = null; #[ORM\Column(nullable: true)] + #[Assert\NotBlank] private ?float $longitude = null; #[ORM\Column(nullable: true)] + #[Assert\NotBlank] private ?float $altitude = null; #[ORM\Column(type: Types::TEXT)] + #[Assert\NotBlank] private ?string $commentary = null; #[ORM\ManyToOne(inversedBy: 'posts')] diff --git a/src/Form/PostType.php b/src/Form/PostType.php new file mode 100644 index 0000000..fef3b0c --- /dev/null +++ b/src/Form/PostType.php @@ -0,0 +1,39 @@ +add('foundDate', null, [ + 'widget' => 'single_text', + ]) + ->add('latitude') + ->add('longitude') + ->add('altitude') + ->add('commentary') + ->add('species', EntityType::class, [ + 'class' => Species::class, + 'choice_label' => 'scientific_name', + ]) + ->add('save', SubmitType::class, ['label' => 'Create Post']); + ; + } + + public function configureOptions(OptionsResolver $resolver): void + { + $resolver->setDefaults([ + 'data_class' => Post::class, + ]); + } +} diff --git a/templates/post/post.html.twig b/templates/post/post.html.twig new file mode 100644 index 0000000..2727393 --- /dev/null +++ b/templates/post/post.html.twig @@ -0,0 +1,3 @@ +{{ form_start(form, {'attr': {'novalidate': 'novalidate'}}) }} + {{ form_widget(form) }} +{{ form_end(form) }} -- 2.36.3 From 94992c09dbd1c594482b261be1429f32f2dd331d Mon Sep 17 00:00:00 2001 From: Hugo PRADIER Date: Fri, 7 Jun 2024 13:36:11 +0200 Subject: [PATCH 04/11] correction lint ci --- src/Entity/Post.php | 1 + 1 file changed, 1 insertion(+) diff --git a/src/Entity/Post.php b/src/Entity/Post.php index 2bd8488..7f000b3 100644 --- a/src/Entity/Post.php +++ b/src/Entity/Post.php @@ -5,6 +5,7 @@ namespace App\Entity; use App\Repository\PostRepository; use Doctrine\DBAL\Types\Types; use Doctrine\ORM\Mapping as ORM; +use Symfony\Component\Validator\Constraints as Assert; #[ORM\Entity(repositoryClass: PostRepository::class)] class Post -- 2.36.3 From 189a9fc79ae83390842e1677b2436f8d8c536f5b Mon Sep 17 00:00:00 2001 From: Hugo PRADIER Date: Fri, 7 Jun 2024 14:06:16 +0200 Subject: [PATCH 05/11] ajout authorisations avant post species et posts --- src/Controller/PostController.php | 6 ++++-- src/Controller/RegistrationController.php | 6 +++++- src/Controller/SpeciesController.php | 3 ++- 3 files changed, 11 insertions(+), 4 deletions(-) diff --git a/src/Controller/PostController.php b/src/Controller/PostController.php index 93c5db1..68ec08f 100644 --- a/src/Controller/PostController.php +++ b/src/Controller/PostController.php @@ -10,6 +10,7 @@ use Symfony\Component\HttpFoundation\Response; use App\Entity\Post; use App\Form\PostType; use Doctrine\ORM\EntityManagerInterface; +use Symfony\Component\Security\Http\Attribute\IsGranted; class PostController extends AbstractController { @@ -22,7 +23,8 @@ class PostController extends AbstractController ]); } - #[Route('/posts', name: 'app_posts')] + #[Route('/posts', name: 'app_add_posts')] + #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] public function new(Request $request, EntityManagerInterface $entityManager): Response { $post = new Post(); @@ -38,7 +40,7 @@ class PostController extends AbstractController $entityManager->persist($post); $entityManager->flush(); - return $this->redirectToRoute('app_posts'); + return $this->redirectToRoute('app_add_posts'); } return $this->render('post/post.html.twig', [ diff --git a/src/Controller/RegistrationController.php b/src/Controller/RegistrationController.php index 6bfc237..43043a9 100644 --- a/src/Controller/RegistrationController.php +++ b/src/Controller/RegistrationController.php @@ -34,7 +34,11 @@ class RegistrationController extends AbstractController // do anything else you need here, like send an email - return $this->redirectToRoute('_profiler_home'); + return $this->redirectToRoute('app_login'); + } + + if ($this->getUser()) { + return $this->redirectToRoute('app_posts'); } return $this->render('registration/register.html.twig', [ diff --git a/src/Controller/SpeciesController.php b/src/Controller/SpeciesController.php index 9c222a9..a330aa8 100644 --- a/src/Controller/SpeciesController.php +++ b/src/Controller/SpeciesController.php @@ -9,14 +9,15 @@ use Symfony\Component\Routing\Annotation\Route; use App\Entity\Species; use App\Form\SpeciesType; use Doctrine\ORM\EntityManagerInterface; +use Symfony\Component\Security\Http\Attribute\IsGranted; class SpeciesController extends AbstractController { #[Route('/species', name: 'app_species')] + #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] public function new(Request $request, EntityManagerInterface $entityManager): Response { $species = new Species(); - $form = $this->createForm(SpeciesType::class, $species); $form->handleRequest($request); -- 2.36.3 From be057a316d41a5ff1b20a6b6005a01347639b672 Mon Sep 17 00:00:00 2001 From: Hugo PRADIER Date: Fri, 7 Jun 2024 15:07:00 +0200 Subject: [PATCH 06/11] correction suite a demande ajout --- src/Controller/PostController.php | 6 +++--- src/Controller/SpeciesController.php | 4 ++-- src/Entity/Post.php | 1 + src/Form/PostType.php | 4 +++- templates/species/index.html.twig | 20 -------------------- 5 files changed, 9 insertions(+), 26 deletions(-) delete mode 100644 templates/species/index.html.twig diff --git a/src/Controller/PostController.php b/src/Controller/PostController.php index 68ec08f..b0bc747 100644 --- a/src/Controller/PostController.php +++ b/src/Controller/PostController.php @@ -23,7 +23,7 @@ class PostController extends AbstractController ]); } - #[Route('/posts', name: 'app_add_posts')] + #[Route('/posts/add', name: 'app_add_posts')] #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] public function new(Request $request, EntityManagerInterface $entityManager): Response { @@ -32,8 +32,8 @@ class PostController extends AbstractController $form = $this->createForm(PostType::class, $post); $form->handleRequest($request); + //dd($form); if ($form->isSubmitted() && $form->isValid()) { - $post = $form->getData(); $post->setPublicationDate(new \DateTimeImmutable("now")); @@ -44,7 +44,7 @@ class PostController extends AbstractController } return $this->render('post/post.html.twig', [ - 'form' => $form->createView(), + 'form' => $form, //->createView(), ]); } } diff --git a/src/Controller/SpeciesController.php b/src/Controller/SpeciesController.php index a330aa8..1bf70ee 100644 --- a/src/Controller/SpeciesController.php +++ b/src/Controller/SpeciesController.php @@ -13,7 +13,7 @@ use Symfony\Component\Security\Http\Attribute\IsGranted; class SpeciesController extends AbstractController { - #[Route('/species', name: 'app_species')] + #[Route('/species/add', name: 'app_add_species')] #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] public function new(Request $request, EntityManagerInterface $entityManager): Response { @@ -28,7 +28,7 @@ class SpeciesController extends AbstractController $entityManager->persist($species); $entityManager->flush(); - return $this->redirectToRoute('app_species'); + return $this->redirectToRoute('app_add_species'); } return $this->render('species/species.html.twig', [ diff --git a/src/Entity/Post.php b/src/Entity/Post.php index 7f000b3..21a5976 100644 --- a/src/Entity/Post.php +++ b/src/Entity/Post.php @@ -16,6 +16,7 @@ class Post private ?int $id = null; #[ORM\Column] + #[Assert\NotBlank] private ?\DateTimeImmutable $foundDate = null; #[ORM\Column] diff --git a/src/Form/PostType.php b/src/Form/PostType.php index fef3b0c..ceaff2c 100644 --- a/src/Form/PostType.php +++ b/src/Form/PostType.php @@ -6,6 +6,7 @@ use App\Entity\Post; use App\Entity\Species; use Symfony\Bridge\Doctrine\Form\Type\EntityType; use Symfony\Component\Form\AbstractType; +use Symfony\Component\Form\Extension\Core\Type\DateTimeType; use Symfony\Component\Form\FormBuilderInterface; use Symfony\Component\OptionsResolver\OptionsResolver; use Symfony\Component\Form\Extension\Core\Type\SubmitType; @@ -15,8 +16,9 @@ class PostType extends AbstractType public function buildForm(FormBuilderInterface $builder, array $options): void { $builder - ->add('foundDate', null, [ + ->add('foundDate', DateTimeType::class, [ 'widget' => 'single_text', + 'empty_data' => null, ]) ->add('latitude') ->add('longitude') diff --git a/templates/species/index.html.twig b/templates/species/index.html.twig deleted file mode 100644 index 3f56295..0000000 --- a/templates/species/index.html.twig +++ /dev/null @@ -1,20 +0,0 @@ -{% extends 'base.html.twig' %} - -{% block title %}Hello SpeciesController!{% endblock %} - -{% block body %} - - -
-

Hello {{ controller_name }}! ✅

- - This friendly message is coming from: -
    -
  • Your controller at /home/scratch/hupradier1/herbarium/src/Controller/SpeciesController.php
  • -
  • Your template at /home/scratch/hupradier1/herbarium/templates/species/index.html.twig
  • -
-
-{% endblock %} -- 2.36.3 From c806227de251f45633b2f4dd936350c6111d8951 Mon Sep 17 00:00:00 2001 From: Hugo PRADIER Date: Fri, 7 Jun 2024 15:24:29 +0200 Subject: [PATCH 07/11] ajout edit post --- src/Controller/PostController.php | 18 ++++++++++++++++++ templates/post/edit.html.twig | 15 +++++++++++++++ 2 files changed, 33 insertions(+) create mode 100644 templates/post/edit.html.twig diff --git a/src/Controller/PostController.php b/src/Controller/PostController.php index b0bc747..a6320a9 100644 --- a/src/Controller/PostController.php +++ b/src/Controller/PostController.php @@ -47,4 +47,22 @@ class PostController extends AbstractController 'form' => $form, //->createView(), ]); } + + #[Route('/posts/edit/{id}', name: 'app_edit_post')] + #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] + public function edit(Request $request, EntityManagerInterface $entityManager, Post $post): Response +{ + $form = $this->createForm(PostType::class, $post); + $form->handleRequest($request); + + if ($form->isSubmitted() && $form->isValid()) { + $entityManager->flush(); + + return $this->redirectToRoute('app_posts'); + } + + return $this->render('post/edit.html.twig', [ + 'form' => $form->createView(), + ]); +} } diff --git a/templates/post/edit.html.twig b/templates/post/edit.html.twig new file mode 100644 index 0000000..1c8e0bb --- /dev/null +++ b/templates/post/edit.html.twig @@ -0,0 +1,15 @@ +{% extends 'base.html.twig' %} + +{% block title %}Edit Post{% endblock %} + +{% block body %} +

Edit Post

+ + {{ form_start(form) }} + {{ form_widget(form) }} + + + {{ form_end(form) }} + + Back to posts +{% endblock %} \ No newline at end of file -- 2.36.3 From 541ec566d1e7e9fe30af846d9560f619f132dbcb Mon Sep 17 00:00:00 2001 From: clfreville2 Date: Fri, 7 Jun 2024 15:39:37 +0200 Subject: [PATCH 08/11] Reformat --- src/Controller/PostController.php | 25 ++++++++++++------------- src/Controller/SpeciesController.php | 2 +- 2 files changed, 13 insertions(+), 14 deletions(-) diff --git a/src/Controller/PostController.php b/src/Controller/PostController.php index a6320a9..79dbc44 100644 --- a/src/Controller/PostController.php +++ b/src/Controller/PostController.php @@ -32,7 +32,6 @@ class PostController extends AbstractController $form = $this->createForm(PostType::class, $post); $form->handleRequest($request); - //dd($form); if ($form->isSubmitted() && $form->isValid()) { $post = $form->getData(); $post->setPublicationDate(new \DateTimeImmutable("now")); @@ -44,25 +43,25 @@ class PostController extends AbstractController } return $this->render('post/post.html.twig', [ - 'form' => $form, //->createView(), + 'form' => $form, ]); } #[Route('/posts/edit/{id}', name: 'app_edit_post')] #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] public function edit(Request $request, EntityManagerInterface $entityManager, Post $post): Response -{ - $form = $this->createForm(PostType::class, $post); - $form->handleRequest($request); + { + $form = $this->createForm(PostType::class, $post); + $form->handleRequest($request); - if ($form->isSubmitted() && $form->isValid()) { - $entityManager->flush(); + if ($form->isSubmitted() && $form->isValid()) { + $entityManager->flush(); - return $this->redirectToRoute('app_posts'); - } + return $this->redirectToRoute('app_posts'); + } - return $this->render('post/edit.html.twig', [ - 'form' => $form->createView(), - ]); -} + return $this->render('post/edit.html.twig', [ + 'form' => $form->createView(), + ]); + } } diff --git a/src/Controller/SpeciesController.php b/src/Controller/SpeciesController.php index 1bf70ee..4a2b7c2 100644 --- a/src/Controller/SpeciesController.php +++ b/src/Controller/SpeciesController.php @@ -5,10 +5,10 @@ namespace App\Controller; use Symfony\Bundle\FrameworkBundle\Controller\AbstractController; use Symfony\Component\HttpFoundation\Request; use Symfony\Component\HttpFoundation\Response; -use Symfony\Component\Routing\Annotation\Route; use App\Entity\Species; use App\Form\SpeciesType; use Doctrine\ORM\EntityManagerInterface; +use Symfony\Component\Routing\Attribute\Route; use Symfony\Component\Security\Http\Attribute\IsGranted; class SpeciesController extends AbstractController -- 2.36.3 From b7a750604a54c75b431ddd988de9eeb1e826f880 Mon Sep 17 00:00:00 2001 From: bastien ollier Date: Fri, 7 Jun 2024 15:54:49 +0200 Subject: [PATCH 09/11] update form --- src/Controller/PostController.php | 60 ++++++--- src/Controller/SpeciesController.php | 69 ++++++++-- src/Form/PostType.php | 7 +- src/Form/SpeciesType.php | 3 +- templates/post/_delete_form.html.twig | 4 + templates/post/_form.html.twig | 4 + templates/post/edit.html.twig | 10 +- templates/post/index.html.twig | 46 ++++++- templates/post/new.html.twig | 11 ++ templates/post/post.html.twig | 3 - templates/post/show.html.twig | 46 +++++++ templates/species/_delete_form.html.twig | 4 + templates/species/_form.html.twig | 4 + templates/species/edit.html.twig | 13 ++ templates/species/index.html.twig | 39 ++++++ templates/species/new.html.twig | 11 ++ templates/species/show.html.twig | 34 +++++ templates/species/species.html.twig | 3 - tests/Controller/PostControllerTest.php | 142 +++++++++++++++++++++ tests/Controller/SpeciesControllerTest.php | 124 ++++++++++++++++++ 20 files changed, 581 insertions(+), 56 deletions(-) create mode 100644 templates/post/_delete_form.html.twig create mode 100644 templates/post/_form.html.twig create mode 100644 templates/post/new.html.twig delete mode 100644 templates/post/post.html.twig create mode 100644 templates/post/show.html.twig create mode 100644 templates/species/_delete_form.html.twig create mode 100644 templates/species/_form.html.twig create mode 100644 templates/species/edit.html.twig create mode 100644 templates/species/index.html.twig create mode 100644 templates/species/new.html.twig create mode 100644 templates/species/show.html.twig delete mode 100644 templates/species/species.html.twig create mode 100644 tests/Controller/PostControllerTest.php create mode 100644 tests/Controller/SpeciesControllerTest.php diff --git a/src/Controller/PostController.php b/src/Controller/PostController.php index 79dbc44..484a494 100644 --- a/src/Controller/PostController.php +++ b/src/Controller/PostController.php @@ -2,66 +2,86 @@ namespace App\Controller; +use App\Entity\Post; +use App\Form\PostType; use App\Repository\PostRepository; +use Doctrine\ORM\EntityManagerInterface; use Symfony\Bundle\FrameworkBundle\Controller\AbstractController; -use Symfony\Component\Routing\Attribute\Route; use Symfony\Component\HttpFoundation\Request; use Symfony\Component\HttpFoundation\Response; -use App\Entity\Post; -use App\Form\PostType; -use Doctrine\ORM\EntityManagerInterface; +use Symfony\Component\Routing\Attribute\Route; use Symfony\Component\Security\Http\Attribute\IsGranted; +#[Route('/post')] class PostController extends AbstractController { - #[Route('/', name: 'app_posts')] - public function index(PostRepository $repository): Response + #[Route('/', name: 'app_post_index', methods: ['GET'])] + public function index(PostRepository $postRepository): Response { - $posts = $repository->findAll(); return $this->render('post/index.html.twig', [ - 'posts' => $posts, + 'posts' => $postRepository->findAll(), ]); } - #[Route('/posts/add', name: 'app_add_posts')] + #[Route('/new', name: 'app_post_new', methods: ['GET', 'POST'])] #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] public function new(Request $request, EntityManagerInterface $entityManager): Response { $post = new Post(); - $form = $this->createForm(PostType::class, $post); - $form->handleRequest($request); + if ($form->isSubmitted() && $form->isValid()) { - $post = $form->getData(); - $post->setPublicationDate(new \DateTimeImmutable("now")); - $entityManager->persist($post); $entityManager->flush(); - return $this->redirectToRoute('app_add_posts'); + return $this->redirectToRoute('app_post_index', [], Response::HTTP_SEE_OTHER); } - return $this->render('post/post.html.twig', [ + return $this->render('post/new.html.twig', [ + 'post' => $post, 'form' => $form, ]); } - #[Route('/posts/edit/{id}', name: 'app_edit_post')] + #[Route('/{id}', name: 'app_post_show', methods: ['GET'])] + public function show(Post $post): Response + { + return $this->render('post/show.html.twig', [ + 'post' => $post, + ]); + } + + #[Route('/{id}/edit', name: 'app_post_edit', methods: ['GET', 'POST'])] #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] - public function edit(Request $request, EntityManagerInterface $entityManager, Post $post): Response + public function edit(Request $request, Post $post, EntityManagerInterface $entityManager): Response { $form = $this->createForm(PostType::class, $post); $form->handleRequest($request); + if ($form->isSubmitted() && $form->isValid()) { + $entityManager->flush(); if ($form->isSubmitted() && $form->isValid()) { $entityManager->flush(); - return $this->redirectToRoute('app_posts'); + return $this->redirectToRoute('app_post_index', [], Response::HTTP_SEE_OTHER); } return $this->render('post/edit.html.twig', [ - 'form' => $form->createView(), + 'post' => $post, + 'form' => $form, ]); } + + #[Route('/{id}', name: 'app_post_delete', methods: ['POST'])] + #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] + public function delete(Request $request, Post $post, EntityManagerInterface $entityManager): Response + { + if ($this->isCsrfTokenValid('delete'.$post->getId(), $request->getPayload()->get('_token'))) { + $entityManager->remove($post); + $entityManager->flush(); + } + + return $this->redirectToRoute('app_post_index', [], Response::HTTP_SEE_OTHER); + } } diff --git a/src/Controller/SpeciesController.php b/src/Controller/SpeciesController.php index 4a2b7c2..4e5d4cf 100644 --- a/src/Controller/SpeciesController.php +++ b/src/Controller/SpeciesController.php @@ -2,37 +2,84 @@ namespace App\Controller; -use Symfony\Bundle\FrameworkBundle\Controller\AbstractController; -use Symfony\Component\HttpFoundation\Request; -use Symfony\Component\HttpFoundation\Response; use App\Entity\Species; use App\Form\SpeciesType; +use App\Repository\SpeciesRepository; use Doctrine\ORM\EntityManagerInterface; +use Symfony\Bundle\FrameworkBundle\Controller\AbstractController; +use Symfony\Component\HttpFoundation\Request; +use Symfony\Component\HttpFoundation\Response; use Symfony\Component\Routing\Attribute\Route; use Symfony\Component\Security\Http\Attribute\IsGranted; +#[Route('/species')] class SpeciesController extends AbstractController { - #[Route('/species/add', name: 'app_add_species')] + #[Route('/', name: 'app_species_index', methods: ['GET'])] + public function index(SpeciesRepository $speciesRepository): Response + { + return $this->render('species/index.html.twig', [ + 'species' => $speciesRepository->findAll(), + ]); + } + + #[Route('/new', name: 'app_species_new', methods: ['GET', 'POST'])] #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] public function new(Request $request, EntityManagerInterface $entityManager): Response { $species = new Species(); $form = $this->createForm(SpeciesType::class, $species); - $form->handleRequest($request); - if ($form->isSubmitted() && $form->isValid()) { - $species = $form->getData(); - + if ($form->isSubmitted() && $form->isValid()) { $entityManager->persist($species); $entityManager->flush(); - return $this->redirectToRoute('app_add_species'); + return $this->redirectToRoute('app_species_index', [], Response::HTTP_SEE_OTHER); } - return $this->render('species/species.html.twig', [ - 'form' => $form->createView(), + return $this->render('species/new.html.twig', [ + 'species' => $species, + 'form' => $form, ]); } + + #[Route('/{id}', name: 'app_species_show', methods: ['GET'])] + public function show(Species $species): Response + { + return $this->render('species/show.html.twig', [ + 'species' => $species, + ]); + } + + #[Route('/{id}/edit', name: 'app_species_edit', methods: ['GET', 'POST'])] + #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] + public function edit(Request $request, Species $species, EntityManagerInterface $entityManager): Response + { + $form = $this->createForm(SpeciesType::class, $species); + $form->handleRequest($request); + + if ($form->isSubmitted() && $form->isValid()) { + $entityManager->flush(); + + return $this->redirectToRoute('app_species_index', [], Response::HTTP_SEE_OTHER); + } + + return $this->render('species/edit.html.twig', [ + 'species' => $species, + 'form' => $form, + ]); + } + + #[Route('/{id}', name: 'app_species_delete', methods: ['POST'])] + #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] + public function delete(Request $request, Species $species, EntityManagerInterface $entityManager): Response + { + if ($this->isCsrfTokenValid('delete'.$species->getId(), $request->getPayload()->get('_token'))) { + $entityManager->remove($species); + $entityManager->flush(); + } + + return $this->redirectToRoute('app_species_index', [], Response::HTTP_SEE_OTHER); + } } diff --git a/src/Form/PostType.php b/src/Form/PostType.php index ceaff2c..bea7e6f 100644 --- a/src/Form/PostType.php +++ b/src/Form/PostType.php @@ -6,19 +6,16 @@ use App\Entity\Post; use App\Entity\Species; use Symfony\Bridge\Doctrine\Form\Type\EntityType; use Symfony\Component\Form\AbstractType; -use Symfony\Component\Form\Extension\Core\Type\DateTimeType; use Symfony\Component\Form\FormBuilderInterface; use Symfony\Component\OptionsResolver\OptionsResolver; -use Symfony\Component\Form\Extension\Core\Type\SubmitType; class PostType extends AbstractType { public function buildForm(FormBuilderInterface $builder, array $options): void { $builder - ->add('foundDate', DateTimeType::class, [ + ->add('foundDate', null, [ 'widget' => 'single_text', - 'empty_data' => null, ]) ->add('latitude') ->add('longitude') @@ -28,7 +25,7 @@ class PostType extends AbstractType 'class' => Species::class, 'choice_label' => 'scientific_name', ]) - ->add('save', SubmitType::class, ['label' => 'Create Post']); + ; } diff --git a/src/Form/SpeciesType.php b/src/Form/SpeciesType.php index 0d6cab9..ae3b919 100644 --- a/src/Form/SpeciesType.php +++ b/src/Form/SpeciesType.php @@ -6,7 +6,6 @@ use App\Entity\Species; use Symfony\Component\Form\AbstractType; use Symfony\Component\Form\FormBuilderInterface; use Symfony\Component\OptionsResolver\OptionsResolver; -use Symfony\Component\Form\Extension\Core\Type\SubmitType; class SpeciesType extends AbstractType { @@ -16,7 +15,7 @@ class SpeciesType extends AbstractType ->add('scientific_name') ->add('vernacular_name') ->add('region') - ->add('save', SubmitType::class, ['label' => 'Create Species']); + ; } public function configureOptions(OptionsResolver $resolver): void diff --git a/templates/post/_delete_form.html.twig b/templates/post/_delete_form.html.twig new file mode 100644 index 0000000..1223c9b --- /dev/null +++ b/templates/post/_delete_form.html.twig @@ -0,0 +1,4 @@ +
+ + +
diff --git a/templates/post/_form.html.twig b/templates/post/_form.html.twig new file mode 100644 index 0000000..bf20b98 --- /dev/null +++ b/templates/post/_form.html.twig @@ -0,0 +1,4 @@ +{{ form_start(form) }} + {{ form_widget(form) }} + +{{ form_end(form) }} diff --git a/templates/post/edit.html.twig b/templates/post/edit.html.twig index 1c8e0bb..16b6b5f 100644 --- a/templates/post/edit.html.twig +++ b/templates/post/edit.html.twig @@ -5,11 +5,9 @@ {% block body %}

Edit Post

- {{ form_start(form) }} - {{ form_widget(form) }} + {{ include('post/_form.html.twig', {'button_label': 'Update'}) }} - - {{ form_end(form) }} + back to list - Back to posts -{% endblock %} \ No newline at end of file + {{ include('post/_delete_form.html.twig') }} +{% endblock %} diff --git a/templates/post/index.html.twig b/templates/post/index.html.twig index 94f3756..49ca738 100644 --- a/templates/post/index.html.twig +++ b/templates/post/index.html.twig @@ -1,11 +1,45 @@ {% extends 'base.html.twig' %} -{% block title %}Posts!{% endblock %} +{% block title %}Post index{% endblock %} {% block body %} -{% for post in posts %} -
- #{{ post.id }} trouvé le {{ post.foundDate | date("d/m/Y \\à H \\h") }} -
-{% endfor %} +

Post index

+ + + + + + + + + + + + + + + + {% for post in posts %} + + + + + + + + + + + {% else %} + + + + {% endfor %} + +
IdFoundDatePublicationDateLatitudeLongitudeAltitudeCommentaryactions
{{ post.id }}{{ post.foundDate ? post.foundDate|date('Y-m-d H:i:s') : '' }}{{ post.publicationDate ? post.publicationDate|date('Y-m-d H:i:s') : '' }}{{ post.latitude }}{{ post.longitude }}{{ post.altitude }}{{ post.commentary }} + show + edit +
no records found
+ + Create new {% endblock %} diff --git a/templates/post/new.html.twig b/templates/post/new.html.twig new file mode 100644 index 0000000..b8bc236 --- /dev/null +++ b/templates/post/new.html.twig @@ -0,0 +1,11 @@ +{% extends 'base.html.twig' %} + +{% block title %}New Post{% endblock %} + +{% block body %} +

Create new Post

+ + {{ include('post/_form.html.twig') }} + + back to list +{% endblock %} diff --git a/templates/post/post.html.twig b/templates/post/post.html.twig deleted file mode 100644 index 2727393..0000000 --- a/templates/post/post.html.twig +++ /dev/null @@ -1,3 +0,0 @@ -{{ form_start(form, {'attr': {'novalidate': 'novalidate'}}) }} - {{ form_widget(form) }} -{{ form_end(form) }} diff --git a/templates/post/show.html.twig b/templates/post/show.html.twig new file mode 100644 index 0000000..a332dba --- /dev/null +++ b/templates/post/show.html.twig @@ -0,0 +1,46 @@ +{% extends 'base.html.twig' %} + +{% block title %}Post{% endblock %} + +{% block body %} +

Post

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Id{{ post.id }}
FoundDate{{ post.foundDate ? post.foundDate|date('Y-m-d H:i:s') : '' }}
PublicationDate{{ post.publicationDate ? post.publicationDate|date('Y-m-d H:i:s') : '' }}
Latitude{{ post.latitude }}
Longitude{{ post.longitude }}
Altitude{{ post.altitude }}
Commentary{{ post.commentary }}
+ + back to list + + edit + + {{ include('post/_delete_form.html.twig') }} +{% endblock %} diff --git a/templates/species/_delete_form.html.twig b/templates/species/_delete_form.html.twig new file mode 100644 index 0000000..9e7c05a --- /dev/null +++ b/templates/species/_delete_form.html.twig @@ -0,0 +1,4 @@ +
+ + +
diff --git a/templates/species/_form.html.twig b/templates/species/_form.html.twig new file mode 100644 index 0000000..bf20b98 --- /dev/null +++ b/templates/species/_form.html.twig @@ -0,0 +1,4 @@ +{{ form_start(form) }} + {{ form_widget(form) }} + +{{ form_end(form) }} diff --git a/templates/species/edit.html.twig b/templates/species/edit.html.twig new file mode 100644 index 0000000..8e4401b --- /dev/null +++ b/templates/species/edit.html.twig @@ -0,0 +1,13 @@ +{% extends 'base.html.twig' %} + +{% block title %}Edit Species{% endblock %} + +{% block body %} +

Edit Species

+ + {{ include('species/_form.html.twig', {'button_label': 'Update'}) }} + + back to list + + {{ include('species/_delete_form.html.twig') }} +{% endblock %} diff --git a/templates/species/index.html.twig b/templates/species/index.html.twig new file mode 100644 index 0000000..39c0d06 --- /dev/null +++ b/templates/species/index.html.twig @@ -0,0 +1,39 @@ +{% extends 'base.html.twig' %} + +{% block title %}Species index{% endblock %} + +{% block body %} +

Species index

+ + + + + + + + + + + + + {% for species in species %} + + + + + + + + {% else %} + + + + {% endfor %} + +
IdScientific_nameVernacular_nameRegionactions
{{ species.id }}{{ species.scientificName }}{{ species.vernacularName }}{{ species.region }} + show + edit +
no records found
+ + Create new +{% endblock %} diff --git a/templates/species/new.html.twig b/templates/species/new.html.twig new file mode 100644 index 0000000..8e58597 --- /dev/null +++ b/templates/species/new.html.twig @@ -0,0 +1,11 @@ +{% extends 'base.html.twig' %} + +{% block title %}New Species{% endblock %} + +{% block body %} +

Create new Species

+ + {{ include('species/_form.html.twig') }} + + back to list +{% endblock %} diff --git a/templates/species/show.html.twig b/templates/species/show.html.twig new file mode 100644 index 0000000..d0b5a78 --- /dev/null +++ b/templates/species/show.html.twig @@ -0,0 +1,34 @@ +{% extends 'base.html.twig' %} + +{% block title %}Species{% endblock %} + +{% block body %} +

Species

+ + + + + + + + + + + + + + + + + + + + +
Id{{ species.id }}
Scientific_name{{ species.scientificName }}
Vernacular_name{{ species.vernacularName }}
Region{{ species.region }}
+ + back to list + + edit + + {{ include('species/_delete_form.html.twig') }} +{% endblock %} diff --git a/templates/species/species.html.twig b/templates/species/species.html.twig deleted file mode 100644 index 2727393..0000000 --- a/templates/species/species.html.twig +++ /dev/null @@ -1,3 +0,0 @@ -{{ form_start(form, {'attr': {'novalidate': 'novalidate'}}) }} - {{ form_widget(form) }} -{{ form_end(form) }} diff --git a/tests/Controller/PostControllerTest.php b/tests/Controller/PostControllerTest.php new file mode 100644 index 0000000..a94c010 --- /dev/null +++ b/tests/Controller/PostControllerTest.php @@ -0,0 +1,142 @@ +client = static::createClient(); + $this->manager = static::getContainer()->get('doctrine')->getManager(); + $this->repository = $this->manager->getRepository(Post::class); + + foreach ($this->repository->findAll() as $object) { + $this->manager->remove($object); + } + + $this->manager->flush(); + } + + public function testIndex(): void + { + $crawler = $this->client->request('GET', $this->path); + + self::assertResponseStatusCodeSame(200); + self::assertPageTitleContains('Post index'); + + // Use the $crawler to perform additional assertions e.g. + // self::assertSame('Some text on the page', $crawler->filter('.p')->first()); + } + + public function testNew(): void + { + $this->markTestIncomplete(); + $this->client->request('GET', sprintf('%snew', $this->path)); + + self::assertResponseStatusCodeSame(200); + + $this->client->submitForm('Save', [ + 'post[foundDate]' => 'Testing', + 'post[latitude]' => 'Testing', + 'post[longitude]' => 'Testing', + 'post[altitude]' => 'Testing', + 'post[commentary]' => 'Testing', + 'post[species]' => 'Testing', + ]); + + self::assertResponseRedirects($this->path); + + self::assertSame(1, $this->repository->count([])); + } + + public function testShow(): void + { + $this->markTestIncomplete(); + $fixture = new Post(); + $fixture->setFoundDate('My Title'); + $fixture->setLatitude('My Title'); + $fixture->setLongitude('My Title'); + $fixture->setAltitude('My Title'); + $fixture->setCommentary('My Title'); + $fixture->setSpecies('My Title'); + + $this->manager->persist($fixture); + $this->manager->flush(); + + $this->client->request('GET', sprintf('%s%s', $this->path, $fixture->getId())); + + self::assertResponseStatusCodeSame(200); + self::assertPageTitleContains('Post'); + + // Use assertions to check that the properties are properly displayed. + } + + public function testEdit(): void + { + $this->markTestIncomplete(); + $fixture = new Post(); + $fixture->setFoundDate('Value'); + $fixture->setLatitude('Value'); + $fixture->setLongitude('Value'); + $fixture->setAltitude('Value'); + $fixture->setCommentary('Value'); + $fixture->setSpecies('Value'); + + $this->manager->persist($fixture); + $this->manager->flush(); + + $this->client->request('GET', sprintf('%s%s/edit', $this->path, $fixture->getId())); + + $this->client->submitForm('Update', [ + 'post[foundDate]' => 'Something New', + 'post[latitude]' => 'Something New', + 'post[longitude]' => 'Something New', + 'post[altitude]' => 'Something New', + 'post[commentary]' => 'Something New', + 'post[species]' => 'Something New', + ]); + + self::assertResponseRedirects('/post/'); + + $fixture = $this->repository->findAll(); + + self::assertSame('Something New', $fixture[0]->getFoundDate()); + self::assertSame('Something New', $fixture[0]->getLatitude()); + self::assertSame('Something New', $fixture[0]->getLongitude()); + self::assertSame('Something New', $fixture[0]->getAltitude()); + self::assertSame('Something New', $fixture[0]->getCommentary()); + self::assertSame('Something New', $fixture[0]->getSpecies()); + } + + public function testRemove(): void + { + $this->markTestIncomplete(); + $fixture = new Post(); + $fixture->setFoundDate('Value'); + $fixture->setLatitude('Value'); + $fixture->setLongitude('Value'); + $fixture->setAltitude('Value'); + $fixture->setCommentary('Value'); + $fixture->setSpecies('Value'); + + $this->manager->persist($fixture); + $this->manager->flush(); + + $this->client->request('GET', sprintf('%s%s', $this->path, $fixture->getId())); + $this->client->submitForm('Delete'); + + self::assertResponseRedirects('/post/'); + self::assertSame(0, $this->repository->count([])); + } +} diff --git a/tests/Controller/SpeciesControllerTest.php b/tests/Controller/SpeciesControllerTest.php new file mode 100644 index 0000000..ef3289e --- /dev/null +++ b/tests/Controller/SpeciesControllerTest.php @@ -0,0 +1,124 @@ +client = static::createClient(); + $this->manager = static::getContainer()->get('doctrine')->getManager(); + $this->repository = $this->manager->getRepository(Species::class); + + foreach ($this->repository->findAll() as $object) { + $this->manager->remove($object); + } + + $this->manager->flush(); + } + + public function testIndex(): void + { + $crawler = $this->client->request('GET', $this->path); + + self::assertResponseStatusCodeSame(200); + self::assertPageTitleContains('Species index'); + + // Use the $crawler to perform additional assertions e.g. + // self::assertSame('Some text on the page', $crawler->filter('.p')->first()); + } + + public function testNew(): void + { + $this->markTestIncomplete(); + $this->client->request('GET', sprintf('%snew', $this->path)); + + self::assertResponseStatusCodeSame(200); + + $this->client->submitForm('Save', [ + 'species[scientific_name]' => 'Testing', + 'species[vernacular_name]' => 'Testing', + 'species[region]' => 'Testing', + ]); + + self::assertResponseRedirects($this->path); + + self::assertSame(1, $this->repository->count([])); + } + + public function testShow(): void + { + $this->markTestIncomplete(); + $fixture = new Species(); + $fixture->setScientific_name('My Title'); + $fixture->setVernacular_name('My Title'); + $fixture->setRegion('My Title'); + + $this->manager->persist($fixture); + $this->manager->flush(); + + $this->client->request('GET', sprintf('%s%s', $this->path, $fixture->getId())); + + self::assertResponseStatusCodeSame(200); + self::assertPageTitleContains('Species'); + + // Use assertions to check that the properties are properly displayed. + } + + public function testEdit(): void + { + $this->markTestIncomplete(); + $fixture = new Species(); + $fixture->setScientific_name('Value'); + $fixture->setVernacular_name('Value'); + $fixture->setRegion('Value'); + + $this->manager->persist($fixture); + $this->manager->flush(); + + $this->client->request('GET', sprintf('%s%s/edit', $this->path, $fixture->getId())); + + $this->client->submitForm('Update', [ + 'species[scientific_name]' => 'Something New', + 'species[vernacular_name]' => 'Something New', + 'species[region]' => 'Something New', + ]); + + self::assertResponseRedirects('/species/'); + + $fixture = $this->repository->findAll(); + + self::assertSame('Something New', $fixture[0]->getScientific_name()); + self::assertSame('Something New', $fixture[0]->getVernacular_name()); + self::assertSame('Something New', $fixture[0]->getRegion()); + } + + public function testRemove(): void + { + $this->markTestIncomplete(); + $fixture = new Species(); + $fixture->setScientific_name('Value'); + $fixture->setVernacular_name('Value'); + $fixture->setRegion('Value'); + + $this->manager->persist($fixture); + $this->manager->flush(); + + $this->client->request('GET', sprintf('%s%s', $this->path, $fixture->getId())); + $this->client->submitForm('Delete'); + + self::assertResponseRedirects('/species/'); + self::assertSame(0, $this->repository->count([])); + } +} -- 2.36.3 From 9afe77b4edc2d49a2171f3235d19893592e61205 Mon Sep 17 00:00:00 2001 From: bastien ollier Date: Fri, 7 Jun 2024 16:04:14 +0200 Subject: [PATCH 10/11] update PostController --- src/Controller/PostController.php | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/Controller/PostController.php b/src/Controller/PostController.php index 484a494..2c71a98 100644 --- a/src/Controller/PostController.php +++ b/src/Controller/PostController.php @@ -59,8 +59,6 @@ class PostController extends AbstractController $form = $this->createForm(PostType::class, $post); $form->handleRequest($request); - if ($form->isSubmitted() && $form->isValid()) { - $entityManager->flush(); if ($form->isSubmitted() && $form->isValid()) { $entityManager->flush(); -- 2.36.3 From 1dc528f269d9a536fcdf39d4354c241c8f891537 Mon Sep 17 00:00:00 2001 From: clfreville2 Date: Fri, 7 Jun 2024 17:30:57 +0200 Subject: [PATCH 11/11] Fix tests --- src/Controller/PostController.php | 8 +-- src/Controller/SpeciesController.php | 8 +-- src/DataFixtures/AppFixtures.php | 14 +++- src/Entity/Post.php | 9 +++ src/Repository/UserRepository.php | 10 +++ tests/Controller/PostControllerTest.php | 80 +++++++++------------- tests/Controller/SpeciesControllerTest.php | 35 ++++++---- 7 files changed, 93 insertions(+), 71 deletions(-) diff --git a/src/Controller/PostController.php b/src/Controller/PostController.php index 2c71a98..c8cdd5f 100644 --- a/src/Controller/PostController.php +++ b/src/Controller/PostController.php @@ -24,7 +24,7 @@ class PostController extends AbstractController } #[Route('/new', name: 'app_post_new', methods: ['GET', 'POST'])] - #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] + #[IsGranted('ROLE_USER')] public function new(Request $request, EntityManagerInterface $entityManager): Response { $post = new Post(); @@ -53,7 +53,7 @@ class PostController extends AbstractController } #[Route('/{id}/edit', name: 'app_post_edit', methods: ['GET', 'POST'])] - #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] + #[IsGranted('ROLE_USER')] public function edit(Request $request, Post $post, EntityManagerInterface $entityManager): Response { $form = $this->createForm(PostType::class, $post); @@ -72,10 +72,10 @@ class PostController extends AbstractController } #[Route('/{id}', name: 'app_post_delete', methods: ['POST'])] - #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] + #[IsGranted('ROLE_USER')] public function delete(Request $request, Post $post, EntityManagerInterface $entityManager): Response { - if ($this->isCsrfTokenValid('delete'.$post->getId(), $request->getPayload()->get('_token'))) { + if ($this->isCsrfTokenValid('delete'.$post->getId(), (string) $request->getPayload()->get('_token'))) { $entityManager->remove($post); $entityManager->flush(); } diff --git a/src/Controller/SpeciesController.php b/src/Controller/SpeciesController.php index 4e5d4cf..b63b960 100644 --- a/src/Controller/SpeciesController.php +++ b/src/Controller/SpeciesController.php @@ -24,7 +24,7 @@ class SpeciesController extends AbstractController } #[Route('/new', name: 'app_species_new', methods: ['GET', 'POST'])] - #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] + #[IsGranted('ROLE_USER')] public function new(Request $request, EntityManagerInterface $entityManager): Response { $species = new Species(); @@ -53,7 +53,7 @@ class SpeciesController extends AbstractController } #[Route('/{id}/edit', name: 'app_species_edit', methods: ['GET', 'POST'])] - #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] + #[IsGranted('ROLE_USER')] public function edit(Request $request, Species $species, EntityManagerInterface $entityManager): Response { $form = $this->createForm(SpeciesType::class, $species); @@ -72,10 +72,10 @@ class SpeciesController extends AbstractController } #[Route('/{id}', name: 'app_species_delete', methods: ['POST'])] - #[IsGranted('ROLE_USER', message: 'You must be logged in to access this page.')] + #[IsGranted('ROLE_USER')] public function delete(Request $request, Species $species, EntityManagerInterface $entityManager): Response { - if ($this->isCsrfTokenValid('delete'.$species->getId(), $request->getPayload()->get('_token'))) { + if ($this->isCsrfTokenValid('delete'.$species->getId(), (string) $request->getPayload()->get('_token'))) { $entityManager->remove($species); $entityManager->flush(); } diff --git a/src/DataFixtures/AppFixtures.php b/src/DataFixtures/AppFixtures.php index 12d5f40..3b45990 100644 --- a/src/DataFixtures/AppFixtures.php +++ b/src/DataFixtures/AppFixtures.php @@ -4,17 +4,29 @@ namespace App\DataFixtures; use App\Entity\Post; use App\Entity\Species; +use App\Entity\User; use DateTimeImmutable; use Doctrine\Bundle\FixturesBundle\Fixture; use Doctrine\Persistence\ObjectManager; +use Symfony\Component\PasswordHasher\Hasher\UserPasswordHasherInterface; class AppFixtures extends Fixture { + public function __construct( + private readonly UserPasswordHasherInterface $passwordHasher + ) + { + } + public function load(ObjectManager $manager): void { + $user = (new User())->setEmail('test@test.fr'); + $user->setPassword($this->passwordHasher->hashPassword($user, 'password')); + $manager->persist($user); + $faker = \Faker\Factory::create(); for ($i = 0; $i < 20; ++$i) { - $name = $faker->text(); + $name = $faker->name(); $species = (new Species()) ->setScientificName($name) ->setVernacularName($name) diff --git a/src/Entity/Post.php b/src/Entity/Post.php index 21a5976..58f13d2 100644 --- a/src/Entity/Post.php +++ b/src/Entity/Post.php @@ -8,6 +8,7 @@ use Doctrine\ORM\Mapping as ORM; use Symfony\Component\Validator\Constraints as Assert; #[ORM\Entity(repositoryClass: PostRepository::class)] +#[ORM\HasLifecycleCallbacks] class Post { #[ORM\Id] @@ -128,4 +129,12 @@ class Post return $this; } + + #[ORM\PrePersist] + public function setPublicationDateValue(): void + { + if ($this->publicationDate === null) { + $this->publicationDate = new \DateTimeImmutable(); + } + } } diff --git a/src/Repository/UserRepository.php b/src/Repository/UserRepository.php index 4f2804e..e861224 100644 --- a/src/Repository/UserRepository.php +++ b/src/Repository/UserRepository.php @@ -33,6 +33,16 @@ class UserRepository extends ServiceEntityRepository implements PasswordUpgrader $this->getEntityManager()->flush(); } + public function findOneByEmail(string $email): ?User + { + return $this->createQueryBuilder('u') + ->andWhere('u.email = :email') + ->setParameter('email', $email) + ->getQuery() + ->getOneOrNullResult() + ; + } + // /** // * @return User[] Returns an array of User objects // */ diff --git a/tests/Controller/PostControllerTest.php b/tests/Controller/PostControllerTest.php index a94c010..ea52747 100644 --- a/tests/Controller/PostControllerTest.php +++ b/tests/Controller/PostControllerTest.php @@ -3,8 +3,9 @@ namespace App\Test\Controller; use App\Entity\Post; +use App\Entity\User; +use App\Repository\PostRepository; use Doctrine\ORM\EntityManagerInterface; -use Doctrine\ORM\EntityRepository; use Symfony\Bundle\FrameworkBundle\KernelBrowser; use Symfony\Bundle\FrameworkBundle\Test\WebTestCase; @@ -12,13 +13,15 @@ class PostControllerTest extends WebTestCase { private KernelBrowser $client; private EntityManagerInterface $manager; - private EntityRepository $repository; + private PostRepository $repository; private string $path = '/post/'; protected function setUp(): void { $this->client = static::createClient(); - $this->manager = static::getContainer()->get('doctrine')->getManager(); + /** @var EntityManagerInterface $manager */ + $manager = static::getContainer()->get(EntityManagerInterface::class); + $this->manager = $manager; $this->repository = $this->manager->getRepository(Post::class); foreach ($this->repository->findAll() as $object) { @@ -26,6 +29,12 @@ class PostControllerTest extends WebTestCase } $this->manager->flush(); + + $userRepository = $this->manager->getRepository(User::class); + /** @var User $user */ + $user = $userRepository->findOneByEmail('test@test.fr'); + $this->client->loginUser($user); + $this->client->request('GET', sprintf('%snew', $this->path)); } public function testIndex(): void @@ -41,35 +50,26 @@ class PostControllerTest extends WebTestCase public function testNew(): void { - $this->markTestIncomplete(); - $this->client->request('GET', sprintf('%snew', $this->path)); - self::assertResponseStatusCodeSame(200); $this->client->submitForm('Save', [ - 'post[foundDate]' => 'Testing', - 'post[latitude]' => 'Testing', - 'post[longitude]' => 'Testing', - 'post[altitude]' => 'Testing', + 'post[foundDate]' => '2024-01-01 00:00:00', + 'post[latitude]' => '45.0', + 'post[longitude]' => '45.0', + 'post[altitude]' => '500.0', 'post[commentary]' => 'Testing', - 'post[species]' => 'Testing', ]); self::assertResponseRedirects($this->path); - self::assertSame(1, $this->repository->count([])); + self::assertSame(1, $this->repository->count()); } public function testShow(): void { - $this->markTestIncomplete(); $fixture = new Post(); - $fixture->setFoundDate('My Title'); - $fixture->setLatitude('My Title'); - $fixture->setLongitude('My Title'); - $fixture->setAltitude('My Title'); - $fixture->setCommentary('My Title'); - $fixture->setSpecies('My Title'); + $fixture->setFoundDate(new \DateTimeImmutable('2024-01-01 00:00:00')); + $fixture->setCommentary('Cool stuff'); $this->manager->persist($fixture); $this->manager->flush(); @@ -77,21 +77,14 @@ class PostControllerTest extends WebTestCase $this->client->request('GET', sprintf('%s%s', $this->path, $fixture->getId())); self::assertResponseStatusCodeSame(200); - self::assertPageTitleContains('Post'); - - // Use assertions to check that the properties are properly displayed. + self::assertSelectorTextContains('h1', 'Post'); } public function testEdit(): void { - $this->markTestIncomplete(); $fixture = new Post(); - $fixture->setFoundDate('Value'); - $fixture->setLatitude('Value'); - $fixture->setLongitude('Value'); - $fixture->setAltitude('Value'); - $fixture->setCommentary('Value'); - $fixture->setSpecies('Value'); + $fixture->setFoundDate(new \DateTimeImmutable('2024-01-01 00:00:00')); + $fixture->setCommentary('Cool stuff'); $this->manager->persist($fixture); $this->manager->flush(); @@ -99,36 +92,29 @@ class PostControllerTest extends WebTestCase $this->client->request('GET', sprintf('%s%s/edit', $this->path, $fixture->getId())); $this->client->submitForm('Update', [ - 'post[foundDate]' => 'Something New', - 'post[latitude]' => 'Something New', - 'post[longitude]' => 'Something New', - 'post[altitude]' => 'Something New', + 'post[foundDate]' => '2024-03-25 00:00:00', + 'post[latitude]' => '90', + 'post[longitude]' => '90', + 'post[altitude]' => '200', 'post[commentary]' => 'Something New', - 'post[species]' => 'Something New', ]); self::assertResponseRedirects('/post/'); $fixture = $this->repository->findAll(); - self::assertSame('Something New', $fixture[0]->getFoundDate()); - self::assertSame('Something New', $fixture[0]->getLatitude()); - self::assertSame('Something New', $fixture[0]->getLongitude()); - self::assertSame('Something New', $fixture[0]->getAltitude()); + self::assertEquals(new \DateTimeImmutable('2024-03-25 00:00:00'), $fixture[0]->getFoundDate()); + self::assertSame(90., $fixture[0]->getLatitude()); + self::assertSame(90., $fixture[0]->getLongitude()); + self::assertSame(200., $fixture[0]->getAltitude()); self::assertSame('Something New', $fixture[0]->getCommentary()); - self::assertSame('Something New', $fixture[0]->getSpecies()); } public function testRemove(): void { - $this->markTestIncomplete(); $fixture = new Post(); - $fixture->setFoundDate('Value'); - $fixture->setLatitude('Value'); - $fixture->setLongitude('Value'); - $fixture->setAltitude('Value'); - $fixture->setCommentary('Value'); - $fixture->setSpecies('Value'); + $fixture->setFoundDate(new \DateTimeImmutable('2024-01-01 00:00:00')); + $fixture->setCommentary('Cool stuff'); $this->manager->persist($fixture); $this->manager->flush(); @@ -137,6 +123,6 @@ class PostControllerTest extends WebTestCase $this->client->submitForm('Delete'); self::assertResponseRedirects('/post/'); - self::assertSame(0, $this->repository->count([])); + self::assertSame(0, $this->repository->count()); } } diff --git a/tests/Controller/SpeciesControllerTest.php b/tests/Controller/SpeciesControllerTest.php index ef3289e..5ce80dd 100644 --- a/tests/Controller/SpeciesControllerTest.php +++ b/tests/Controller/SpeciesControllerTest.php @@ -3,8 +3,9 @@ namespace App\Test\Controller; use App\Entity\Species; +use App\Entity\User; +use App\Repository\SpeciesRepository; use Doctrine\ORM\EntityManagerInterface; -use Doctrine\ORM\EntityRepository; use Symfony\Bundle\FrameworkBundle\KernelBrowser; use Symfony\Bundle\FrameworkBundle\Test\WebTestCase; @@ -12,13 +13,15 @@ class SpeciesControllerTest extends WebTestCase { private KernelBrowser $client; private EntityManagerInterface $manager; - private EntityRepository $repository; + private SpeciesRepository $repository; private string $path = '/species/'; protected function setUp(): void { $this->client = static::createClient(); - $this->manager = static::getContainer()->get('doctrine')->getManager(); + /** @var EntityManagerInterface $manager */ + $manager = static::getContainer()->get(EntityManagerInterface::class); + $this->manager = $manager; $this->repository = $this->manager->getRepository(Species::class); foreach ($this->repository->findAll() as $object) { @@ -26,6 +29,12 @@ class SpeciesControllerTest extends WebTestCase } $this->manager->flush(); + + $userRepository = $this->manager->getRepository(User::class); + /** @var User $user */ + $user = $userRepository->findOneByEmail('test@test.fr'); + $this->client->loginUser($user); + $this->client->request('GET', sprintf('%snew', $this->path)); } public function testIndex(): void @@ -41,7 +50,6 @@ class SpeciesControllerTest extends WebTestCase public function testNew(): void { - $this->markTestIncomplete(); $this->client->request('GET', sprintf('%snew', $this->path)); self::assertResponseStatusCodeSame(200); @@ -59,10 +67,9 @@ class SpeciesControllerTest extends WebTestCase public function testShow(): void { - $this->markTestIncomplete(); $fixture = new Species(); - $fixture->setScientific_name('My Title'); - $fixture->setVernacular_name('My Title'); + $fixture->setScientificName('My Title'); + $fixture->setVernacularName('My Title'); $fixture->setRegion('My Title'); $this->manager->persist($fixture); @@ -78,10 +85,9 @@ class SpeciesControllerTest extends WebTestCase public function testEdit(): void { - $this->markTestIncomplete(); $fixture = new Species(); - $fixture->setScientific_name('Value'); - $fixture->setVernacular_name('Value'); + $fixture->setScientificName('Value'); + $fixture->setVernacularName('Value'); $fixture->setRegion('Value'); $this->manager->persist($fixture); @@ -99,17 +105,16 @@ class SpeciesControllerTest extends WebTestCase $fixture = $this->repository->findAll(); - self::assertSame('Something New', $fixture[0]->getScientific_name()); - self::assertSame('Something New', $fixture[0]->getVernacular_name()); + self::assertSame('Something New', $fixture[0]->getScientificName()); + self::assertSame('Something New', $fixture[0]->getVernacularName()); self::assertSame('Something New', $fixture[0]->getRegion()); } public function testRemove(): void { - $this->markTestIncomplete(); $fixture = new Species(); - $fixture->setScientific_name('Value'); - $fixture->setVernacular_name('Value'); + $fixture->setScientificName('Value'); + $fixture->setVernacularName('Value'); $fixture->setRegion('Value'); $this->manager->persist($fixture); -- 2.36.3