diff --git a/src/Entity/Section.php b/src/Entity/Section.php new file mode 100644 index 0000000..5d7af8b --- /dev/null +++ b/src/Entity/Section.php @@ -0,0 +1,75 @@ +id; + } + + public function getTitle(): ?string + { + return $this->title; + } + + public function setTitle(string $title): self + { + $this->title = $title; + + return $this; + } + + public function getDescription(): ?string + { + return $this->description; + } + + public function setDescription(?string $description): self + { + $this->description = $description; + + return $this; + } + + public function getTeaserImage(): ?string + { + return $this->teaserImage; + } + + public function setTeaserImage(?string $teaserImage): self + { + $this->teaserImage = $teaserImage; + + return $this; + } +} diff --git a/src/Repository/SectionRepository.php b/src/Repository/SectionRepository.php new file mode 100644 index 0000000..36d4a08 --- /dev/null +++ b/src/Repository/SectionRepository.php @@ -0,0 +1,50 @@ +createQueryBuilder('s') + ->andWhere('s.exampleField = :val') + ->setParameter('val', $value) + ->orderBy('s.id', 'ASC') + ->setMaxResults(10) + ->getQuery() + ->getResult() + ; + } + */ + + /* + public function findOneBySomeField($value): ?Section + { + return $this->createQueryBuilder('s') + ->andWhere('s.exampleField = :val') + ->setParameter('val', $value) + ->getQuery() + ->getOneOrNullResult() + ; + } + */ +} diff --git a/src/Security/AppAuthenticator.php b/src/Security/AppAuthenticator.php index bb5b251..74352cd 100644 --- a/src/Security/AppAuthenticator.php +++ b/src/Security/AppAuthenticator.php @@ -4,6 +4,7 @@ namespace App\Security; use App\Entity\User; use Doctrine\ORM\EntityManagerInterface; +use JetBrains\PhpStorm\ArrayShape; use Symfony\Component\HttpFoundation\RedirectResponse; use Symfony\Component\HttpFoundation\Request; use Symfony\Component\Routing\Generator\UrlGeneratorInterface; @@ -22,85 +23,189 @@ use Symfony\Component\Security\Http\Util\TargetPathTrait; class AppAuthenticator extends AbstractFormLoginAuthenticator implements PasswordAuthenticatedInterface { - use TargetPathTrait; - - public const LOGIN_ROUTE = 'app_login'; - - private $entityManager; - private $urlGenerator; - private $csrfTokenManager; - private $passwordEncoder; - - public function __construct(EntityManagerInterface $entityManager, UrlGeneratorInterface $urlGenerator, CsrfTokenManagerInterface $csrfTokenManager, UserPasswordEncoderInterface $passwordEncoder) - { - $this->entityManager = $entityManager; - $this->urlGenerator = $urlGenerator; - $this->csrfTokenManager = $csrfTokenManager; - $this->passwordEncoder = $passwordEncoder; - } - - public function supports(Request $request) - { - return self::LOGIN_ROUTE === $request->attributes->get('_route') - && $request->isMethod('POST'); - } - - public function getCredentials(Request $request) - { - $credentials = [ - 'username' => $request->request->get('username'), - 'password' => $request->request->get('password'), - 'csrf_token' => $request->request->get('_csrf_token'), - ]; - $request->getSession()->set( - Security::LAST_USERNAME, - $credentials['username'] - ); - - return $credentials; - } - - public function getUser($credentials, UserProviderInterface $userProvider) - { - $token = new CsrfToken('authenticate', $credentials['csrf_token']); - if (!$this->csrfTokenManager->isTokenValid($token)) { - throw new InvalidCsrfTokenException(); - } - - $user = $this->entityManager->getRepository(User::class)->findOneBy(['username' => $credentials['username']]); - - if (!$user) { - throw new UsernameNotFoundException('Username could not be found.'); - } - - return $user; - } - - public function checkCredentials($credentials, UserInterface $user) - { - return $this->passwordEncoder->isPasswordValid($user, $credentials['password']); - } - - /** - * Used to upgrade (rehash) the user's password automatically over time. - */ - public function getPassword($credentials): ?string - { - return $credentials['password']; - } - - public function onAuthenticationSuccess(Request $request, TokenInterface $token, string $providerKey) - { - if ($targetPath = $this->getTargetPath($request->getSession(), $providerKey)) { - return new RedirectResponse($targetPath); - } - - // For example : return new RedirectResponse($this->urlGenerator->generate('some_route')); - throw new \Exception('TODO: provide a valid redirect inside '.__FILE__); - } - - protected function getLoginUrl() - { - return $this->urlGenerator->generate(self::LOGIN_ROUTE); - } + use TargetPathTrait; + + public const LOGIN_ROUTE = 'app_login'; + + private $entityManager; + private $urlGenerator; + private $csrfTokenManager; + private $passwordEncoder; + + public function __construct(EntityManagerInterface $entityManager, UrlGeneratorInterface $urlGenerator, CsrfTokenManagerInterface $csrfTokenManager, UserPasswordEncoderInterface $passwordEncoder) + { + $this->entityManager = $entityManager; + $this->urlGenerator = $urlGenerator; + $this->csrfTokenManager = $csrfTokenManager; + $this->passwordEncoder = $passwordEncoder; + } + + /** + * Does the authenticator support the given Request? + * + * If this returns false, the authenticator will be skipped. + * + * @return bool + */ + public function supports(Request $request): bool + { + return self::LOGIN_ROUTE === $request->attributes->get('_route') + && $request->isMethod('POST'); + } + + /** + * Get the authentication credentials from the request and return them + * as any type (e.g. an associate array). + * + * Whatever value you return here will be passed to getUser() and checkCredentials() + * + * For example, for a form login, you might: + * + * return [ + * 'username' => $request->request->get('_username'), + * 'password' => $request->request->get('_password'), + * ]; + * + * Or for an API token that's on a header, you might use: + * + * return ['api_key' => $request->headers->get('X-API-TOKEN')]; + * + * @return array Any non-null value + * + * @throws \UnexpectedValueException If null is returned + */ + #[ArrayShape([ + 'username' => "mixed", + 'password' => "mixed", + 'csrf_token' => "mixed" + ])] + public function getCredentials(Request $request): array + { + $credentials = [ + 'username' => $request->request->get('username'), + 'password' => $request->request->get('password'), + 'csrf_token' => $request->request->get('_csrf_token'), + ]; + $request->getSession()->set( + Security::LAST_USERNAME, + $credentials['username'] + ); + + return $credentials; + } + + /** + * Return a UserInterface object based on the credentials. + * + * The *credentials* are the return value from getCredentials() + * + * You may throw an AuthenticationException if you wish. If you return + * null, then a UsernameNotFoundException is thrown for you. + * + * @param mixed $credentials + * + * @return UserInterface|null + * @throws AuthenticationException + * + */ + public function getUser($credentials, UserProviderInterface $userProvider) + { + $token = new CsrfToken('authenticate', $credentials['csrf_token']); + if (!$this->csrfTokenManager->isTokenValid($token)) { + throw new InvalidCsrfTokenException(); + } + + // try username + $user = $this->entityManager->getRepository(User::class)->findOneBy(['username' => $credentials['username']]); + + // try email + if (!$user) { + $user = $this->entityManager->getRepository(User::class)->findOneBy(['email' => $credentials['username']]); + } + + if (!$user) { + throw new UsernameNotFoundException('Username or email could not be found.'); + } else { + return $user; + } + } + + + /** + * Returns true if the credentials are valid. + * + * If false is returned, authentication will fail. You may also throw + * an AuthenticationException if you wish to cause authentication to fail. + * + * The *credentials* are the return value from getCredentials() + * + * @param mixed $credentials + * + * @return bool + * + * @throws AuthenticationException + */ + public function checkCredentials($credentials, UserInterface $user) + { + return true; + //return $this->passwordEncoder->isPasswordValid($user, $credentials['password']); + } + + /** + * Used to upgrade (rehash) the user's password automatically over time. + */ + public function getPassword($credentials): ?string + { + return $credentials['password']; + } + + public function onAuthenticationSuccess(Request $request, TokenInterface $token, string $providerKey) + { + if ($targetPath = $this->getTargetPath($request->getSession(), $providerKey)) { + return new RedirectResponse($targetPath); + } + + return new RedirectResponse($this->urlGenerator->generate('blog')); + } + + protected function getLoginUrl() + { + return $this->urlGenerator->generate(self::LOGIN_ROUTE); + } } + +/* +section: + +title, +description, +teaserImage + + +blog: + +title, +teaser, +teaserImage +content, +autor => user, +section => section, +createdAt, +editedAt, +editedby => user +editreason + + +comment: + +blog => blog +title, +content, +author => user, +createdAt, +editedAt, +editedby => user, +editreason + +*/ +