2013-08-29 17 views
6

Mam flagę na moich użytkownikach dla "aktywnych" i jeśli ustawiono na zero lub zero, nie zezwalam na logowanie.Symfony2 FOSUserBundle - Sprawdź poprawność przed flagą "użytkownika aktywnego" podczas logowania

Próbowałem kilka podejść i nie mam czasu.

Jeśli wykonuję trasę wylogowania, wiadomość flash nie jest zachowywana, więc użytkownik nic nie widzi.

Sprawdziłem, czy dodałem sprawdzanie poprawności w formularzu logowania, aby wygenerować normalny błąd formularza, gdyby flaga nie była ustawiona na wartość true, ale w tym folderze (sprzedawca/Pakiety/FOS/UserBundle/Form/Type) I nic nie znalazłem w formularzu logowania, tylko w rejestracji i tym podobnych, więc nie wiedziałbym, gdzie go umieścić ani skąd odziedziczyć, aby nadpisać.

Próbowałem też jak sugeruje tutaj, aby wylogować się ręcznie, ale zostawił mnie z biały ekran śmierci ...

Wszelkie sugestie, jak łatwo to osiągnąć?

** * ** * ** * ** * ** UPDATE ** * ** * ** * * **

Uświadomiłem sobie, że prawdopodobnie chcę do tego dodać walidator w formularzu logowania. Obecnie mam to zakodowane w kontrolerze pierwszej trasy, do której użytkownik jest wysyłany, ale to nie zapewni większego bezpieczeństwa, jeśli użytkownik wpisze trasę przed zalogowaniem, ponieważ po udanej próbie zalogowania, moja domyślna "strona docelowa" po logowanie nie będzie droga, że ​​użytkownik jest podjęta, ale będzie mu lądowania na trasie jego wybór ...

***Update ** * *

Plik konfiguracji usługi ma to ...

<service id="security.user_checker" class="%security.user_checker.class%" public="false" /> 

I że parametr jest zdefiniowany tu ...

<parameter key="security.user_checker.class">Symfony\Component\Security\Core\User\UserChecker</parameter> 

Więc w celu modyfikacji logiki logowania muszę zastąpić

Symfony\Component\Security\Core\User\UserChecker 

teraz mam zrobić, że nadrzędnymi ten parametr powyżej w moich własnych parameters.ini w aplikacji/konfiguracji tego symfony

security.user_checker.class = BizTV\UserBundle\Controller\UserChecker 

.. i dodałem tę kontrolę do mojego nadpisania userChecker ...

//Test for companylock... 
    if (!$user->getCompany()->getActive()) { 
     throw new LockedException('The company of this user is locked.', $user); 
    } 

Oto cały plik:

<?php 

/* 
* This file is part of the Symfony package. 
* 
* (c) Fabien Potencier <[email protected]> 
* 
* For the full copyright and license information, please view the LICENSE 
* file that was distributed with this source code. 
*/ 

//Override by Mattias 

namespace BizTV\UserBundle\Controller; 
//namespace Symfony\Component\Security\Core\User; 

use Symfony\Component\Security\Core\Exception\CredentialsExpiredException; 
use Symfony\Component\Security\Core\Exception\LockedException; 
use Symfony\Component\Security\Core\Exception\DisabledException; 
use Symfony\Component\Security\Core\Exception\AccountExpiredException; 

use Symfony\Component\Security\Core\User\UserInterface; 
use Symfony\Component\Security\Core\User\UserChecker as OriginalUserChecker; 

/** 
* UserChecker checks the user account flags. 
* 
* @author Fabien Potencier <[email protected]> 
*/ 
class UserChecker extends OriginalUserChecker 
{ 
    /** 
    * {@inheritdoc} 
    */ 
    public function checkPreAuth(UserInterface $user) 
    { 

    //Test for companylock... 
    if (!$user->getCompany()->getActive()) { 
     throw new LockedException('The company of this user is locked.', $user); 
    } 

     if (!$user instanceof AdvancedUserInterface) { 
      return; 
     } 

     if (!$user->isCredentialsNonExpired()) { 
      throw new CredentialsExpiredException('User credentials have expired.', $user); 
     } 


    } 

    /** 
    * {@inheritdoc} 
    */ 
    public function checkPostAuth(UserInterface $user) 
    { 

    //Test for companylock... 
    if (!$user->getCompany()->getActive()) { 
     throw new LockedException('The company of this user is locked.', $user); 
    } 

     if (!$user instanceof AdvancedUserInterface) { 
      return; 
     } 



     if (!$user->isAccountNonLocked()) { 
      throw new LockedException('User account is locked.', $user); 
     } 

     if (!$user->isEnabled()) { 
      throw new DisabledException('User account is disabled.', $user); 
     } 

     if (!$user->isAccountNonExpired()) { 
      throw new AccountExpiredException('User account has expired.', $user); 
     } 
    } 
} 

* Aktualizacja nb 3 * ** * **** Teraz mam tylko w lewo, aby go właściwie sprawdź standardową blokadę użytkownika, która nieoczekiwanie nie wychodzi z pudełka. (Dziękuję nifr za doprowadzenie mnie tak daleko!)

Moja jednostka użytkownika zaczyna się w ten sposób, i tak jak powiedział Nifr, muszę zaimplementować AdvancedUserInterface, ale prawdopodobnie nie jest to możliwe, ponieważ nadal nie działa sprawdzenia tego zamka ... ale to mi nie wyrzuca komunikat o błędzie, albo (jeśli zmienię je i umieścić implememts AdvancedUserInterface a następnie rozciąga baseUser zgłasza błąd, tak ...)

<?php 
// src/BizTV/UserBundle/Entity/User.php 

namespace BizTV\UserBundle\Entity; 

use BizTV\UserBundle\Validator\Constraints as BizTVAssert; 
use Symfony\Component\Security\Core\User\AdvancedUserInterface; 

use FOS\UserBundle\Entity\User as BaseUser; 
use Doctrine\ORM\Mapping as ORM; 

use BizTV\BackendBundle\Entity\company as company; 

/** 
* @ORM\Entity 
* @ORM\Table(name="fos_user") 
*/ 
class User extends BaseUser implements AdvancedUserInterface 
{ 

Nie wiem, czy to w jaki sposób robisz to, gdy zarówno rozszerzasz podstawowego użytkownika, jak i próbujesz implementować AdvancedUserInterface, kiedy zrobisz to jak powyżej, nadal nie mogę korzystać z funkcji, które powinienem dodać (ale nie wyśle ​​mi też żadnego komunikatu o błędzie), ale jeśli zmienię miejsca w EXTENDS i IMPLEMENTACJE takie jak ten (linia 18) ...

class User implements AdvancedUserInterface extends BaseUser 

... mam ten błąd:

Parse error: syntax error, unexpected T_EXTENDS, expecting '{' in /var/www/cloudsign/src/BizTV/UserBundle/Entity/User.php on line 18 

Odpowiedz

6

FOSUserBundle/Symfony ma już jakieś "aktywnego" flaga zintegrowanego.

FOS\UserBundle\Model\User zapewnia już właściwości "zablokowane" i "włączone", które są zasadniczo przeznaczone do tego celu. Różnica pomiędzy tymi dwoma właściwościami jest następujący (cytowanie @ Stof za komentarz here)

From the Security component point of view, there is no real difference: both are forbidden to log in. The difference is a semantic one: disabled users are generally users that need to activate their account (for instance, when you activate the need to confirm the email in FOSUserBundle, the user is disabled on creation and enabled on confirmation). On the other hand, locking a user is generally an action done by the admin of the site to ban a user. Using the same field in the database does not make sense as it would allow banned user to have access again by simply going through the confirmation process.

Czek dla jest prowadzone przez UserChecker Zamknięty/użytkowników niepełnosprawnych (Symfony dostarcza ten jeden jako @ security.user_checker) w FOSUserBundle na AuthenticationListener który implementuje Symfony\Component\Security\Core\User\UserCheckerInterface.

Teraz w celu przekierowania nieaktywna użytkownika na inną drogą byś:

  1. Catch the Symfony\Component\Security\Core\Exception\DisabledException w bloku try/catch w rozszerzonym AuthenticationListener
  2. przekierować użytkownika na określonej trasie, jeśli złapany wyjątek jest typu InactiveUserException

Opcjonalnie przenieś przekierowanie do nowo utworzonego obiektu EventListener/-Subscriber, który jest wysyłany w rozszerzonym uwierzytelnianiu uwierzytelniania. W ten sposób możesz później utworzyć dodatkowych Słuchaczy, np. Do celów rejestrowania i po prostu zasubskrybować je dla zdarzenia próby zalogowania się użytkownika nieaktywnego.

+0

Tak samo pakiet użytkownika fos używa userChecker znalezionego w rdzeniu symfony2? Pytam, ponieważ szukam w celu dodania czeku do funkcji checkPostAuth (mój użytkownik jest częścią grupy, która może być zablokowana, co z kolei ma zablokować wszystkich użytkowników w grupie bez umieszczania indywidualnej blokady na jednostce użytkownika). Tak więc $ user-> getGroup() -> getActive() jest tym, do czego sięga, aby go tam umieścić. Ale muszę znaleźć sposób na zastąpienie tego userChecker ... –

+1

Tak FOSUserBundle używa Symfony UserChecker - możesz użyć własnego sprawdzania użytkownika, zastępując usługę '@ security.user_checker' jeśli dobrze pamiętam. Po prostu wyszukaj tekst w pliku "UserChecker" w katalogu dostawcy, a znajdziesz plik xml zawierający odpowiednią definicję usługi. Następnie zastąp tę usługę. – nifr

+0

Jestem już blisko ... Czy mógłbyś rzucić okiem na moje zaktualizowane pytanie, może wiesz, czego mi brakuje, aby ominąć te komunikaty o błędach =) –

Powiązane problemy