Completed
Pull Request — master (#8)
by ARCANEDEV
03:55
created

Impersonator::findUserById()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 2
CRAP Score 1

Importance

Changes 0
Metric Value
cc 1
nc 1
nop 1
dl 0
loc 4
rs 10
c 0
b 0
f 0
ccs 2
cts 2
cp 1
crap 1
1
<?php namespace Arcanedev\LaravelImpersonator;
2
3
use Arcanedev\LaravelImpersonator\Contracts\Impersonatable;
4
use Exception;
5
use Illuminate\Contracts\Foundation\Application;
6
7
/**
8
 * Class     Impersonator
9
 *
10
 * @package  Arcanedev\LaravelImpersonator
11
 * @author   ARCANEDEV <[email protected]>
12
 */
13
class Impersonator implements Contracts\Impersonator
14
{
15
    /* -----------------------------------------------------------------
16
     |  Properties
17
     | -----------------------------------------------------------------
18
     */
19
20
    /** @var  \Illuminate\Contracts\Foundation\Application */
21
    protected $app;
22
23
    /* -----------------------------------------------------------------
24
     |  Constructor
25
     | -----------------------------------------------------------------
26
     */
27
28
    /**
29
     * Impersonator constructor.
30
     *
31
     * @param  \Illuminate\Contracts\Foundation\Application  $app
32
     */
33 44
    public function __construct(Application $app)
34
    {
35 44
        $this->app = $app;
36 44
    }
37
38
    /* -----------------------------------------------------------------
39
     |  Getters & Setters
40
     | -----------------------------------------------------------------
41
     */
42
43
    /**
44
     * Get the guard session instance.
45
     *
46
     * @return \Illuminate\Auth\AuthManager|\Arcanedev\LaravelImpersonator\Guard\SessionGuard
47
     */
48 18
    protected function auth()
49
    {
50 18
        return $this->app['auth'];
51
    }
52
53
    /**
54
     * Get the session store instance.
55
     *
56
     * @return \Illuminate\Contracts\Session\Session
57
     */
58 22
    protected function session()
59
    {
60 22
        return $this->app['session'];
61
    }
62
63
    /**
64
     * Get the config repository.
65
     *
66
     * @return \Illuminate\Contracts\Config\Repository
67
     */
68 34
    protected function config()
69
    {
70 34
        return $this->app['config'];
71
    }
72
73
    /**
74
     * Get the event dispatcher.
75
     *
76
     * @return \Illuminate\Contracts\Events\Dispatcher
77
     */
78 16
    protected function events()
79
    {
80 16
        return $this->app['events'];
81
    }
82
83
    /**
84
     * Get the session key.
85
     *
86
     * @return string
87
     */
88 24
    public function getSessionKey()
89
    {
90 24
        return $this->config()->get('impersonator.session.key', 'impersonator_id');
91
    }
92
93
    /**
94
     * Get the impersonator id.
95
     *
96
     * @return  int|null
97
     */
98 18
    public function getImpersonatorId()
99
    {
100 18
        return $this->session()->get($this->getSessionKey(), null);
101
    }
102
103
    /* -----------------------------------------------------------------
104
     |  Main Methods
105
     | -----------------------------------------------------------------
106
     */
107
108
    /**
109
     * Start the impersonation.
110
     *
111
     * @param  \Arcanedev\LaravelImpersonator\Contracts\Impersonatable  $impersonater
112
     * @param  \Arcanedev\LaravelImpersonator\Contracts\Impersonatable  $impersonated
113
     *
114
     * @return bool
115
     */
116 24
    public function start(Impersonatable $impersonater, Impersonatable $impersonated)
117
    {
118 24
        $this->checkImpersonation($impersonater, $impersonated);
119
120
        try {
121 16
            session()->put($this->getSessionKey(), $impersonater->getAuthIdentifier());
122 16
            $this->auth()->silentLogout();
0 ignored issues
show
Bug introduced by
The method silentLogout does only exist in Arcanedev\LaravelImpersonator\Guard\SessionGuard, but not in Illuminate\Auth\AuthManager.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
123 16
            $this->auth()->silentLogin($impersonated);
0 ignored issues
show
Bug introduced by
The method silentLogin does only exist in Arcanedev\LaravelImpersonator\Guard\SessionGuard, but not in Illuminate\Auth\AuthManager.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
124
125 16
            $this->events()->dispatch(
126 16
                new Events\ImpersonationStarted($impersonater, $impersonated)
127
            );
128
129 16
            return true;
130
        }
131
        catch (Exception $e) {
132
            return false;
133
        }
134
    }
135
136
    /**
137
     * Stop the impersonation.
138
     *
139
     * @return bool
140
     */
141 14
    public function stop()
142
    {
143
        try {
144 14
            $impersonated = $this->auth()->user();
0 ignored issues
show
Bug introduced by
The method user does only exist in Arcanedev\LaravelImpersonator\Guard\SessionGuard, but not in Illuminate\Auth\AuthManager.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
145 14
            $impersonater = $this->findUserById($this->getImpersonatorId());
146
147 12
            $this->auth()->silentLogout();
0 ignored issues
show
Bug introduced by
The method silentLogout does only exist in Arcanedev\LaravelImpersonator\Guard\SessionGuard, but not in Illuminate\Auth\AuthManager.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
148 12
            $this->auth()->silentLogin($impersonater);
0 ignored issues
show
Bug introduced by
The method silentLogin does only exist in Arcanedev\LaravelImpersonator\Guard\SessionGuard, but not in Illuminate\Auth\AuthManager.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
149 12
            $this->clear();
150
151 12
            $this->events()->dispatch(
152 12
                new Events\ImpersonationStopped($impersonater, $impersonated)
153
            );
154
155 12
            return true;
156
        }
157 2
        catch (Exception $e) {
158 2
            return false;
159
        }
160
    }
161
162
    /**
163
     * Clear the impersonation.
164
     */
165 14
    public function clear()
166
    {
167 14
        $this->session()->forget($this->getSessionKey());
168 14
    }
169
170
    /**
171
     * Find a user by the given id.
172
     *
173
     * @param  int|string  $id
174
     *
175
     * @return \Arcanedev\LaravelImpersonator\Contracts\Impersonatable
176
     *
177
     * @throws \Exception
178
     */
179 26
    public function findUserById($id)
180
    {
181 26
        return call_user_func([$this->config()->get('auth.providers.users.model'), 'findOrFail'], $id);
182
    }
183
184
    /* -----------------------------------------------------------------
185
     |  Check Functions
186
     | -----------------------------------------------------------------
187
     */
188
189
    /**
190
     * Check if it's impersonating.
191
     *
192
     * @return bool
193
     */
194 18
    public function isImpersonating()
195
    {
196 18
        return $this->session()->has($this->getSessionKey());
197
    }
198
199
    /**
200
     * Check if the impersonations is enabled.
201
     *
202
     * @return bool
203
     */
204 24
    public function isEnabled()
205
    {
206 24
        return $this->config()->get('impersonator.enabled', false);
207
    }
208
209
    /* -----------------------------------------------------------------
210
     |  Other Methods
211
     | -----------------------------------------------------------------
212
     */
213
214
    /**
215
     * Check the impersonation.
216
     *
217
     * @param  \Arcanedev\LaravelImpersonator\Contracts\Impersonatable  $impersonater
218
     * @param  \Arcanedev\LaravelImpersonator\Contracts\Impersonatable  $impersonated
219
     */
220 24
    private function checkImpersonation(Impersonatable $impersonater, Impersonatable $impersonated)
221
    {
222 24
        $this->mustBeEnabled();
223 22
        $this->mustBeDifferentImpersonatable($impersonater, $impersonated);
224 20
        $this->checkImpersonater($impersonater);
225 18
        $this->checkImpersonated($impersonated);
226 16
    }
227
228
    /**
229
     * Check if the impersonation is enabled.
230
     *
231
     * @throws \Arcanedev\LaravelImpersonator\Exceptions\ImpersonationException
232
     */
233 24
    private function mustBeEnabled()
234
    {
235 24
        if ( ! $this->isEnabled())
236 2
            throw new Exceptions\ImpersonationException(
237 2
                'The impersonation is disabled.'
238
            );
239 22
    }
240
241
    /**
242
     * Check the impersonater and the impersonated are different.
243
     *
244
     * @param  \Arcanedev\LaravelImpersonator\Contracts\Impersonatable  $impersonater
245
     * @param  \Arcanedev\LaravelImpersonator\Contracts\Impersonatable  $impersonated
246
     *
247
     * @throws \Arcanedev\LaravelImpersonator\Exceptions\ImpersonationException
248
     */
249 22
    private function mustBeDifferentImpersonatable(Impersonatable $impersonater, Impersonatable $impersonated)
250
    {
251 22
        if ($impersonater->getAuthIdentifier() == $impersonated->getAuthIdentifier())
252 2
            throw new Exceptions\ImpersonationException(
253 2
                'The impersonater & impersonated with must be different.'
254
            );
255 20
    }
256
257
    /**
258
     * Check the impersonater.
259
     *
260
     * @param  \Arcanedev\LaravelImpersonator\Contracts\Impersonatable  $impersonater
261
     *
262
     * @throws \Arcanedev\LaravelImpersonator\Exceptions\ImpersonationException
263
     */
264 20
    private function checkImpersonater(Impersonatable $impersonater)
265
    {
266 20
        if ( ! $impersonater->canImpersonate())
267 2
            throw new Exceptions\ImpersonationException(
268 2
                "The impersonater with `{$impersonater->getAuthIdentifierName()}`=[{$impersonater->getAuthIdentifier()}] doesn't have the ability to impersonate."
269
            );
270 18
    }
271
272
    /**
273
     * Check the impersonated.
274
     *
275
     * @param  \Arcanedev\LaravelImpersonator\Contracts\Impersonatable  $impersonated
276
     *
277
     * @throws \Arcanedev\LaravelImpersonator\Exceptions\ImpersonationException
278
     */
279 18
    private function checkImpersonated(Impersonatable $impersonated)
280
    {
281 18
        if ( ! $impersonated->canBeImpersonated())
282 2
            throw new Exceptions\ImpersonationException(
283 2
                "The impersonated with `{$impersonated->getAuthIdentifierName()}`=[{$impersonated->getAuthIdentifier()}] cannot be impersonated."
284
            );
285 16
    }
286
}
287