U authenticatoru se volá konstruktor stále tím i vkládaná fasáda

Upozornění: Tohle vlákno je hodně staré a informace nemusí být platné pro současné Nette.
Karlito
Člen | 18
+
0
-

Chci se zeptat, jak bych mohl vložit fasadu do authenticatoru, abych mohl v metodě authenticate pracovat s UserFacade, ale abych to nemusel vkládat jako závislost do konstruktoru. S tím to sice funguje, ale je to dost časově náročné protože authenticator se volá vždy a tím i závislosti na něj. Přijde mi to zbytečné, když authenticate je jen pro přihlášení, takže by stačilo kdyby se to načetlo jen při přihlášení.

class Authentication implements Nette\Security\IAuthenticator
{
	use Nette\SmartObject;

	/**
	 * Repozitář
	 * @var UserFacade userFacade
	 */
	private $userFacade;

	public function __construct(UserFacade $userFacade)
	{
		$this->userFacade = $userFacade;
	}

	/**
	 * Performs an authentication.
	 * @return Identity
	 * @throws AuthenticationException
	 */
	public function authenticate(array $credentials)
	{
		list($username, $password) = $credentials;

		$user = $this->userFacade->getUserByName($username);
		if (!$user) {
			throw new AuthenticationException('Uživatelské jméno je špatně zapsané.', self::IDENTITY_NOT_FOUND);

		} elseif (!Passwords::verify($password, $user->getPassword())) {
			throw new AuthenticationException('Heslo je špatně zapsané.', self::INVALID_CREDENTIAL);

		} elseif (Passwords::needsRehash($user->getPassword())) {
			$user->setPassword(Passwords::hash($password));
		}

		// uložení kdy byl naposled přihlášen
		$user->setLastSign(date("Y-m-d H:i:s", time()));

		return new Identity($user->getId(), $user->getRole(), $this->userFacade->getIdentityData($user));
	}
}

Je možné že to špatně používám. Mohli by jste mi poradit jak na to, nebo jak to třeba máte vy?
Používám Kdyby/doctrine mám entitu User a s ní komunikuji přes UserFacade.

David Matějka
Moderator | 6445
+
0
-

opravdu je to casove narocne? inicializace objektu by mela byt levna – v konstruktoru bys vetsinou mel pouze priradit predane parametry do clenskych promennych

Karlito
Člen | 18
+
0
-

No je možné, že to někde špatně používám, ale mám li úvodní stránku kde skoro nic není
tak první načtení je 3000–4500 ms a další z cache 190–230ms
Pokud smažu konstruktor pro předání fasády, tak první spuštění 750ms a další 90ms
Příjde mi to škoda, když authentizaci používám jen pro přihlášení a jen danou funkci.

Zde přiřazuji teda UserFacade kde mám v konstruktoru navázání EntityManageru a rovnou si tam tahám repozitář na uživatele

public function __construct(EntityManager $em)
{
	$this->em = $em;
	$this->repository = $em->getRepository(User::class);
}

EDIT
Tady bude asi problém to getRepository že? Teď nevím co je lepší, tohle mít v konstruktoru nebo si to rozházet do funkcí, nebo to hodit jako persistentní proměnnou, kterou nastavím jen v případě pokud nebude nastavena. Nebo nějaká rada?

Přišlo mi jednodušíí si to na začátku nahodit a pak to tahat už jen z repozitáře viz kod:

class UserFacade
{
	use Nette\SmartObject;

	/** @var EntityManager Manager pro práci s entitami. */
	private $em;

	private $repository;

	/**
	 * Konstruktor s injektovanou třídou pro práci s entitami.
	 * @param EntityManager $em automaticky injektovaná třída pro práci s entitami
	 */
	public function __construct(EntityManager $em)
	{
		$this->em = $em;
		$this->repository = $em->getRepository(User::class);
	}

	/**
	 * Najde a vrátí uživatele podle jeho ID.
	 * @param int|NULL $id ID uživatele
	 * @return User|NULL vrátí entitu uživatele nebo NULL pokud uživatel nebyl nalezen
	 */
	public function getUser($id)
	{
		return $this->repository->find($id);
	}

	public function getUsers()
	{
		return $this->repository->findAll();
	}

	public function getUserByName($username) {
		return $this->repository->findOneBy(['username' => $username]);
	}

	public function getUserByEmail($email) {
		return $this->repository->findOneBy(['email' => $email]);
	}

	/**
	 * Načtení nové identity
	 * @param $id
	 * @return Identity
	 */
	public function getIdentity($id) {
		$user = $this->getUser($id);
		/*
		$row = $this->database->table(self::TABLE_USERS)->where(self::COLUMN_ID, $id)->fetch();
		$arr = $row->toArray();
		unset($arr[self::COLUMN_PASSWORD]);
		*/

		return new Nette\Security\Identity($user->getId(), $user->getRole(), $this->getIdentityData($user));
	}
...

Editoval Karlito (26. 2. 2017 21:50)