Passed
Push — develop ( 7600ed...503338 )
by Enea
04:04
created

Authorizable::permissions()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 2
CRAP Score 1

Importance

Changes 0
Metric Value
cc 1
eloc 1
nc 1
nop 0
dl 0
loc 3
ccs 2
cts 2
cp 1
crap 1
rs 10
c 0
b 0
f 0
1
<?php
2
3
declare(strict_types=1);
4
5
/**
6
 * @author enea dhack <[email protected]>
7
 *
8
 * For the full copyright and license information, please view the LICENSE
9
 * file that was distributed with this source code.
10
 */
11
12
namespace Enea\Authorization\Traits;
13
14
use Closure;
15
use Enea\Authorization\Contracts\Grantable;
0 ignored issues
show
Bug introduced by
This use statement conflicts with another class in this namespace, Enea\Authorization\Traits\Grantable. Consider defining an alias.

Let?s assume that you have a directory layout like this:

.
|-- OtherDir
|   |-- Bar.php
|   `-- Foo.php
`-- SomeDir
    `-- Foo.php

and let?s assume the following content of Bar.php:

// Bar.php
namespace OtherDir;

use SomeDir\Foo; // This now conflicts the class OtherDir\Foo

If both files OtherDir/Foo.php and SomeDir/Foo.php are loaded in the same runtime, you will see a PHP error such as the following:

PHP Fatal error:  Cannot use SomeDir\Foo as Foo because the name is already in use in OtherDir/Foo.php

However, as OtherDir/Foo.php does not necessarily have to be loaded and the error is only triggered if it is loaded before OtherDir/Bar.php, this problem might go unnoticed for a while. In order to prevent this error from surfacing, you must import the namespace with a different alias:

// Bar.php
namespace OtherDir;

use SomeDir\Foo as SomeDirFoo; // There is no conflict anymore.
Loading history...
16
use Enea\Authorization\Contracts\PermissionContract;
17
use Enea\Authorization\Contracts\RoleContract;
18
use Enea\Authorization\Facades\Authorizer;
19
use Enea\Authorization\Facades\Granter;
20
use Enea\Authorization\Facades\Revoker;
21
use Enea\Authorization\Support\Config;
22
use Illuminate\Database\Eloquent\Collection as EloquentCollection;
23
use Illuminate\Database\Eloquent\Relations\BelongsToMany;
24
use Illuminate\Support\Collection;
25
26
/**
27
 * Trait Authorizable.
28
 *
29
 * @package Enea\Authorization\Traits
30
 *
31
 * @property EloquentCollection permissions
32
 * @property EloquentCollection roles
33
 */
34
trait Authorizable
35
{
36
    use Model;
37
38 45
    public function getIdentificationKey(): string
39
    {
40 45
        return (string) $this->getKey();
41
    }
42
43 20
    public function grant(Grantable $grantable): void
44
    {
45 20
        $this->grantMultiple([$grantable]);
46 20
    }
47
48
    public function grantMultiple(array $grantables): void
49
    {
50 36
        $this->operateOn(RoleContract::class, function (Collection $roles) {
51 19
            Granter::roles($this, $roles);
52 36
        }, $grantables);
53
54 36
        $this->operateOn(PermissionContract::class, function (Collection $permissions) {
55 17
            Granter::permissions($this, $permissions);
56 36
        }, $grantables);
57 36
    }
58
59 8
    public function revoke(Grantable $grantable): void
60
    {
61 8
        $this->revokeMultiple([$grantable]);
62 8
    }
63
64
    public function revokeMultiple(array $grantables): void
65
    {
66 10
        $this->operateOn(RoleContract::class, function (Collection $roles) {
67 5
            Revoker::roles($this, $roles);
68 10
        }, $grantables);
69
70 10
        $this->operateOn(PermissionContract::class, function (Collection $permissions) {
71 5
            Revoker::permissions($this, $permissions);
72 10
        }, $grantables);
73 10
    }
74
75 6
    public function can(string $permission): bool
76
    {
77 6
        return Authorizer::can($this, $permission);
78
    }
79
80 2
    public function cannot(string $permission): bool
81
    {
82 2
        return ! $this->can($permission);
83
    }
84
85 6
    public function isMemberOf(string $role): bool
86
    {
87 6
        return Authorizer::is($this, $role);
88
    }
89
90 2
    public function isntMemberOf(string $role): bool
91
    {
92 2
        return ! $this->isMemberOf($role);
93
    }
94
95 24
    public function permissions(): BelongsToMany
96
    {
97 24
        return $this->morphToMany(Config::permissionModel(), 'authorizable', Config::userPermissionTableName());
98
    }
99
100 43
    public function roles(): BelongsToMany
101
    {
102 43
        return $this->morphToMany(Config::roleModel(), 'authorizable', Config::userRoleTableName());
103
    }
104
105 1
    public function getPermissionModels(): EloquentCollection
106
    {
107 1
        return $this->permissions;
108
    }
109
110 1
    public function getRoleModels(): EloquentCollection
111
    {
112 1
        return $this->roles;
113
    }
114
115 36
    private function operateOn(string $contract, Closure $closure, array $grantables): void
116
    {
117 36
        $collection = $this->filterOnly($contract)($grantables);
118 36
        if (! $collection->isEmpty()) {
119 36
            $closure($collection);
120
        };
121 36
    }
122
123
    private function filterOnly(string $abstract): Closure
124
    {
125
        return function (array $grantables) use ($abstract): Collection {
126 36
            return collect($grantables)->filter(function (Grantable $grantable) use ($abstract) {
127 36
                return $grantable instanceof $abstract;
128 36
            });
129 36
        };
130
    }
131
}
132