Completed
Push — master ( 0405f6...feac36 )
by Adrien
07:49
created

User::hasInsurance()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 0
Metric Value
cc 1
eloc 1
nc 1
nop 0
dl 0
loc 3
ccs 0
cts 2
cp 0
crap 2
rs 10
c 0
b 0
f 0
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Application\Model;
6
7
use Application\Api\Exception;
8
use Application\DBAL\Types\BillingTypeType;
9
use Application\DBAL\Types\RelationshipType;
10
use Application\ORM\Query\Filter\AclFilter;
11
use Application\Traits\HasAddress;
12
use Application\Traits\HasDoorAccess;
13
use Application\Traits\HasIban;
14
use Application\Traits\HasInternalRemarks;
15
use Application\Traits\HasRemarks;
16
use Cake\Chronos\Chronos;
17
use Cake\Chronos\Date;
18
use Doctrine\Common\Collections\ArrayCollection;
19
use Doctrine\Common\Collections\Collection;
20
use Doctrine\ORM\Mapping as ORM;
21
use GraphQL\Doctrine\Annotation as API;
22
23
/**
24
 * User
25
 *
26
 * @ORM\Entity(repositoryClass="Application\Repository\UserRepository")
27
 * @ORM\AssociationOverrides({
28
 *     @ORM\AssociationOverride(name="owner", inversedBy="users")
29
 * })
30
 */
31
class User extends AbstractModel
32
{
33
    const ROLE_ANONYMOUS = 'anonymous';
34
    const ROLE_BOOKING_ONLY = 'booking_only';
35
    const ROLE_INDIVIDUAL = 'individual';
36
    const ROLE_MEMBER = 'member';
37
    const ROLE_RESPONSIBLE = 'responsible';
38
    const ROLE_ADMINISTRATOR = 'administrator';
39
40
    const STATUS_INACTIVE = 'inactive';
41
    const STATUS_NEW = 'new';
42
    const STATUS_ACTIVE = 'active';
43
    const STATUS_ARCHIVED = 'archived';
44
45
    use HasDoorAccess;
46
    use HasRemarks;
47
    use HasInternalRemarks;
48
    use HasAddress;
49
    use HasIban;
50
51
    /**
52
     * @var User
53
     */
54
    private static $currentUser;
55
56
    /**
57
     * Set currently logged in user
58
     * WARNING: this method should only be called from \Application\Authentication\AuthenticationListener
59
     *
60
     * @param \Application\Model\User $user
61
     */
62 161
    public static function setCurrent(?self $user): void
63
    {
64 161
        self::$currentUser = $user;
65
66
        // Initalize ACL filter with current user if a logged in one exists
67 161
        _em()->getFilters()->getFilter(AclFilter::class)->setUser($user);
68 161
    }
69
70
    /**
71
     * Returns currently logged user or null
72
     *
73
     * @return null|self
74
     */
75 66
    public static function getCurrent(): ?self
76
    {
77 66
        return self::$currentUser;
78
    }
79
80
    /**
81
     * @var null|string
82
     *
83
     * @ORM\Column(type="string", length=50, nullable=true, unique=true)
84
     */
85
    private $login;
86
87
    /**
88
     * @var string
89
     * @ORM\Column(type="string", length=191)
90
     */
91
    private $firstName = '';
92
93
    /**
94
     * @var string
95
     * @ORM\Column(type="string", length=191)
96
     */
97
    private $lastName = '';
98
99
    /**
100
     * @var string
101
     *
102
     * @ORM\Column(type="string", length=255)
103
     */
104
    private $password = '';
105
106
    /**
107
     * @var null|string
108
     * @ORM\Column(type="string", length=191, nullable=true, unique=true)
109
     */
110
    private $email;
111
112
    /**
113
     * @var string
114
     * @ORM\Column(type="UserRole", options={"default" = User::ROLE_INDIVIDUAL})
115
     */
116
    private $role = self::ROLE_INDIVIDUAL;
117
118
    /**
119
     * @var string
120
     * @ORM\Column(type="UserStatus", options={"default" = User::STATUS_NEW})
121
     */
122
    private $status = self::STATUS_NEW;
123
124
    /**
125
     * @var null|Chronos
126
     * @ORM\Column(type="datetime", nullable=true)
127
     */
128
    private $lastLogin;
129
130
    /**
131
     * @var null|Chronos
132
     * @ORM\Column(type="datetime", nullable=true)
133
     */
134
    private $welcomeSessionDate;
135
136
    /**
137
     * @var int sex
138
     * @ORM\Column(type="smallint", options={"default" = 0}))
139
     */
140
    private $sex = 0;
141
142
    /**
143
     * @var string
144
     * @ORM\Column(type="string", length=25, options={"default" = ""})
145
     */
146
    private $phone = '';
147
148
    /**
149
     * @var string
150
     * @ORM\Column(type="string", length=25, options={"default" = ""})
151
     */
152
    private $mobilePhone = '';
153
154
    /**
155
     * @var string
156
     * @ORM\Column(type="string", length=25, options={"default" = ""})
157
     */
158
    private $swissSailing = '';
159
160
    /**
161
     * @var string
162
     * @ORM\Column(type="SwissSailingType", nullable=true)
163
     */
164
    private $swissSailingType;
165
166
    /**
167
     * @var string
168
     * @ORM\Column(type="SwissWindsurfType", nullable=true)
169
     */
170
    private $swissWindsurfType;
171
172
    /**
173
     * @var null|Date
174
     * @ORM\Column(type="date", nullable=true)
175
     */
176
    private $birthday;
177
178
    /**
179
     * @var bool
180
     * @ORM\Column(type="boolean", options={"default" = 0})
181
     */
182
    private $termsAgreement = false;
183
184
    /**
185
     * @var bool
186
     * @ORM\Column(type="boolean", options={"default" = 0})
187
     */
188
    private $hasInsurance = false;
189
190
    /**
191
     * @var bool
192
     * @ORM\Column(type="boolean", options={"default" = 0})
193
     */
194
    private $receivesNewsletter = false;
195
196
    /**
197
     * @var string
198
     * @ORM\Column(type="Relationship", options={"default" = RelationshipType::HOUSEHOLDER})
199
     */
200
    private $familyRelationship = RelationshipType::HOUSEHOLDER;
201
202
    /**
203
     * @var string
204
     * @ORM\Column(type="BillingType", options={"default" = BillingTypeType::ELECTRONIC})
205
     */
206
    private $billingType = BillingTypeType::ELECTRONIC;
207
208
    /**
209
     * @var null|string
210
     * @ORM\Column(type="string", length=32, nullable=true, unique=true)
211
     */
212
    private $token;
213
214
    /**
215
     * @var null|Chronos
216
     *
217
     * @ORM\Column(type="datetime", nullable=true)
218
     */
219
    private $tokenCreationDate;
220
221
    /**
222
     * @var Collection
223
     * @ORM\OneToMany(targetEntity="Booking", mappedBy="owner")
224
     */
225
    private $bookings;
226
227
    /**
228
     * @var Collection
229
     * @ORM\ManyToMany(targetEntity="License", mappedBy="users")
230
     */
231
    private $licenses;
232
233
    /**
234
     * @var Collection
235
     * @ORM\ManyToMany(targetEntity="UserTag", mappedBy="users")
236
     */
237
    private $userTags;
238
239
    /**
240
     * @var Collection
241
     * @ORM\OneToMany(targetEntity="Message", mappedBy="recipient")
242
     */
243
    private $messages;
244
245
    /**
246
     * There is actually 0 to 1 account, never more. And this is
247
     * enforced by DB unique constraints
248
     *
249
     * @var Collection
250
     * @ORM\OneToMany(targetEntity="Account", mappedBy="owner")
251
     */
252
    private $accounts;
253
254
    /**
255
     * @var Collection
256
     * @ORM\OneToMany(targetEntity="User", mappedBy="owner")
257
     */
258
    private $users;
259
260
    /**
261
     * Constructor
262
     *
263
     * @param string $role role for new user
264
     */
265 39
    public function __construct(string $role = self::ROLE_INDIVIDUAL)
266
    {
267 39
        $this->role = $role;
268 39
        $this->bookings = new ArrayCollection();
269 39
        $this->accounts = new ArrayCollection();
270 39
        $this->licenses = new ArrayCollection();
271 39
        $this->userTags = new ArrayCollection();
272 39
        $this->messages = new ArrayCollection();
273 39
        $this->users = new ArrayCollection();
274 39
    }
275
276
    /**
277
     * Set login (eg: johndoe)
278
     *
279
     * @API\Input(type="Login")
280
     *
281
     * @param string $login
282
     */
283 4
    public function setLogin(string $login): void
284
    {
285 4
        $this->login = $login;
286 4
    }
287
288
    /**
289
     * Get login (eg: johndoe)
290
     *
291
     * @API\Field(type="?Login")
292
     *
293
     * @return null|string
294
     */
295 11
    public function getLogin(): ?string
296
    {
297 11
        return $this->login;
298
    }
299
300
    /**
301
     * Hash and change the user password
302
     *
303
     * @param string $password
304
     */
305 6
    public function setPassword(string $password): void
306
    {
307
        // Ignore empty password that could be sent "by mistake" by the client
308
        // when agreeing to terms
309 6
        if ($password === '') {
310 1
            return;
311
        }
312
313 6
        $this->revokeToken();
314
315 6
        $this->password = password_hash($password, PASSWORD_DEFAULT);
316 6
    }
317
318
    /**
319
     * Returns the hashed password
320
     *
321
     * @API\Exclude
322
     *
323
     * @return string
324
     */
325 3
    public function getPassword(): string
326
    {
327 3
        return $this->password;
328
    }
329
330
    /**
331
     * Set first name
332
     *
333
     * @param string $firstName
334
     */
335 5
    public function setFirstName($firstName): void
336
    {
337 5
        $this->firstName = $firstName;
338 5
    }
339
340
    /**
341
     * Get first name
342
     *
343
     * @return string
344
     */
345 11
    public function getFirstName(): string
346
    {
347 11
        return (string) $this->firstName;
348
    }
349
350
    /**
351
     * Set last name
352
     *
353
     * @param string $lastName
354
     */
355 5
    public function setLastName($lastName): void
356
    {
357 5
        $this->lastName = $lastName;
358 5
    }
359
360
    /**
361
     * Get last name
362
     *
363
     * @return string
364
     */
365 6
    public function getLastName(): string
366
    {
367 6
        return (string) $this->lastName;
368
    }
369
370
    /**
371
     * Get full name
372
     *
373
     * @return string
374
     */
375 6
    public function getName(): string
376
    {
377 6
        return implode(' ', [$this->getFirstName(), $this->getLastName()]);
378
    }
379
380
    /**
381
     * Set email
382
     *
383
     * @API\Input(type="?Email")
384
     *
385
     * @param string $email
386
     */
387 5
    public function setEmail(string $email): void
388
    {
389 5
        $this->email = $email;
390 5
    }
391
392
    /**
393
     * Get email
394
     *
395
     * @API\Field(type="?Email")
396
     *
397
     * @return null|string
398
     */
399 15
    public function getEmail(): ?string
400
    {
401 15
        return $this->email;
402
    }
403
404
    /**
405
     * Returns whether the user is administrator and thus have can do anything.
406
     *
407
     * @API\Field(type="Application\Api\Enum\UserRoleType")
408
     */
409 76
    public function getRole(): string
410
    {
411 76
        return $this->role;
412
    }
413
414
    /**
415
     * Sets the user role
416
     *
417
     * The current user is allowed to promote another user up to the same role as himself. So
418
     * a Responsible can promote a Member to Responsible. Or an Admin can promote a Individual to Admin.
419
     *
420
     * But the current user is **not** allowed to demote a user who has a higher role than himself.
421
     * That means that a Responsible cannot demote an Admin to Individual.
422
     *
423
     * @param string $role
424
     */
425 7
    public function setRole(string $role): void
426
    {
427 7
        if ($role === $this->role) {
428 2
            return;
429
        }
430
431 5
        $currentRole = self::getCurrent() ? self::getCurrent()->getRole() : self::ROLE_ANONYMOUS;
432
        $orderedRoles = [
433 5
            self::ROLE_ANONYMOUS,
434 5
            self::ROLE_INDIVIDUAL,
435 5
            self::ROLE_MEMBER,
436 5
            self::ROLE_BOOKING_ONLY,
437 5
            self::ROLE_RESPONSIBLE,
438 5
            self::ROLE_ADMINISTRATOR,
439
        ];
440
441 5
        $newFound = false;
442 5
        $oldFound = false;
443 5
        foreach ($orderedRoles as $r) {
444 5
            if ($r === $this->role) {
445 3
                $oldFound = true;
446
            }
447 5
            if ($r === $role) {
448 2
                $newFound = true;
449
            }
450
451 5
            if ($r === $currentRole) {
452 5
                break;
453
            }
454
        }
455
456 5
        if (!$newFound || !$oldFound) {
457 3
            throw new Exception($currentRole . ' is not allowed to change role from ' . $this->role . ' to ' . $role);
458
        }
459
460 2
        $this->role = $role;
461 2
    }
462
463 7
    public function setOwner(self $owner = null): void
464
    {
465 7
        if ($owner && $owner !== $this) {
466 4
            if ($owner->getOwner() && $owner !== $owner->getOwner()) {
467 1
                throw new Exception('This user cannot be owned by a user who is himself owned by somebody else');
468
            }
469
470 4
            if ($this->users->count()) {
471 1
                throw new Exception('This user owns other users, so he cannot himself be owned by somebody else');
472
            }
473
        }
474
475 7
        if ($this->getOwner()) {
476 1
            $this->getOwner()->getEmail(); // Trigger lazy loading
477 1
            $this->getOwner()->users->removeElement($this);
478
        }
479
480 7
        parent::setOwner($owner);
481
482 7
        if ($this->getOwner()) {
483 5
            $this->getOwner()->getEmail(); // Trigger lazy loading
484 5
            $this->getOwner()->users->add($this);
485 5
            $this->setStatus($this->getOwner()->getStatus());
486
        }
487 7
    }
488
489
    /**
490
     * @API\Field(type="Application\Api\Enum\UserStatusType")
491
     *
492
     * @return string
493
     */
494 7
    public function getStatus(): string
495
    {
496 7
        return $this->status;
497
    }
498
499
    /**
500
     * @API\Input(type="Application\Api\Enum\UserStatusType")
501
     *
502
     * @param string $status
503
     */
504 14
    public function setStatus(string $status): void
505
    {
506 14
        $this->status = $status;
507 14
        $this->revokeToken();
508
509 14
        foreach ($this->users as $user) {
510 4
            if ($user !== $this) {
511 1
                $user->setStatus($status);
512
            }
513
        }
514 14
    }
515
516 1
    public function activate(): void
517
    {
518 1
        $this->role = self::ROLE_MEMBER; // Bypass security
519 1
        $this->setStatus(self::STATUS_ACTIVE);
520 1
    }
521
522
    /**
523
     * @return string
524
     */
525
    public function getPhone(): string
526
    {
527
        return $this->phone;
528
    }
529
530
    /**
531
     * @param string $phone
532
     */
533
    public function setPhone(string $phone): void
534
    {
535
        $this->phone = $phone;
536
    }
537
538
    /**
539
     * @return string
540
     */
541
    public function getMobilePhone(): string
542
    {
543
        return $this->mobilePhone;
544
    }
545
546
    /**
547
     * @param string $mobilePhone
548
     */
549
    public function setMobilePhone(string $mobilePhone): void
550
    {
551
        $this->mobilePhone = $mobilePhone;
552
    }
553
554
    /**
555
     * @return null|Date
556
     */
557
    public function getBirthday(): ?Date
558
    {
559
        return $this->birthday;
560
    }
561
562
    /**
563
     * @param null|Date $birthday
564
     */
565
    public function setBirthday(?Date $birthday): void
566
    {
567
        $this->birthday = $birthday;
568
    }
569
570
    /**
571
     * Get bookings
572
     *
573
     * @return Collection
574
     */
575 2
    public function getBookings(): Collection
576
    {
577 2
        return $this->bookings;
578
    }
579
580
    /**
581
     * Notify the user that it has a new booking.
582
     * This should only be called by Booking::setResponsible()
583
     *
584
     * @param Booking $booking
585
     */
586 8
    public function bookingAdded(Booking $booking): void
587
    {
588 8
        $this->bookings->add($booking);
589 8
    }
590
591
    /**
592
     * Notify the user that it has a booking was removed.
593
     * This should only be called by Booking::setResponsible()
594
     *
595
     * @param Booking $booking
596
     */
597 4
    public function bookingRemoved(Booking $booking): void
598
    {
599 4
        $this->bookings->removeElement($booking);
600 4
    }
601
602
    /**
603
     * @return Collection
604
     */
605 1
    public function getLicenses(): Collection
606
    {
607 1
        return $this->licenses;
608
    }
609
610
    /**
611
     * @return Collection
612
     */
613 1
    public function getUserTags(): Collection
614
    {
615 1
        return $this->userTags;
616
    }
617
618
    /**
619
     * Notify the user that it has a new license.
620
     * This should only be called by License::addUser()
621
     *
622
     * @param License $license
623
     */
624 1
    public function licenseAdded(License $license): void
625
    {
626 1
        $this->licenses->add($license);
627 1
    }
628
629
    /**
630
     * Notify the user that it a license was removed.
631
     * This should only be called by License::removeUser()
632
     *
633
     * @param License $license
634
     */
635 1
    public function licenseRemoved(License $license): void
636
    {
637 1
        $this->licenses->removeElement($license);
638 1
    }
639
640
    /**
641
     * Notify the user that it has a new userTag.
642
     * This should only be called by UserTag::addUser()
643
     *
644
     * @param UserTag $userTag
645
     */
646 1
    public function userTagAdded(UserTag $userTag): void
647
    {
648 1
        $this->userTags->add($userTag);
649 1
    }
650
651
    /**
652
     * Notify the user that a userTag was removed.
653
     * This should only be called by UserTag::removeUser()
654
     *
655
     * @param UserTag $userTag
656
     */
657 1
    public function userTagRemoved(UserTag $userTag): void
658
    {
659 1
        $this->userTags->removeElement($userTag);
660 1
    }
661
662
    /**
663
     * @return bool
664
     */
665
    public function isTermsAgreement(): bool
666
    {
667
        return $this->termsAgreement;
668
    }
669
670
    /**
671
     * @param bool $termsAgreement
672
     */
673 1
    public function setTermsAgreement(bool $termsAgreement): void
674
    {
675 1
        $this->termsAgreement = $termsAgreement;
676 1
    }
677
678
    /**
679
     * @return bool
680
     */
681
    public function hasInsurance(): bool
682
    {
683
        return $this->hasInsurance;
684
    }
685
686
    /**
687
     * @param bool $hasInsurance
688
     */
689 1
    public function setHasInsurance(bool $hasInsurance): void
690
    {
691 1
        $this->hasInsurance = $hasInsurance;
692 1
    }
693
694
    /**
695
     * @return null|Chronos
696
     */
697
    public function getWelcomeSessionDate(): ?Chronos
698
    {
699
        return $this->welcomeSessionDate;
700
    }
701
702
    /**
703
     * @param null|Chronos $welcomeSessionDate
704
     */
705
    public function setWelcomeSessionDate(?Chronos $welcomeSessionDate): void
706
    {
707
        $this->welcomeSessionDate = $welcomeSessionDate;
708
    }
709
710
    /**
711
     * @return bool
712
     */
713
    public function isReceivesNewsletter(): bool
714
    {
715
        return $this->receivesNewsletter;
716
    }
717
718
    /**
719
     * @param bool $receivesNewsletter
720
     */
721
    public function setReceivesNewsletter(bool $receivesNewsletter): void
722
    {
723
        $this->receivesNewsletter = $receivesNewsletter;
724
    }
725
726
    /**
727
     * Get the sex
728
     *
729
     * @API\Field(type="Sex")
730
     *
731
     * @return int
732
     */
733
    public function getSex(): int
734
    {
735
        return $this->sex;
736
    }
737
738
    /**
739
     * Set the sex
740
     *
741
     * @API\Input(type="Sex")
742
     *
743
     * @param int $sex
744
     */
745
    public function setSex(int $sex): void
746
    {
747
        $this->sex = $sex;
748
    }
749
750
    /**
751
     * Get the Swiss Sailing licence number
752
     *
753
     * @return string
754
     */
755
    public function getSwissSailing(): string
756
    {
757
        return $this->swissSailing;
758
    }
759
760
    /**
761
     * @param string $swissSailing
762
     */
763
    public function setSwissSailing(string $swissSailing): void
764
    {
765
        $this->swissSailing = $swissSailing;
766
    }
767
768
    /**
769
     * Get the Swiss Sailing licence type
770
     *
771
     * @API\Field(type="?SwissSailingType")
772
     *
773
     * @return null|string
774
     */
775
    public function getSwissSailingType(): ?string
776
    {
777
        return $this->swissSailingType;
778
    }
779
780
    /**
781
     * Set the Swiss Sailing licence type
782
     *
783
     * @API\Input(type="?SwissSailingType")
784
     *
785
     * @param null|string $swissSailingType
786
     */
787
    public function setSwissSailingType(?string $swissSailingType): void
788
    {
789
        $this->swissSailingType = $swissSailingType;
790
    }
791
792
    /**
793
     * Get the Swiss Windsurf licence type
794
     *
795
     * @API\Field(type="?SwissWindsurfType")
796
     *
797
     * @return null|string
798
     */
799
    public function getSwissWindsurfType(): ?string
800
    {
801
        return $this->swissWindsurfType;
802
    }
803
804
    /**
805
     * Set the Swiss Windsurf licence type
806
     *
807
     * @API\Input(type="?SwissWindsurfType")
808
     *
809
     * @param null|string $swissWindsurfType
810
     */
811
    public function setSwissWindsurfType(?string $swissWindsurfType): void
812
    {
813
        $this->swissWindsurfType = $swissWindsurfType;
814
    }
815
816
    /**
817
     * Get the last login
818
     *
819
     * @return null|Chronos
820
     */
821
    public function getLastLogin(): ?Chronos
822
    {
823
        return $this->lastLogin;
824
    }
825
826
    /**
827
     * @param null|Chronos $lastLogin
828
     */
829 3
    public function setLastLogin(?Chronos $lastLogin): void
830
    {
831 3
        $this->lastLogin = $lastLogin;
832 3
        $this->revokeToken();
833 3
    }
834
835
    /**
836
     * @API\Field(type="Relationship")
837
     *
838
     * @return string
839
     */
840 1
    public function getFamilyRelationship(): string
841
    {
842 1
        return $this->familyRelationship;
843
    }
844
845
    /**
846
     * @API\Input(type="Relationship")
847
     *
848
     * @param string $familyRelationship
849
     */
850 1
    public function setFamilyRelationship(string $familyRelationship): void
851
    {
852 1
        $this->familyRelationship = $familyRelationship;
853 1
    }
854
855
    /**
856
     * @API\Field(type="BillingType")
857
     *
858
     * @return string
859
     */
860
    public function getBillingType(): string
861
    {
862
        return $this->billingType;
863
    }
864
865
    /**
866
     * @API\Input(type="BillingType")
867
     *
868
     * @param string $billingType
869
     */
870
    public function setBillingType(string $billingType): void
871
    {
872
        $this->billingType = $billingType;
873
    }
874
875
    /**
876
     * Get the user transaction account
877
     *
878
     * @return null|Account
879
     */
880 7
    public function getAccount(): ?Account
881
    {
882 7
        return $this->accounts->count() ? $this->accounts->first() : null;
883
    }
884
885
    /**
886
     * Notify the user that it has a new account
887
     * This should only be called by Account::setOwner()
888
     *
889
     * @param Account $account
890
     */
891 7
    public function accountAdded(Account $account): void
892
    {
893 7
        $this->accounts->clear();
894 7
        $this->accounts->add($account);
895 7
    }
896
897
    /**
898
     * Notify the user that a account was removed
899
     * This should only be called by Account::setOwner()
900
     */
901 4
    public function accountRemoved(): void
902
    {
903 4
        $this->accounts->clear();
904 4
    }
905
906
    /**
907
     * Get messages sent to the user
908
     *
909
     * @return Collection
910
     */
911 1
    public function getMessages(): Collection
912
    {
913 1
        return $this->messages;
914
    }
915
916
    /**
917
     * Notify the user that it has a new message
918
     * This should only be called by Message::setRecipient()
919
     *
920
     * @param Message $message
921
     */
922 9
    public function messageAdded(Message $message): void
923
    {
924 9
        $this->messages->add($message);
925 9
    }
926
927
    /**
928
     * Notify the user that a message was removed
929
     * This should only be called by Message::setRecipient()
930
     *
931
     * @param Message $message
932
     */
933 1
    public function messageRemoved(Message $message): void
934
    {
935 1
        $this->messages->removeElement($message);
936 1
    }
937
938
    /**
939
     * Generate a new random token to reset password
940
     */
941 4
    public function createToken(): string
942
    {
943 4
        $this->token = bin2hex(random_bytes(16));
944 4
        $this->tokenCreationDate = new Chronos();
945
946 4
        return $this->token;
947
    }
948
949
    /**
950
     * Destroy existing token
951
     */
952 18
    private function revokeToken(): void
953
    {
954 18
        $this->token = null;
955 18
        $this->tokenCreationDate = null;
956 18
    }
957
958
    /**
959
     * Check if token is valid.
960
     *
961
     * @API\Exclude
962
     *
963
     * @return bool
964
     */
965 3
    public function isTokenValid(): bool
966
    {
967 3
        if (!$this->tokenCreationDate) {
968 1
            return false;
969
        }
970
971 3
        $timeLimit = $this->tokenCreationDate->addMinutes(30);
972
973 3
        return $timeLimit->isFuture();
974
    }
975
976
    /**
977
     * Check if the user can *really* open a door
978
     * This also takes into account the user status, role and IP address
979
     *
980
     * @API\Field(args={@API\Argument(name="door", type="?Application\Api\Enum\DoorType")})
981
     *
982
     * @param null|string $door a particular door, or null for any
983
     *
984
     * @return bool
985
     */
986 6
    public function getCanOpenDoor(?string $door = null): bool
987
    {
988 6
        $allowedStatus = [self::STATUS_ACTIVE];
989 6
        $allowedRoles = [self::ROLE_INDIVIDUAL, self::ROLE_MEMBER, self::ROLE_RESPONSIBLE, self::ROLE_ADMINISTRATOR];
990
991 6
        if ($door && !$this->$door) {
992 3
            return false;
993
        }
994
995 6
        if (!in_array($this->status, $allowedStatus, true) || !in_array($this->role, $allowedRoles, true)) {
996 2
            return false;
997
        }
998
999 4
        return true;
1000
    }
1001
}
1002