GitHub Access Token became invalid

It seems like the GitHub access token used for retrieving details about this repository from GitHub became invalid. This might prevent certain types of inspections from being run (in particular, everything related to pull requests).
Please ask an admin of your repository to re-new the access token on this website.
Completed
Pull Request — 3.x (#93)
by Jindřich
02:11 queued 01:07
created

User   A

Complexity

Total Complexity 32

Size/Duplication

Total Lines 226
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 3

Test Coverage

Coverage 87.01%

Importance

Changes 0
Metric Value
dl 0
loc 226
ccs 67
cts 77
cp 0.8701
rs 9.84
c 0
b 0
f 0
wmc 32
lcom 1
cbo 3

15 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 9 3
A getLoginId() 0 4 1
A getRoleId() 0 4 1
A getUnitId() 0 4 1
A getLogoutDate() 0 4 1
A setLoginData() 0 10 1
A updateLoginData() 0 26 5
A resetLoginData() 0 7 1
A isLoggedIn() 0 16 6
A isAuthConfirmed() 0 4 1
A setAuthConfirmed() 0 5 1
A confirmAuth() 0 13 3
A updateLogoutTime() 0 17 2
A saveToSession() 0 6 2
A parseDate() 0 17 3
1
<?php
2
declare(strict_types = 1);
3
4
namespace Skaut\Skautis;
5
6
use DateTimeImmutable;
7
use DateTimeInterface;
8
use DateTimeZone;
9
use Skaut\Skautis\SessionAdapter\AdapterInterface;
10
use Skaut\Skautis\Wsdl\WebServiceName;
11
use Skaut\Skautis\Wsdl\WsdlManager;
12
13
/**
14
 * @author Petr Morávek <[email protected]>
15
 */
16
class User
17
{
18
19
    public const ID_LOGIN = 'ID_Login';
20
    public const ID_ROLE = 'ID_Role';
21
    public const ID_UNIT = 'ID_Unit';
22
    public const LOGOUT_DATE = 'LOGOUT_Date';
23
    private const AUTH_CONFIRMED = 'AUTH_Confirmed';
24
    private const SESSION_ID = 'skautis_user_data';
25
26
    /**
27
     * @var WsdlManager
28
     */
29
    private $wsdlManager;
30
31
    /**
32
     * @var AdapterInterface|null
33
     */
34
    private $session;
35
36
    /**
37
     * Informace o přihlášení uživatele
38
     *
39
     * @var array<string, mixed>
40
     */
41
    protected $loginData = [];
42
43
    /**
44
     * @param WsdlManager $wsdlManager
45
     * @param AdapterInterface|null $session
46
     */
47 7
    public function __construct(WsdlManager $wsdlManager, AdapterInterface $session = null)
48
    {
49 7
        $this->wsdlManager = $wsdlManager;
50 7
        $this->session = $session;
51
52 7
        if ($session !== null && $session->has(self::SESSION_ID)) {
53
            $this->loginData = (array)$session->get(self::SESSION_ID);
54
        }
55 7
    }
56
57 6
    public function getLoginId(): ?string
58
    {
59 6
        return $this->loginData[self::ID_LOGIN] ?? null;
60
    }
61
62 2
    public function getRoleId(): ?int
63
    {
64 2
        return $this->loginData[self::ID_ROLE] ?? null;
65
    }
66
67 2
    public function getUnitId(): ?int
68
    {
69 2
        return $this->loginData[self::ID_UNIT] ?? null;
70
    }
71
72
    /**
73
     * Vrací datum a čas automatického odhlášení ze skautISu
74
     */
75 3
    public function getLogoutDate(): ?DateTimeInterface
76
    {
77 3
        return $this->loginData[self::LOGOUT_DATE] ?? null;
78
    }
79
80
    /**+
81
     * Hromadné nastavení po přihlášení
82
     */
83 3
    public function setLoginData(
84
      string $loginId,
85
      ?int $roleId = null,
86
      ?int $unitId = null,
87
      ?DateTimeInterface $logoutDate = null
88
    ): self {
89 3
        $this->loginData = [];
90
91 3
        return $this->updateLoginData($loginId, $roleId, $unitId, $logoutDate);
92
    }
93
94
    /**
95
     * Hromadná změna údajů, bez vymazání stávajících
96
     */
97 3
    public function updateLoginData(
98
      ?string $loginId = null,
99
      ?int $roleId = null,
100
      ?int $unitId = null,
101
      ?DateTimeInterface $logoutDate = null
102
    ): self {
103 3
        if ($loginId !== null) {
104 3
            $this->loginData[self::ID_LOGIN] = $loginId;
105
        }
106
107 3
        if ($roleId !== null) {
108 3
            $this->loginData[self::ID_ROLE] = $roleId;
109
        }
110
111 3
        if ($unitId !== null) {
112 3
            $this->loginData[self::ID_UNIT] = $unitId;
113
        }
114
115 3
        if ($logoutDate !== null) {
116 3
            $this->loginData[self::LOGOUT_DATE] = $logoutDate;
117
        }
118
119 3
        $this->saveToSession();
120
121 3
        return $this;
122
    }
123
124
    /**
125
     * Hromadný reset dat po odhlášení
126
     */
127 1
    public function resetLoginData(): self
128
    {
129 1
        $this->loginData = [];
130 1
        $this->saveToSession();
131
132 1
        return $this;
133
    }
134
135
    /**
136
     * Kontoluje, jestli je přihlášení platné.
137
     * Pro správné fungování je nezbytně nutné, aby byl na serveru nastaven správný čas.
138
     *
139
     * @param bool $hardCheck vynutí kontrolu přihlášení na serveru
140
     */
141 3
    public function isLoggedIn(bool $hardCheck = false): bool
142
    {
143 3
        if (empty($this->loginData[self::ID_LOGIN])) {
144 2
            return false;
145
        }
146
147 1
        if ($hardCheck || !$this->isAuthConfirmed()) {
148 1
            $this->confirmAuth();
149
        }
150
151 1
        if ($this->getLogoutDate() === null) {
152
          return false;
153
        }
154
155 1
        return $this->isAuthConfirmed() && $this->getLogoutDate()->getTimestamp() > time();
156
    }
157
158
    /**
159
     * Bylo potvrzeno přihlášení dotazem na skautIS?
160
     */
161 1
    protected function isAuthConfirmed(): bool
162
    {
163 1
        return !empty($this->loginData[self::AUTH_CONFIRMED]);
164
    }
165
166 1
    protected function setAuthConfirmed(bool $isConfirmed): void
167
    {
168 1
        $this->loginData[self::AUTH_CONFIRMED] = $isConfirmed;
169 1
        $this->saveToSession();
170 1
    }
171
172
  /**
173
   * Potvrdí (a prodlouží) přihlášení dotazem na skautIS.
174
   *
175
   * @throws \Exception Pokud se authentikace nepovede
176
   */
177 1
    protected function confirmAuth(): void
178
    {
179
        try {
180 1
          $logoutTimeUpdated = $this->updateLogoutTime();
181 1
          if(!$logoutTimeUpdated) {
182
              throw new \RuntimeException('Updating logout time failed');
183
            }
184 1
            $this->setAuthConfirmed(true);
185
        } catch (\Exception $e) {
186
            $this->setAuthConfirmed(false);
187
            throw $e;
188
        }
189 1
    }
190
191
    /**
192
     * Prodloužení přihlášení o 30 min
193
     *
194
     * @throws UnexpectedValueException pokud se nepodaří naparsovat datum
195
     */
196 1
    public function updateLogoutTime(): bool
197
    {
198 1
        $loginId = $this->getLoginId();
199 1
        if ($loginId === null) {
200
            // Nemáme token, uživatel není přihlášen a není, co prodlužovat
201
            return false;
202
        }
203
204 1
        $result = $this->wsdlManager->getWebService(WebServiceName::USER_MANAGEMENT, $loginId)->LoginUpdateRefresh(['ID' => $loginId]);
205
206 1
        $logoutDate = $this->parseDate($result->DateLogout);
207 1
        $this->loginData[self::LOGOUT_DATE] = $logoutDate;
208
209 1
        $this->saveToSession();
210
211 1
        return true;
212
    }
213
214
    /**
215
     * Uloží nastavení do session
216
     */
217 3
    protected function saveToSession(): void
218
    {
219 3
        if ($this->session !== null) {
220
            $this->session->set(self::SESSION_ID, $this->loginData);
221
        }
222 3
    }
223
224 1
    private function parseDate(string $dateText): DateTimeInterface {
225
      //skautIS vrací sekundy včetně desetinné části
226 1
      $dateTextWithoutDecimals = preg_replace('/\.(\d*)$/', '', $dateText);
227
228 1
      if (!is_string($dateTextWithoutDecimals)) {
229
        throw new UnexpectedValueException("Could not parse date '$dateText'.");
230
      }
231
232 1
      $tz = new DateTimeZone('Europe/Prague');
233 1
      $dateTime =  DateTimeImmutable::createFromFormat('Y-m-d\TH:i:s', $dateTextWithoutDecimals, $tz);
234
235 1
      if ($dateTime === false) {
236
        throw new UnexpectedValueException("Could not parse date '$dateText'.");
237
      }
238
239 1
      return $dateTime;
240
    }
241
}
242