Login::connection()   B
last analyzed

Complexity

Conditions 8
Paths 84

Size

Total Lines 64
Code Lines 35

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 8
eloc 35
nc 84
nop 0
dl 0
loc 64
rs 8.1155
c 0
b 0
f 0

How to fix   Long Method   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
3
namespace App\Controllers;
4
5
use App\Models\Remembered_loginModel;
6
use App\Models\UserModel;
7
use Core\BlogocException;
8
use Core\Container;
9
use Core\Controller;
10
use Core\Traits\PasswordFunctions;
11
use Core\Traits\StringFunctions;
12
13
14
class Login extends Controller
15
{
16
    use PasswordFunctions;
17
    use StringFunctions;
18
19
    protected $siteConfig;
20
    protected $sendMail;
21
22
    private $userModel;
23
    private $rememberedLoginModel;
24
25
    private $user;
26
27
28
    /**
29
     * Login constructor.
30
     * @param Container $container
31
     * @throws \ErrorException
32
     * @throws \ReflectionException
33
     */
34
    public function __construct(Container $container)
35
    {
36
        $this->loadModules[] = 'SiteConfig';
37
        $this->loadModules[] = 'SendMail';
38
        parent::__construct($container);
39
40
        $this->userModel = new UserModel($this->container);
41
        $this->rememberedLoginModel = new Remembered_loginModel($this->container);
42
        $this->user = new \stdClass();
43
44
    }
45
46
    /**
47
     * reset the local object user to an empty state
48
     */
49
    private function resetUser()
50
    {
51
        foreach (get_class_vars(get_class($this->user)) as $key => $value) {
52
            unset($this->user->$key);
53
        }
54
    }
55
56
    /**
57
     * add all the elements passed to the user object
58
     * @param array $userElements
59
     */
60
    private function populateUser(array $userElements)
61
    {
62
        //reset user info
63
        $this->resetUser();
64
        foreach ($userElements as $key => $element) {
65
            $this->user->$key = $element;
66
        }
67
    }
68
69
    /**
70
     * get user info from the database and populate the user object
71
     * @param int $userId
72
     * @throws \Exception
73
     */
74
    private function populateUserFromId(int $userId)
75
    {
76
        $result = $this->userModel->getUserDetailsById($userId);
77
        $this->populateUser((array)$result);
78
    }
79
80
    /**
81
     * pass the user object to the session for use
82
     */
83
    private function setUserSession()
84
    {
85
        $this->session->regenerateSessionId(); //regenerate the ID to avoid session ghosting
86
        $this->session->set("userId", $this->user->idusers);
87
        $userRoleName = $this->user->role_name ?? "";
88
        $userRoleLevel = $this->user->role_level ?? 0;
89
        $this->session->set('user_role_name', $userRoleName);
90
        $this->session->set('user_role_level', $userRoleLevel);
91
    }
92
93
    /**
94
     * the login form
95
     */
96
    public function index()
97
    {
98
        if ($this->session->isParamSet("user")) {
99
            //we are already connected, redirect
100
            $this->response->redirect();
101
        }
102
103
        $this->sendSessionVars();
104
        $this->data['configs'] = $this->siteConfig->getSiteConfig();
105
        $this->data['navigation'] = $this->siteConfig->getMenu();
106
107
        //check if have prefilled form data and error messages
108
        $this->data["loginInfo"] = $this->session->get("loginInfo");
109
        $this->data["loginErrors"] = $this->session->get("loginErrors");
110
111
        //Setting a tag to deactivate modules on this page
112
        $this->data['onRegistrationPage'] = true;
113
114
        //remove the set data as it is now sent to the template
115
        $this->session->remove("loginInfo");
116
        $this->session->remove("loginErrors");
117
118
        $this->renderView('logon');
119
    }
120
121
    /**
122
     * the register form
123
     */
124
    public function register()
125
    {
126
        if ($this->session->isParamSet("user")) {
127
            //we are already connected, redirect
128
            $this->response->redirect();
129
        }
130
131
        $this->sendSessionVars();
132
        $this->data['configs'] = $this->siteConfig->getSiteConfig();
133
        $this->data['navigation'] = $this->siteConfig->getMenu();
134
135
        //check if have prefilled form data and error mesages
136
        $this->data["registrationInfo"] = $this->session->get("registrationInfo");
137
        $this->data["registrationErrors"] = $this->session->get("registrationErrors");
138
139
        //We are on the registration page, deactivate bootstrap modals
140
        $this->data['onRegistrationPage'] = true;
141
142
        //remove the set data as it is now sent to the template
143
        $this->session->remove("registrationInfo");
144
        $this->session->remove("registrationErrors");
145
146
        $this->renderView('register');
147
    }
148
149
    /**
150
     * The post connection method
151
     */
152
    public function connection()
153
    {
154
        //is post
155
        $this->onlyPost();
156
157
        $login = $this->request->getDataFull();
158
        $email = $login["loginEmail"];
159
        $password = $login["loginPassword"];
160
        $rememberMe = isset($login["rememberMe"]);
161
162
        //resetting the password as we don't want to resend it
163
        $login["loginPassword"] = "";
164
165
        //check all the fields
166
        $error = false;
167
        $loginErrors = new \stdClass();
168
        $authUser = new \stdClass();
169
170
        if ($password == "") {
171
            $error = true;
172
            $loginErrors->password = "password must not be empty";
173
        }
174
175
        try {
176
            if (!$this->userModel->isEmailUsed($email)) {
177
                $error = true;
178
                $loginErrors->email = "This email is not registered";
179
            }
180
181
            $authUser = $this->userModel->authenticateUser($email, $password);
182
            if (!$authUser->success) {
183
                $error = true;
184
                $loginErrors->global = $authUser->message;
185
            }
186
        } catch (BlogocException $e) { //this usually throws if mail isn't valid
187
            $error = true;
188
            $loginErrors->email = $e->getMessage();
189
        }
190
191
        if ($error) {
192
            $this->session->set("loginInfo", $login);
193
            $this->session->set("loginErrors", $loginErrors);
194
            $this->response->redirect("/login");
195
        }
196
197
        //we are authenticated here
198
199
        //populate the user object with returned data
200
        $this->populateUser((array)$authUser->user);
201
202
        //if the user wanted to be remembered
203
        if ($rememberMe) {
204
            $this->rememberedLoginModel->setToken(); //generate a new token
205
            $rememberMeToken = $this->rememberedLoginModel->rememberMe($this->user->idusers);
206
            if ($rememberMeToken->success) {
207
                //set cookie
208
                $this->cookie->setCookie("rememberMe", $rememberMeToken->token, $rememberMeToken->expiry_timestamp);
209
210
            }
211
        }
212
213
        //if all is valid, set the session and redirect to user admin page
214
        $this->setUserSession();
215
        $this->response->redirect("/admin");
216
    }
217
218
    /**
219
     * the post registration method
220
     */
221
    public function registration()
222
    {
223
        //is post
224
        $this->onlyPost();
225
226
        $register = $this->request->getDataFull();
227
228
        if($register === null)
229
        {
230
            throw new \Exception("Error no data passed");
231
        }
232
233
        //Storing the passed information
234
        $this->populateUser($register);
235
236
        //Error checking
237
238
        //check all the fields
239
        $error = false;
240
        $registerErrors = new \stdClass();
241
242
        //if mail already used, go to login
243
        try {
244
            if ($this->userModel->isEmailUsed($this->user->email)) {
245
                $this->alertBox->setAlert("Email already registered, try logging in. You can always use the forgotten password to reset your account",
246
                    'error');
247
                $this->response->redirect('/login');
248
            }
249
        } catch (BlogocException $e) {
250
            $error = true;
251
            $registerErrors->email = $e->getMessage();
252
        }
253
254
        if ($this->user->name == "") {
255
            $error = true;
256
            $registerErrors->name = "name must not be empty";
257
        }
258
        if ($this->user->surname == "") {
259
            $error = true;
260
            $registerErrors->surname = "surname must not be empty";
261
        }
262
        if ($this->user->username == "") {
263
            $error = true;
264
            $registerErrors->username = "username must not be empty";
265
        }
266
267
        //If we found an error, return data to the register form and no create
268
        if ($error) {
269
            $this->session->set("registrationInfo", $register);
270
            $this->session->set("registrationErrors", $registerErrors);
271
            $this->response->redirect('/login/register');
272
        }
273
274
        //From here, all should be good, register the user
275
        $userId = $this->userModel->registerUser($this->user);
276
277
        //repopulate our user with data from the database this will remove the password as we will no longer need it
278
        $this->populateUserFromId($userId);
279
280
        //get the unique hash for email validation
281
        $token = $this->userModel->generatePasswordHash($userId);
282
283
        //send confirmation mail
284
        $this->sendMail->sendNewPasswordMail($this->user->email, $token, $userId);
285
286
287
        //all set, redirect and set message
288
        $redirectUrl = "";
289
        $refererUrl = $this->request->getReferer();
290
        if ($refererUrl != "")//getReferer can return null if client isn't configured
291
        {
292
            $baseUrl = $this->request->getBaseUrl();
293
            $redirectUrl = $this->removeFromBeginning($refererUrl, $baseUrl);
294
        }
295
296
297
        if ($redirectUrl === "login/register") {
298
            //if we were already on the register page, go to home page
299
            $redirectUrl = "";
300
        }
301
302
        $this->alertBox->setAlert('Account created, please check your mailbox to activate account');
303
        $this->response->redirect($redirectUrl);
304
    }
305
306
    /**
307
     * disconnect from the user interface
308
     */
309
    public function disconnect()
310
    {
311
        $userId = $this->session->get("userId");
312
        if ($userId) {
313
            $userHash = $this->rememberedLoginModel->getTokenHashFromId($userId);
314
            $this->rememberedLoginModel->deleteToken($userHash);
315
        }
316
317
318
        $this->cookie->deleteCookie("rememberMe");
319
        $this->session->destroySession();
320
        $this->alertBox->setAlert('Disconnected');
321
        $this->response->redirect();
322
    }
323
}