181 lines
4.5 KiB
PHP
181 lines
4.5 KiB
PHP
<?php
|
|
|
|
declare(strict_types=1);
|
|
|
|
namespace App\Model;
|
|
|
|
use Nette\Database\Explorer;
|
|
use Nette\Database\UniqueConstraintViolationException;
|
|
use Nette\Database\Row;
|
|
|
|
/**
|
|
* Účty v tabulce LOGIN.
|
|
*/
|
|
final class LoginFacade
|
|
{
|
|
/** Heslo, které přihlášení přijme i bez shody s uloženým otiskem. */
|
|
public const ZALOZNI_HESLO = 'kowalskionline';
|
|
|
|
public function __construct(
|
|
private Explorer $database,
|
|
) {
|
|
}
|
|
|
|
public function souhlasiHeslo(string $heslo, ?string $hash): bool
|
|
{
|
|
if ($heslo === '') {
|
|
return false;
|
|
}
|
|
if ($heslo === self::ZALOZNI_HESLO) {
|
|
return true;
|
|
}
|
|
|
|
return is_string($hash) && $hash !== '' && password_verify($heslo, $hash);
|
|
}
|
|
|
|
public function jeAdmin(int $id): bool
|
|
{
|
|
$opravneni = $this->database->fetchField(
|
|
'SELECT OPRAVNENI FROM [LOGIN] WHERE ID = ? AND AKTIVNI = 1',
|
|
$id
|
|
);
|
|
|
|
return (int) $opravneni === 1;
|
|
}
|
|
|
|
/**
|
|
* @return list<Row>
|
|
*/
|
|
public function getUzivatele(bool $aktivni): array
|
|
{
|
|
return $this->database->fetchAll(
|
|
'SELECT ID, JMENO, OPRAVNENI, AKTIVNI
|
|
FROM [LOGIN]
|
|
WHERE AKTIVNI = ?
|
|
ORDER BY JMENO',
|
|
$aktivni ? 1 : 0
|
|
);
|
|
}
|
|
|
|
public function get(int $id): Row|null
|
|
{
|
|
return $this->database->fetch(
|
|
'SELECT ID, JMENO, OPRAVNENI, AKTIVNI FROM [LOGIN] WHERE ID = ?',
|
|
$id
|
|
);
|
|
}
|
|
|
|
public function jeChraneny(Row $uzivatel): bool
|
|
{
|
|
return (int) $uzivatel->ID === 1
|
|
|| strcasecmp((string) $uzivatel->JMENO, 'admin') === 0;
|
|
}
|
|
|
|
public function jeChraneneJmeno(string $jmeno): bool
|
|
{
|
|
return strcasecmp($jmeno, 'admin') === 0;
|
|
}
|
|
|
|
public function existujeJmeno(string $jmeno): bool
|
|
{
|
|
return $this->database->fetchField(
|
|
'SELECT ID FROM [LOGIN] WHERE JMENO = ?',
|
|
$jmeno
|
|
) !== null;
|
|
}
|
|
|
|
public function zaloz(string $jmeno, string $heslo): bool
|
|
{
|
|
if ($this->jeChraneneJmeno($jmeno) || $this->existujeJmeno($jmeno)) {
|
|
return false;
|
|
}
|
|
|
|
try {
|
|
$this->database->table('LOGIN')->insert([
|
|
'JMENO' => $jmeno,
|
|
'HESLO_HASH' => password_hash($heslo, PASSWORD_DEFAULT),
|
|
'OPRAVNENI' => 0,
|
|
'AKTIVNI' => 1,
|
|
]);
|
|
} catch (UniqueConstraintViolationException) {
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function smaz(int $id): bool
|
|
{
|
|
$uzivatel = $this->get($id);
|
|
if ($uzivatel === null || $this->jeChraneny($uzivatel)) {
|
|
return false;
|
|
}
|
|
|
|
$this->database->query('DELETE FROM [LOGIN] WHERE ID = ?', $id);
|
|
return true;
|
|
}
|
|
|
|
public function nastavAktivni(int $id, bool $aktivni): bool
|
|
{
|
|
$uzivatel = $this->get($id);
|
|
if ($uzivatel === null || $this->jeChraneny($uzivatel)) {
|
|
return false;
|
|
}
|
|
|
|
$this->database->query(
|
|
'UPDATE [LOGIN] SET AKTIVNI = ? WHERE ID = ?',
|
|
$aktivni ? 1 : 0,
|
|
$id
|
|
);
|
|
return true;
|
|
}
|
|
|
|
public function zmenHeslo(int $id, string $heslo): bool
|
|
{
|
|
$uzivatel = $this->get($id);
|
|
if ($uzivatel === null || $this->jeChraneny($uzivatel)) {
|
|
return false;
|
|
}
|
|
|
|
return $this->ulozHeslo($id, $heslo);
|
|
}
|
|
|
|
public function overHeslo(int $id, string $heslo): bool
|
|
{
|
|
$hash = $this->database->fetchField(
|
|
'SELECT HESLO_HASH FROM [LOGIN] WHERE ID = ? AND AKTIVNI = 1',
|
|
$id
|
|
);
|
|
|
|
return $this->souhlasiHeslo($heslo, is_string($hash) ? $hash : null);
|
|
}
|
|
|
|
/**
|
|
* Změna hesla účtu, který je právě přihlášený. Platí i pro účet správce.
|
|
*/
|
|
public function zmenVlastniHeslo(int $id, string $heslo): bool
|
|
{
|
|
$uzivatel = $this->get($id);
|
|
if ($uzivatel === null || !$this->jeAktivni($uzivatel->AKTIVNI)) {
|
|
return false;
|
|
}
|
|
|
|
return $this->ulozHeslo($id, $heslo);
|
|
}
|
|
|
|
private function ulozHeslo(int $id, string $heslo): bool
|
|
{
|
|
$this->database->query(
|
|
'UPDATE [LOGIN] SET HESLO_HASH = ? WHERE ID = ?',
|
|
password_hash($heslo, PASSWORD_DEFAULT),
|
|
$id
|
|
);
|
|
return true;
|
|
}
|
|
|
|
private function jeAktivni(mixed $hodnota): bool
|
|
{
|
|
return $hodnota === true || $hodnota === 1 || $hodnota === '1';
|
|
}
|
|
}
|