Complex classes like Component often do a lot of different things. To break such a class down, we need to identify a cohesive component within that class. A common approach to find such a component is to look for fields/methods that share the same prefixes, or suffixes. You can also have a look at the cohesion graph to spot any un-connected, or weakly-connected components.
Once you have determined the fields that belong together, you can apply the Extract Class refactoring. If the component makes sense as a sub-class, Extract Subclass is also a candidate, and is often faster.
While breaking up the class, it is a good idea to analyze how other classes use Component, and based on these observations, apply Extract Interface, too.
1 | <?php |
||
29 | class Component |
||
30 | { |
||
31 | |||
32 | /** @var object This property gives you access to the SQLite3 (or custom) users database. */ |
||
33 | public $db; |
||
34 | |||
35 | /** @var object BootPress\Page\Component instance. */ |
||
36 | private $page; |
||
37 | |||
38 | /** @var null|string The HTTP Authenticated username or null. */ |
||
39 | private $basic; |
||
40 | |||
41 | /** @var array Password hashing options. */ |
||
42 | private $password; |
||
43 | |||
44 | /** $var array Information we user to sanity check with a cookie. Has '**id**', '**series**', '**token**', '**time**', and '**user_agent**' keys. */ |
||
45 | private $session = array(); |
||
46 | |||
47 | /** var array Stored information about a logged in user. Has '**id**', '**name**', '**email**', '**admin**', and '**login**' keys. */ |
||
48 | private $user = array(); |
||
49 | |||
50 | /** |
||
51 | * Establishes the authentication settings, and runs all of our security checks. Authentication is either session-based, or via HTTP Basic Auth. Session-based authentication relies on the user database. HTTP Basic Auth can use either the database, an array, or a YAML file of usernames and passwords. A user can be both HTTP and session authenticated as long as Basic Auth is not using the database. This allows an administrator to be logged in as a regular user, yet still retain super admin privileges. |
||
52 | * |
||
53 | * @param array $options Allows you to customize the authorization settings. You can set the: |
||
54 | * |
||
55 | * - '**db**' - A custom BootPress\Database\Component instance. The default is an SQLite Users.db we will automatically create. |
||
56 | * - '**basic**' - Either ``null`` (the default) to use the users database, an ``array('username'=>'password', ...)`` of users, or a YAML file of username's and password's. |
||
57 | * - '**password**' - '**algo**' and '**options**' for hashing passwords. |
||
58 | */ |
||
59 | 9 | public function __construct(array $options = array()) { |
|
195 | |||
196 | /** |
||
197 | * @return null|string The basic username if HTTP authenticated, or null if not. |
||
198 | */ |
||
199 | 1 | public function http() |
|
203 | |||
204 | /** |
||
205 | * HTTP Authenticate a user for current directory and all subdirectories whether they are signed in or not. |
||
206 | * |
||
207 | * @param string $name Identifies the set of resources to which the username and password will apply. |
||
208 | * |
||
209 | * @see http://stackoverflow.com/questions/12701085/what-is-the-realm-in-basic-authentication |
||
210 | * |
||
211 | * ```php |
||
212 | * if (!$auth->http()) { |
||
213 | * $auth->realm('Website'); |
||
214 | * } |
||
215 | * ``` |
||
216 | */ |
||
217 | 1 | public function realm($name, $message = null) |
|
224 | |||
225 | /** |
||
226 | * Retrieve some information about the signed in user. |
||
227 | * |
||
228 | * @param string $param Can be any of the following: |
||
229 | * - '**id**' - From the database's user table. |
||
230 | * - '**name**' - Of the user. |
||
231 | * - '**email**' - Of the user. |
||
232 | * - '**admin**' level - The default is 0 meaning they have no admin privileges. |
||
233 | * - '**login**' - The number of seconds ago that they actually signed in with a username and password for the current session. If using HTTP Basic Authentication, this will always be 0. |
||
234 | * |
||
235 | * @return array|string|null An array if you don't set $param, a string if the user is logged in and the $param exists, or null if not. |
||
236 | * |
||
237 | * ```php |
||
238 | * echo 'Hello '.$auth->user('name'); |
||
239 | * ``` |
||
240 | */ |
||
241 | 7 | public function user($param = null) |
|
249 | |||
250 | /** |
||
251 | * Gives you the following information about your user(s): |
||
252 | * |
||
253 | * - '**id**' |
||
254 | * - '**name**' |
||
255 | * - '**email**' |
||
256 | * - '**admin**' - Integer. |
||
257 | * - '**approved**' - Y (yes) or N (no). |
||
258 | * - '**registered**' - A GMT timestamp. |
||
259 | * - '**last_activity**' - A GMT timestamp (updated at 5 minute intervals) or 0 if we don't know. |
||
260 | * - A '**groups**' ``array($group, ...)`` of groups they are in. |
||
261 | * |
||
262 | * @param int|int[] $user_id An integer, or an ``array($user_id, ...)``` of users you would like to return information for. |
||
263 | * |
||
264 | * @return array An associative array of information about your user(s). If $user_id is an array, then this will be a multidimensional ``array($user_id => $info, ...)``` for every user in the order given. If there was no record found for a given $user_id, then it will be an empty array. |
||
265 | */ |
||
266 | 2 | public function info($user_id) |
|
284 | |||
285 | /** |
||
286 | * This takes the submitted parameters and check to see if they exist in the users database. |
||
287 | * |
||
288 | * @param string $email This is the only required argument. If you stop here then we are only checking to see if the email already exists. |
||
289 | * @param string $password The submitted password to check if the user is who they are claiming to be. Encryption is handled in vitro. |
||
290 | * @param string $and Additional qualifier's to check against. |
||
291 | * |
||
292 | * @return int|false (bool) false if the record does not exist, or the id (integer) of the user if we have a match. |
||
293 | * |
||
294 | * ```php |
||
295 | * if ($user_id = $auth->check('[email protected]', 'password', 'approved = "Y"')) { |
||
296 | * // Then you may proceed with $user_id |
||
297 | * } |
||
298 | * ``` |
||
299 | */ |
||
300 | 5 | public function check($email, $password = null, $and = null) |
|
324 | |||
325 | /** |
||
326 | * Verifies whether or not an email address looks valid. |
||
327 | * |
||
328 | * @param string $address The email you would like to verify the looks of. |
||
329 | * |
||
330 | * @return bool True or False. Whether the $address looks like a real email or not. |
||
331 | * |
||
332 | * ```php |
||
333 | * if ($auth->isEmail('[email protected]')) { |
||
334 | * // Then you may proceed |
||
335 | * } |
||
336 | * ``` |
||
337 | */ |
||
338 | 1 | public function isEmail($address) |
|
342 | |||
343 | /** |
||
344 | * This creates a random password that you can suggest to a user, or use to reset and email them the new password, or to just create a random alpha-numeric string for yourself. |
||
345 | * |
||
346 | * @param int $length The desired length of your password |
||
347 | * |
||
348 | * @return string The random password. |
||
349 | */ |
||
350 | 1 | public function randomPassword($length = 8) |
|
369 | |||
370 | /** |
||
371 | * This will ensure that a user is registered at the site. If you get someone registering twice for whatever reason, then this will make sure they are in, and you can advise them whether or not they already hold an account with you. If they are not a $new_user, then the name and password will not be saved (the email of course will remain the same). You don't want somebody registering themselves access into someone else's account. |
||
372 | * |
||
373 | * @param string $name The user's name. |
||
374 | * @param string $email The user's email. |
||
375 | * @param string $password The user's password. Do not encrypt! We do that for you. |
||
376 | * |
||
377 | * @return array An ``array((bool) $new_user, (int) $user_id)`` where $new_user is either true or false, and $user_id is either the new or the old id depending. |
||
378 | * |
||
379 | * ```php |
||
380 | * list($new_user, $user_id) = $auth->register('Joe Blow', '[email protected]', 'sekrit'); |
||
381 | * ``` |
||
382 | */ |
||
383 | 1 | public function register($name, $email, $password) |
|
400 | |||
401 | /** |
||
402 | * Allows you to update a users account. |
||
403 | * |
||
404 | * @param int $user_id The id of the user you would like to update. |
||
405 | * @param array $user An associative array of fields you would like to update. The available fields are: |
||
406 | * |
||
407 | * - '**name**' => The users name. |
||
408 | * - '**email**' => The users email. If you are changing this, then make sure it is not already in use beforehand. |
||
409 | * - '**password**' => The new password. No encryption needed. |
||
410 | * - '**admin**' => An integer >= 0. |
||
411 | * - '**approved**' => '**Y**' (yes) or '**N**' (no). If you set this to '**N**' (no), they will be logged out immediately wherever they may be. |
||
412 | * - '**registered**' => |
||
413 | * - '**last_activity**' => |
||
414 | * |
||
415 | * ... and any other fields that may exist if you have customized the database to suit your needs. |
||
416 | * |
||
417 | * ```php |
||
418 | * if ($auth->update($user_id, array( |
||
419 | * 'approved' => 'N', // This will log them out and prevent them from ever signing in again. |
||
420 | * )); |
||
421 | * ``` |
||
422 | */ |
||
423 | 1 | public function update($user_id, array $user = array()) |
|
476 | |||
477 | /** |
||
478 | * This will login a user to your site for a specified amount of time (of inactivity), and optionally log them out everywhere else. Session and cookie based. |
||
479 | * |
||
480 | * @param integer $user_id Of the user you want to login. |
||
481 | * @param integer $expires The number of days (if less than or equal to 730) or seconds (if greater than 730) of inactivity after which you would like to require the user to sign back into your site. |
||
482 | * @param false|mixed $single If you set this to true (or to anything besides false), then they will be logged out of every other session that may be currently active. Meaning if you sign in on a public computer, then realize you forgot to sign out, you can sign in again on any other computer and be signed out from all previous sessions if you use this feature. |
||
483 | * |
||
484 | * ```php |
||
485 | * $auth->login($user_id, 30, 'single'); // Sign in $user_id for 30 days here, and log them out everywhere else. |
||
486 | * ``` |
||
487 | */ |
||
488 | 4 | public function login($user_id, $expires = 7200, $single = false) |
|
519 | |||
520 | /** |
||
521 | * This will log a session authenticated user out of your site. |
||
522 | * |
||
523 | * @param integer $user_id If this is an integer, then $user_id will be logged out of all their sessions, everywhere. If null (or not given), then the current user will be logged out of the current session. |
||
524 | * |
||
525 | * ```php |
||
526 | * $auth->logout(); // Log out the current user. |
||
527 | * ``` |
||
528 | */ |
||
529 | 6 | public function logout($user_id = null) |
|
543 | |||
544 | /** |
||
545 | * Get the number of active, session authenticated users at your site within the $duration given. |
||
546 | * |
||
547 | * @param integer $duration How far back (in seconds) you would like to go. The default is 600 seconds ie. 10 minutes. |
||
548 | * |
||
549 | * @return integer The total number of active users. If this is 1, then that's you! |
||
550 | * |
||
551 | * ```php |
||
552 | * $auth->count(86400); // within the last 24 hours |
||
553 | * ``` |
||
554 | */ |
||
555 | 1 | public function online($duration = 600) |
|
559 | |||
560 | /** |
||
561 | * This will tell you if the person viewing the current page is a specific (optional) user, or not. This does not apply if the user is HTTP Basic Authenticated from an array or YAML file of users. |
||
562 | * |
||
563 | * @param integer $user_id If you want to verify that this is a specific user, then you may indicate the user's id here. |
||
564 | * |
||
565 | * @return false|integer False if they are not a signed in user, and if you included a $user_id then false if they are not that specific user. Otherwise this returns the id of the signed in user. |
||
566 | * |
||
567 | * ```php |
||
568 | * if ($user_id = $auth->isUser()) { |
||
569 | * // Now we may do something specifically for $user_id |
||
570 | * } |
||
571 | * |
||
572 | * if (!$auth->isUser($seller_id)) { |
||
573 | * $page->eject(); // not the real seller, get them out of here |
||
574 | * } |
||
575 | * |
||
576 | * if ($auth->isUser()) { |
||
577 | * // Display a logout link |
||
578 | * } |
||
579 | * ``` |
||
580 | */ |
||
581 | 7 | public function isUser($user_id = null) |
|
592 | |||
593 | /** |
||
594 | * Allows you to determine if ``$this->isUser()`` submitted a password during the current session, or if we're relying on a remember-me cookie. |
||
595 | * |
||
596 | * @return false|integer The current user's id if they submitted a password during the current session, or false if not. |
||
597 | * |
||
598 | * ```php |
||
599 | * if ($user_id = $auth->isVerified()) { |
||
600 | * // Allow them to change their password, charge their credit card, etc. |
||
601 | * } |
||
602 | * ``` |
||
603 | */ |
||
604 | 1 | public function isVerified() |
|
608 | |||
609 | /** |
||
610 | * This will tell you if the person viewing the current page has admin access greater than or equal to $level, or not. There is no need to check if ``$this->isUser()`` first when using this function, unless you also want the $user_id, or to make sure this is a specific admin user. HTTP Basic Authenticated users will always pass this test and returns (integer) 1, giving them super-admin privileges. |
||
611 | * |
||
612 | * @param integer $level The admin user must be greater than or equal to the level you indicate here. This method manages admin permissions as follows: |
||
613 | * |
||
614 | * 1. Is the end all and be all of admins, and can access anything. |
||
615 | * 2. Does not have level 1 access, but can access 2, 3, 4, 5, etc. |
||
616 | * 3. Cannot access level 1 or 2 admin pages, but can access 3, 4, 5, 6 ... you get the picture. |
||
617 | * |
||
618 | * @return bool False if they are not even a user in the first place, and false again if they don't have the level of access you desire. Otherwise it returns the level of access they have. |
||
619 | * |
||
620 | * ```php |
||
621 | * if ($auth->isAdmin(1) || $auth->isUser($seller)) { |
||
622 | * // Now you and the seller can edit their info |
||
623 | * } |
||
624 | * |
||
625 | * if ($level = $auth->isAdmin(2)) { |
||
626 | * // Level 1 and level 2 admins can access this |
||
627 | * if ($level == 1) { |
||
628 | * // Now we are tightening down the hatches |
||
629 | * } |
||
630 | * } |
||
631 | * ``` |
||
632 | */ |
||
633 | 3 | public function isAdmin($level = 1) |
|
643 | |||
644 | /** |
||
645 | * Checks to see if the signed in user is included in any or all of the group(s) you specify. |
||
646 | * |
||
647 | * @param string|array $group The name of the group. To verify membership for the current user against |
||
648 | * @param string $check If '**all**' (default) then they must be in every group specified. If '**any**' then they must be in at least one of the groups specified. |
||
649 | * |
||
650 | * @return bool True or False. |
||
651 | * |
||
652 | * ```php |
||
653 | * if ($auth->inGroup(array('heaven', 'hell'), 'any')) { |
||
654 | * // Then this signed in user is dead. |
||
655 | * $auth->logout(); |
||
656 | * } |
||
657 | * ``` |
||
658 | */ |
||
659 | 2 | public function inGroup($group, $check = 'all') |
|
666 | |||
667 | /** |
||
668 | * This will add $user_id(s) to the $group(s) you want to include them in. |
||
669 | * |
||
670 | * @param integer $user_id Of the user. To add multiple users, make this an ``array($user_id, ...)`` of users to add to the $group(s). |
||
671 | * @param string $group The name of the group you would like to include them in. To include in multiple groups, make this an ``array($group, ...)`` of groups to add the $user_id(s) to. |
||
672 | * |
||
673 | * ```php |
||
674 | * $auth->addToGroup($user_id, 'rothschild'); |
||
675 | * ``` |
||
676 | */ |
||
677 | 1 | public function addToGroup($user_id, $group) |
|
690 | |||
691 | /** |
||
692 | * This will remove $user_id(s) from the $group(s) they no longer belong in. |
||
693 | * |
||
694 | * @param integer $user_id Of the user. To remove multiple users, make this an ``array($user_id, ...)`` of users to remove from the $group(s). |
||
695 | * @param string $group The name of the group you would like to remove them from. To remove from multiple groups, make this an ``array($group, ...)`` of groups to remove the $user_id(s) from. |
||
696 | * |
||
697 | * ```php |
||
698 | * $auth->removeFromGroup($user_id, 'rothschild'); // $user_id should not be involved with them anyways |
||
699 | * ``` |
||
700 | */ |
||
701 | 1 | public function removeFromGroup($user_id, $group) |
|
709 | |||
710 | /** |
||
711 | * This will retrieve all of the groups that $user_id(s) belong to. |
||
712 | * |
||
713 | * @param integer $user_id Of the user. If you want to retrieve the groups of multiple users at once, then make this an ``array($user_id, ...)`` of users. |
||
714 | * |
||
715 | * @return array A single ``array($group, ...)`` of groups if $user_id is an integer (single), or a multidimensional ``array($user_id => $groups, ...)`` for every $user_id in the order given. |
||
716 | * |
||
717 | * ```php |
||
718 | * $groups = $auth->getUsersGroups($user_id); |
||
719 | * ``` |
||
720 | */ |
||
721 | 4 | public function getUsersGroups($user_id) |
|
741 | |||
742 | /** |
||
743 | * This will retrieve all of the user_id's that belong to the $group(s). |
||
744 | * |
||
745 | * @param string $group The name of the group. If you want to retrieve the user_id's of multiple groups at once, then make this an ``array($group, ...)`` of groups. |
||
746 | * |
||
747 | * @return array A single ``array($user_id, ...)`` of users if $groups is a string (single), or a multidimensional ``array($group => (array) $user_ids, ...)`` for every $group in the order given. |
||
748 | * |
||
749 | * ```php |
||
750 | * $users = $auth->getGroupsUsers('rothschild'); |
||
751 | * ``` |
||
752 | */ |
||
753 | 1 | public function getGroupsUsers($group) |
|
774 | |||
775 | /** |
||
776 | * This will verify if $user_id is in '**any**' or '**all**' of the $group(s) specified. If you are checking for the current user of your page, then do not use this method. Use ``$this->inGroup()`` instead. |
||
777 | * |
||
778 | * @param integer $user_id Of the user whose $group(s) membership you want to verify. This cannot be an array. Sorry. |
||
779 | * @param string $group The name of the group. To verify $user_id against multiple groups then make this an ``array($group, ...)`` of groups. |
||
780 | * @param string $check If '**all**' (default) then they must be in every group specified. If '**any**' then they must be in at least one of the groups specified. |
||
781 | * |
||
782 | * @return array True or False, whether or not your conditions were met. |
||
783 | * |
||
784 | * ```php |
||
785 | * if ($auth->userInGroup($user_id, array('rothschild', 'white house', 'al-Qaeda'), 'any') { |
||
786 | * // Well then we've got quite the user on our hands. |
||
787 | * } |
||
788 | * ``` |
||
789 | */ |
||
790 | 2 | public function userInGroup($user_id, $group, $check = 'all') // or 'any' |
|
809 | |||
810 | /** |
||
811 | * Retrieves a group's id. |
||
812 | * |
||
813 | * @param string|array $name Of the group. |
||
814 | * |
||
815 | * @return integer|array The group(s) id(s). |
||
816 | */ |
||
817 | 1 | private function groupId($name) |
|
837 | |||
838 | /** |
||
839 | * Sets (or removes if the $value is empty) a cookie to verify the validity of a session. |
||
840 | * |
||
841 | * @param string $value Of the cookie. |
||
842 | * @param integer $expires How long (in seconds) the cookie should exist. |
||
843 | */ |
||
844 | 6 | private function setCookie($value = '', $expires = 0) |
|
859 | |||
860 | /** |
||
861 | * Generates the series and tokens we use to compare sessions and cookies with. |
||
862 | * |
||
863 | * @return string A random, 22 character string. |
||
864 | */ |
||
865 | 4 | private function salt() |
|
869 | } |
||
870 |