Completed
Pull Request — master (#23)
by ARCANEDEV
08:07
created

Role::users()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 12
Code Lines 9

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 8
CRAP Score 1

Importance

Changes 0
Metric Value
dl 0
loc 12
c 0
b 0
f 0
ccs 8
cts 8
cp 1
rs 9.4285
cc 1
eloc 9
nc 1
nop 0
crap 1
1
<?php namespace Arcanedev\LaravelAuth\Models;
2
3
use Arcanedev\LaravelAuth\Bases\Model;
4
use Arcanedev\LaravelAuth\Models\Traits\Activatable;
5
use Arcanesoft\Contracts\Auth\Models\Permission as PermissionContract;
6
use Arcanesoft\Contracts\Auth\Models\Role as RoleContract;
7
use Illuminate\Database\Eloquent\Model as Eloquent;
8
use Illuminate\Support\Str;
9
10
/**
11
 * Class     Role
12
 *
13
 * @package  Arcanedev\LaravelAuth\Models
14
 * @author   ARCANEDEV <[email protected]>
15
 *
16
 * @property  int                                       id
17
 * @property  string                                    name
18
 * @property  string                                    slug
19
 * @property  string                                    description
20
 * @property  bool                                      is_active
21
 * @property  bool                                      is_locked
22
 * @property  \Carbon\Carbon                            created_at
23
 * @property  \Carbon\Carbon                            updated_at
24
 *
25
 * @property  \Illuminate\Database\Eloquent\Collection       users
26
 * @property  \Illuminate\Database\Eloquent\Collection       permissions
27
 * @property  \Arcanedev\LaravelAuth\Models\Pivots\RoleUser  pivot
28
 */
29
class Role extends Model implements RoleContract
30
{
31
    /* ------------------------------------------------------------------------------------------------
32
     |  Traits
33
     | ------------------------------------------------------------------------------------------------
34
     */
35
    use Activatable;
36
37
    /* ------------------------------------------------------------------------------------------------
38
     |  Properties
39
     | ------------------------------------------------------------------------------------------------
40
     */
41
    /**
42
     * The attributes that are mass assignable.
43
     *
44
     * @var array
45
     */
46
    protected $fillable = ['name', 'slug', 'description'];
47
48
    /**
49
     * The attributes that should be casted to native types.
50
     *
51
     * @var array
52
     */
53
    protected $casts = [
54
        'is_active' => 'boolean',
55
        'is_locked' => 'boolean',
56
    ];
57
58
    /* ------------------------------------------------------------------------------------------------
59
     |  Constructor
60
     | ------------------------------------------------------------------------------------------------
61
     */
62
    /**
63
     * Create a new Eloquent model instance.
64
     *
65
     * @param  array  $attributes
66
     */
67 225
    public function __construct(array $attributes = [])
68
    {
69 225
        $this->setTable(config('laravel-auth.roles.table', 'roles'));
70
71 225
        parent::__construct($attributes);
72 225
    }
73
74
    /* ------------------------------------------------------------------------------------------------
75
     |  Relationships
76
     | ------------------------------------------------------------------------------------------------
77
     */
78
    /**
79
     * Role belongs to many users.
80
     *
81
     * @return \Illuminate\Database\Eloquent\Relations\BelongsToMany
82
     */
83 15
    public function users()
84
    {
85
        return $this
86 15
            ->belongsToMany(
87 15
                config('laravel-auth.users.model', User::class),
88 15
                config('laravel-auth.database.prefix').'role_user',
89 15
                'role_id',
90 15
                'user_id'
91
            )
92 15
            ->using(Pivots\RoleUser::class)
93 15
            ->withTimestamps();
94
    }
95
96
    /**
97
     * Role belongs to many permissions.
98
     *
99
     * @return \Illuminate\Database\Eloquent\Relations\BelongsToMany
100
     */
101 33
    public function permissions()
102
    {
103
        return $this
104 33
            ->belongsToMany(
105 33
                config('laravel-auth.permissions.model', Permission::class),
106 33
                config('laravel-auth.database.prefix').'permission_role',
107 33
                'role_id',
108 33
                'permission_id'
109
            )
110 33
            ->using(Pivots\PermissionRole::class)
111 33
            ->withTimestamps();
112
    }
113
114
    /* ------------------------------------------------------------------------------------------------
115
     |  Getters & Setters
116
     | ------------------------------------------------------------------------------------------------
117
     */
118
    /**
119
     * Set the name attribute.
120
     *
121
     * @param  string  $name
122
     */
123 90
    public function setNameAttribute($name)
124
    {
125 90
        $this->attributes['name'] = $name;
126 90
        $this->setSlugAttribute($name);
127 90
    }
128
129
    /**
130
     * Set the slug attribute.
131
     *
132
     * @param  string  $slug
133
     */
134 90
    public function setSlugAttribute($slug)
135
    {
136 90
        $this->attributes['slug'] = $this->slugify($slug);
137 90
    }
138
139
    /* ------------------------------------------------------------------------------------------------
140
     |  CRUD Functions
141
     | ------------------------------------------------------------------------------------------------
142
     */
143
    /**
144
     * Attach a permission to a role.
145
     *
146
     * @param  \Arcanesoft\Contracts\Auth\Models\User|int  $user
147
     * @param  bool                                        $reload
148
     */
149 9
    public function attachUser($user, $reload = true)
150
    {
151 9
        if ( ! $this->hasUser($user)) {
152 9
            $this->users()->attach($user);
153 9
            $this->loadUsers($reload);
154
        }
155 9
    }
156
157
    /**
158
     * Detach a user from a role.
159
     *
160
     * @param  \Arcanesoft\Contracts\Auth\Models\User|int  $user
161
     * @param  bool                                        $reload
162
     *
163
     * @return int
164
     */
165 3
    public function detachUser($user, $reload = true)
166
    {
167 3
        if ($user instanceof Eloquent)
0 ignored issues
show
Bug introduced by
The class Illuminate\Database\Eloquent\Model does not exist. Did you forget a USE statement, or did you not list all dependencies?

This error could be the result of:

1. Missing dependencies

PHP Analyzer uses your composer.json file (if available) to determine the dependencies of your project and to determine all the available classes and functions. It expects the composer.json to be in the root folder of your repository.

Are you sure this class is defined by one of your dependencies, or did you maybe not list a dependency in either the require or require-dev section?

2. Missing use statement

PHP does not complain about undefined classes in ìnstanceof checks. For example, the following PHP code will work perfectly fine:

if ($x instanceof DoesNotExist) {
    // Do something.
}

If you have not tested against this specific condition, such errors might go unnoticed.

Loading history...
168 3
            $user = (array) $user->getKey();
169
170 3
        $result = $this->users()->detach($user);
171 3
        $this->loadUsers($reload);
172
173 3
        return $result;
174
    }
175
176
    /**
177
     * Detach all users from a role.
178
     *
179
     * @param  bool  $reload
180
     *
181
     * @return int
182
     */
183 3
    public function detachAllUsers($reload = true)
184
    {
185 3
        $result = $this->users()->detach();
186 3
        $this->loadUsers($reload);
187
188 3
        return $result;
189
    }
190
191
    /**
192
     * Check if role has the given user (User Model or Id).
193
     *
194
     * @param  \Arcanesoft\Contracts\Auth\Models\User|int  $id
195
     *
196
     * @return bool
197
     */
198 9
    public function hasUser($id)
199
    {
200 9
        if ($id instanceof Eloquent)
0 ignored issues
show
Bug introduced by
The class Illuminate\Database\Eloquent\Model does not exist. Did you forget a USE statement, or did you not list all dependencies?

This error could be the result of:

1. Missing dependencies

PHP Analyzer uses your composer.json file (if available) to determine the dependencies of your project and to determine all the available classes and functions. It expects the composer.json to be in the root folder of your repository.

Are you sure this class is defined by one of your dependencies, or did you maybe not list a dependency in either the require or require-dev section?

2. Missing use statement

PHP does not complain about undefined classes in ìnstanceof checks. For example, the following PHP code will work perfectly fine:

if ($x instanceof DoesNotExist) {
    // Do something.
}

If you have not tested against this specific condition, such errors might go unnoticed.

Loading history...
201 9
            $id = $id->getKey();
202
203 9
        return $this->users->contains($id);
204
    }
205
206
    /**
207
     * Attach a permission to a role.
208
     *
209
     * @param  \Arcanesoft\Contracts\Auth\Models\Permission|int  $permission
210
     * @param  bool                                              $reload
211
     */
212 27
    public function attachPermission($permission, $reload = true)
213
    {
214 27
        if ( ! $this->hasPermission($permission)) {
215 27
            $this->permissions()->attach($permission);
216 27
            $this->loadPermissions($reload);
217
        }
218 27
    }
219
220
    /**
221
     * Detach a permission from a role.
222
     *
223
     * @param  \Arcanesoft\Contracts\Auth\Models\Permission|int  $permission
224
     * @param  bool                                              $reload
225
     *
226
     * @return int
227
     */
228 3
    public function detachPermission($permission, $reload = true)
229
    {
230 3
        if ($permission instanceof Eloquent)
0 ignored issues
show
Bug introduced by
The class Illuminate\Database\Eloquent\Model does not exist. Did you forget a USE statement, or did you not list all dependencies?

This error could be the result of:

1. Missing dependencies

PHP Analyzer uses your composer.json file (if available) to determine the dependencies of your project and to determine all the available classes and functions. It expects the composer.json to be in the root folder of your repository.

Are you sure this class is defined by one of your dependencies, or did you maybe not list a dependency in either the require or require-dev section?

2. Missing use statement

PHP does not complain about undefined classes in ìnstanceof checks. For example, the following PHP code will work perfectly fine:

if ($x instanceof DoesNotExist) {
    // Do something.
}

If you have not tested against this specific condition, such errors might go unnoticed.

Loading history...
231 3
            $permission = (array) $permission->getKey();
232
233 3
        $result = $this->permissions()->detach($permission);
234 3
        $this->loadPermissions($reload);
235
236 3
        return $result;
237
    }
238
239
    /**
240
     * Detach all permissions from a role.
241
     *
242
     * @param  bool  $reload
243
     *
244
     * @return int
245
     */
246 3
    public function detachAllPermissions($reload = true)
247
    {
248 3
        $result = $this->permissions()->detach();
249 3
        $this->loadPermissions($reload);
250
251 3
        return $result;
252
    }
253
254
    /**
255
     * Check if role has the given permission (Permission Model or Id).
256
     *
257
     * @param  mixed  $id
258
     *
259
     * @return bool
260
     */
261 27
    public function hasPermission($id)
262
    {
263 27
        if ($id instanceof Eloquent)
0 ignored issues
show
Bug introduced by
The class Illuminate\Database\Eloquent\Model does not exist. Did you forget a USE statement, or did you not list all dependencies?

This error could be the result of:

1. Missing dependencies

PHP Analyzer uses your composer.json file (if available) to determine the dependencies of your project and to determine all the available classes and functions. It expects the composer.json to be in the root folder of your repository.

Are you sure this class is defined by one of your dependencies, or did you maybe not list a dependency in either the require or require-dev section?

2. Missing use statement

PHP does not complain about undefined classes in ìnstanceof checks. For example, the following PHP code will work perfectly fine:

if ($x instanceof DoesNotExist) {
    // Do something.
}

If you have not tested against this specific condition, such errors might go unnoticed.

Loading history...
264 27
            $id = $id->getKey();
265
266 27
        return $this->permissions->contains($id);
267
    }
268
269
    /* ------------------------------------------------------------------------------------------------
270
     |  Check Functions
271
     | ------------------------------------------------------------------------------------------------
272
     */
273
    /**
274
     * Check if role is associated with a permission by slug.
275
     *
276
     * @param  string  $slug
277
     *
278
     * @return bool
279
     */
280
    public function can($slug)
281
    {
282 9
        $permissions = $this->permissions->filter(function(PermissionContract $permission) use ($slug) {
283 9
            return $permission->checkSlug($slug);
284 9
        });
285
286 9
        return $permissions->count() === 1;
287
    }
288
289
    /**
290
     * Check if a role is associated with any of given permissions.
291
     *
292
     * @param  array  $permissions
293
     * @param  array  &$failedPermissions
294
     *
295
     * @return bool
296
     */
297 6
    public function canAny(array $permissions, array &$failedPermissions = [])
298
    {
299 6
        foreach ($permissions as $permission) {
300 6
            if ( ! $this->can($permission))
301 6
                $failedPermissions[] = $permission;
302
        }
303
304 6
        return count($permissions) !== count($failedPermissions);
305
    }
306
307
    /**
308
     * Check if role is associated with all given permissions.
309
     *
310
     * @param  array  $permissions
311
     * @param  array  &$failedPermissions
312
     *
313
     * @return bool
314
     */
315 3
    public function canAll(array $permissions, array &$failedPermissions = [])
316
    {
317 3
        $this->canAny($permissions, $failedPermissions);
318
319 3
        return count($failedPermissions) === 0;
320
    }
321
322
    /**
323
     * Check if the role is locked.
324
     *
325
     * @return bool
326
     */
327 6
    public function isLocked()
328
    {
329 6
        return $this->is_locked;
330
    }
331
332
    /**
333
     * Check if slug is the same as the given value.
334
     *
335
     * @param  string  $value
336
     *
337
     * @return bool
338
     */
339 18
    public function checkSlug($value)
340
    {
341 18
        return $this->slug === $this->slugify($value);
342
    }
343
344
    /* ------------------------------------------------------------------------------------------------
345
     |  Other Functions
346
     | ------------------------------------------------------------------------------------------------
347
     */
348
    /**
349
     * Load the users.
350
     *
351
     * @param  bool  $load
352
     *
353
     * @return self
354
     */
355 9
    protected function loadUsers($load = true)
356
    {
357 9
        return $load ? $this->load('users') : $this;
358
    }
359
360
    /**
361
     * Load the permissions.
362
     *
363
     * @param  bool  $load
364
     *
365
     * @return self
366
     */
367 27
    protected function loadPermissions($load = true)
368
    {
369 27
        return $load ? $this->load('permissions') : $this;
370
    }
371
372
    /**
373
     * Slugify the value.
374
     *
375
     * @param  string  $value
376
     *
377
     * @return string
378
     */
379 90
    protected function slugify($value)
380
    {
381 90
        return Str::slug($value, config('laravel-auth.roles.slug-separator', '-'));
382
    }
383
}
384