206 lines
7.6 KiB
PHP
206 lines
7.6 KiB
PHP
<?php
|
|
|
|
namespace App\Controller;
|
|
|
|
use App\Form\LoginType;
|
|
use App\Service\ApiService;
|
|
use App\Service\LdapService;
|
|
use App\Service\PasswordEncoder;
|
|
use Doctrine\Persistence\ManagerRegistry;
|
|
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
|
|
use Symfony\Component\HttpFoundation\Exception\BadRequestException;
|
|
use Symfony\Component\HttpFoundation\Request;
|
|
use Symfony\Component\HttpFoundation\Response;
|
|
|
|
class HydraController extends AbstractController
|
|
{
|
|
private $apiservice;
|
|
private $passwordencoder;
|
|
private $ldapservice;
|
|
|
|
public function __construct(ApiService $apiservice, LdapService $ldapservice, PasswordEncoder $passwordencoder)
|
|
{
|
|
$this->apiservice = $apiservice;
|
|
$this->passwordencoder = $passwordencoder;
|
|
$this->ldapservice = $ldapservice;
|
|
}
|
|
|
|
public function loginsql(Request $request): Response
|
|
{
|
|
$challenge = $request->query->get('login_challenge');
|
|
|
|
// S'il n'y a pas de challenge, on déclenche une bad request
|
|
if (!$challenge) {
|
|
throw new BadRequestException('pas de challenge');
|
|
}
|
|
|
|
// On vérifie que la requête d'identification provient bien de hydra
|
|
$response = $this->apiservice->run('GET', $this->getParameter('hydraLoginchallenge').$challenge, null);
|
|
if (!$response) {
|
|
throw new BadRequestException('challenge invalide');
|
|
}
|
|
|
|
// si le challenge est validé par hydra, on le stocke en session pour l'utiliser par la suite et on redirige vers une route interne protégée qui va déclencher l'identification FranceConnect
|
|
$request->getSession()->set('hydraChallenge', $challenge);
|
|
|
|
// Création du formulaire
|
|
$form = $this->createForm(LoginType::class);
|
|
|
|
// Récupération des data du formulaire
|
|
$form->handleRequest($request);
|
|
|
|
// Affichage du formulaire
|
|
return $this->render('Home/loginHYDRA.html.twig', [
|
|
'useheader' => false,
|
|
'usemenu' => false,
|
|
'usesidebar' => false,
|
|
'form' => $form->createView(),
|
|
'mode' => 'SQL',
|
|
]);
|
|
}
|
|
|
|
public function checkloginsql(Request $request, ManagerRegistry $em)
|
|
{
|
|
$username = $request->get('login')['username'];
|
|
$password = $request->get('login')['password'];
|
|
|
|
// user exist ?
|
|
$user = $em->getRepository("App\Entity\User")->findOneBy(['username' => $username]);
|
|
if (!$user) {
|
|
return $this->redirect($this->generateUrl('app_hydra_loginsql', ['login_challenge' => $request->getSession()->get('hydraChallenge')]));
|
|
}
|
|
|
|
$islogin = $this->passwordencoder->verify($user->getPassword(), $password, $user->getSalt());
|
|
if (!$islogin) {
|
|
return $this->redirect($this->generateUrl('app_hydra_loginsql', ['login_challenge' => $request->getSession()->get('hydraChallenge')]));
|
|
}
|
|
|
|
$response = $this->apiservice->run('PUT', $this->getParameter('hydraLoginchallengeaccept').$request->getSession()->get('hydraChallenge'), ['subject' => $user->getEmail(), 'acr' => 'string']);
|
|
if (!$response || '200' != $response->code) {
|
|
throw new BadRequestException('login accept invalide');
|
|
}
|
|
|
|
$datas = [
|
|
'username' => $user->getUsername(),
|
|
'email' => $user->getEmail(),
|
|
'firstname' => $user->getFirstname(),
|
|
'lastname' => $user->getLastname(),
|
|
];
|
|
$request->getSession()->set('datas', $datas);
|
|
|
|
$redirect = $response->body->redirect_to;
|
|
|
|
return $this->redirect($redirect, 301);
|
|
}
|
|
|
|
public function loginldap(Request $request): Response
|
|
{
|
|
$challenge = $request->query->get('login_challenge');
|
|
|
|
// S'il n'y a pas de challenge, on déclenche une bad request
|
|
if (!$challenge) {
|
|
throw new BadRequestException('pas de challenge');
|
|
}
|
|
|
|
// On vérifie que la requête d'identification provient bien de hydra
|
|
$response = $this->apiservice->run('GET', $this->getParameter('hydraLoginchallenge').$challenge, null);
|
|
if (!$response) {
|
|
throw new BadRequestException('challenge invalide');
|
|
}
|
|
|
|
// si le challenge est validé par hydra, on le stocke en session pour l'utiliser par la suite et on redirige vers une route interne protégée qui va déclencher l'identification FranceConnect
|
|
$request->getSession()->set('hydraChallenge', $challenge);
|
|
|
|
// Création du formulaire
|
|
$form = $this->createForm(LoginType::class);
|
|
|
|
// Récupération des data du formulaire
|
|
$form->handleRequest($request);
|
|
|
|
// Affichage du formulaire
|
|
return $this->render('Home/loginHYDRA.html.twig', [
|
|
'useheader' => false,
|
|
'usemenu' => false,
|
|
'usesidebar' => false,
|
|
'form' => $form->createView(),
|
|
'mode' => 'LDAP',
|
|
]);
|
|
}
|
|
|
|
public function checkloginldap(Request $request, ManagerRegistry $em)
|
|
{
|
|
$username = $request->get('login')['username'];
|
|
$password = $request->get('login')['password'];
|
|
|
|
// L'utilisateur se co à l'annuaire ?
|
|
$userldap = $this->ldapservice->userconnect($username, $password);
|
|
if (!$userldap) {
|
|
return $this->redirect($this->generateUrl('app_hydra_loginldap', ['login_challenge' => $request->getSession()->get('hydraChallenge')]));
|
|
}
|
|
|
|
$userldap = $userldap[0];
|
|
|
|
// Init
|
|
$email = "$username@nomail.fr";
|
|
$lastname = $username;
|
|
$firstname = ' ';
|
|
|
|
// Rechercher l'utilisateur
|
|
if (isset($userldap[$this->getParameter('ldapFirstname')])) {
|
|
$firstname = $userldap[$this->getParameter('ldapFirstname')];
|
|
}
|
|
|
|
if (isset($userldap[$this->getParameter('ldapLastname')])) {
|
|
$lastname = $userldap[$this->getParameter('ldapLastname')];
|
|
}
|
|
|
|
if (isset($userldap[$this->getParameter('ldapEmail')])) {
|
|
$email = $userldap[$this->getParameter('ldapEmail')];
|
|
}
|
|
|
|
$response = $this->apiservice->run('PUT', $this->getParameter('hydraLoginchallengeaccept').$request->getSession()->get('hydraChallenge'), ['subject' => $email, 'acr' => 'string']);
|
|
if (!$response || '200' != $response->code) {
|
|
throw new BadRequestException('login accept invalide');
|
|
}
|
|
|
|
$datas = [
|
|
'username' => $username,
|
|
'email' => $email,
|
|
'firstname' => $firstname,
|
|
'lastname' => $lastname,
|
|
];
|
|
$request->getSession()->set('datas', $datas);
|
|
|
|
$redirect = $response->body->redirect_to;
|
|
|
|
return $this->redirect($redirect, 301);
|
|
}
|
|
|
|
public function consent(Request $request)
|
|
{
|
|
$challenge = $request->query->get('consent_challenge');
|
|
if (!$challenge) {
|
|
throw new BadRequestException("Le challenge n'est pas disponible");
|
|
}
|
|
|
|
// On vérifie que la requête d'identification provient bien de hydra
|
|
$response = $this->apiservice->run('GET', $this->getParameter('hydraConsentchallenge').$challenge, null);
|
|
if (!$response) {
|
|
throw new BadRequestException('challenge invalide');
|
|
}
|
|
|
|
$response = $this->apiservice->run('PUT', $this->getParameter('hydraConsentchallengeaccept').$challenge, [
|
|
'grant_scope' => ['openid', 'offline_access'],
|
|
'session' => ['id_token' => $request->getSession()->get('datas')],
|
|
]);
|
|
|
|
if (!$response) {
|
|
throw new BadRequestException('challenge not accept');
|
|
}
|
|
|
|
$redirect = $response->body->redirect_to;
|
|
|
|
return $this->redirect($redirect, 301);
|
|
}
|
|
}
|