[ Index ]

PHP Cross Reference of Joomla 4.2.2 documentation

title

Body

[close]

/components/com_users/src/Model/ -> RegistrationModel.php (source)

   1  <?php
   2  
   3  /**
   4   * @package     Joomla.Site
   5   * @subpackage  com_users
   6   *
   7   * @copyright   (C) 2009 Open Source Matters, Inc. <https://www.joomla.org>
   8   * @license     GNU General Public License version 2 or later; see LICENSE.txt
   9   */
  10  
  11  namespace Joomla\Component\Users\Site\Model;
  12  
  13  use Joomla\CMS\Application\ApplicationHelper;
  14  use Joomla\CMS\Component\ComponentHelper;
  15  use Joomla\CMS\Date\Date;
  16  use Joomla\CMS\Factory;
  17  use Joomla\CMS\Form\Form;
  18  use Joomla\CMS\Form\FormFactoryInterface;
  19  use Joomla\CMS\Language\Multilanguage;
  20  use Joomla\CMS\Language\Text;
  21  use Joomla\CMS\Log\Log;
  22  use Joomla\CMS\Mail\MailTemplate;
  23  use Joomla\CMS\MVC\Factory\MVCFactoryInterface;
  24  use Joomla\CMS\MVC\Model\FormModel;
  25  use Joomla\CMS\Plugin\PluginHelper;
  26  use Joomla\CMS\Router\Route;
  27  use Joomla\CMS\String\PunycodeHelper;
  28  use Joomla\CMS\Uri\Uri;
  29  use Joomla\CMS\User\User;
  30  use Joomla\CMS\User\UserHelper;
  31  use Joomla\Database\ParameterType;
  32  
  33  // phpcs:disable PSR1.Files.SideEffects
  34  \defined('_JEXEC') or die;
  35  // phpcs:enable PSR1.Files.SideEffects
  36  
  37  /**
  38   * Registration model class for Users.
  39   *
  40   * @since  1.6
  41   */
  42  class RegistrationModel extends FormModel
  43  {
  44      /**
  45       * @var    object  The user registration data.
  46       * @since  1.6
  47       */
  48      protected $data;
  49  
  50      /**
  51       * Constructor.
  52       *
  53       * @param   array                 $config       An array of configuration options (name, state, dbo, table_path, ignore_request).
  54       * @param   MVCFactoryInterface   $factory      The factory.
  55       * @param   FormFactoryInterface  $formFactory  The form factory.
  56       *
  57       * @see     \Joomla\CMS\MVC\Model\BaseDatabaseModel
  58       * @since   3.2
  59       */
  60      public function __construct($config = array(), MVCFactoryInterface $factory = null, FormFactoryInterface $formFactory = null)
  61      {
  62          $config = array_merge(
  63              array(
  64                  'events_map' => array('validate' => 'user')
  65              ),
  66              $config
  67          );
  68  
  69          parent::__construct($config, $factory, $formFactory);
  70      }
  71  
  72      /**
  73       * Method to get the user ID from the given token
  74       *
  75       * @param   string  $token  The activation token.
  76       *
  77       * @return  mixed   False on failure, id of the user on success
  78       *
  79       * @since   3.8.13
  80       */
  81      public function getUserIdFromToken($token)
  82      {
  83          $db       = $this->getDatabase();
  84  
  85          // Get the user id based on the token.
  86          $query = $db->getQuery(true);
  87          $query->select($db->quoteName('id'))
  88              ->from($db->quoteName('#__users'))
  89              ->where($db->quoteName('activation') . ' = :activation')
  90              ->where($db->quoteName('block') . ' = 1')
  91              ->where($db->quoteName('lastvisitDate') . ' IS NULL')
  92              ->bind(':activation', $token);
  93          $db->setQuery($query);
  94  
  95          try {
  96              return (int) $db->loadResult();
  97          } catch (\RuntimeException $e) {
  98              $this->setError(Text::sprintf('COM_USERS_DATABASE_ERROR', $e->getMessage()));
  99  
 100              return false;
 101          }
 102      }
 103  
 104      /**
 105       * Method to activate a user account.
 106       *
 107       * @param   string  $token  The activation token.
 108       *
 109       * @return  mixed    False on failure, user object on success.
 110       *
 111       * @since   1.6
 112       */
 113      public function activate($token)
 114      {
 115          $app        = Factory::getApplication();
 116          $userParams = ComponentHelper::getParams('com_users');
 117          $userId     = $this->getUserIdFromToken($token);
 118  
 119          // Check for a valid user id.
 120          if (!$userId) {
 121              $this->setError(Text::_('COM_USERS_ACTIVATION_TOKEN_NOT_FOUND'));
 122  
 123              return false;
 124          }
 125  
 126          // Load the users plugin group.
 127          PluginHelper::importPlugin('user');
 128  
 129          // Activate the user.
 130          $user = Factory::getUser($userId);
 131  
 132          // Admin activation is on and user is verifying their email
 133          if (($userParams->get('useractivation') == 2) && !$user->getParam('activate', 0)) {
 134              $linkMode = $app->get('force_ssl', 0) == 2 ? Route::TLS_FORCE : Route::TLS_IGNORE;
 135  
 136              // Compile the admin notification mail values.
 137              $data = $user->getProperties();
 138              $data['activation'] = ApplicationHelper::getHash(UserHelper::genRandomPassword());
 139              $user->set('activation', $data['activation']);
 140              $data['siteurl'] = Uri::base();
 141              $data['activate'] = Route::link(
 142                  'site',
 143                  'index.php?option=com_users&task=registration.activate&token=' . $data['activation'],
 144                  false,
 145                  $linkMode,
 146                  true
 147              );
 148  
 149              $data['fromname'] = $app->get('fromname');
 150              $data['mailfrom'] = $app->get('mailfrom');
 151              $data['sitename'] = $app->get('sitename');
 152              $user->setParam('activate', 1);
 153  
 154              // Get all admin users
 155              $db = $this->getDatabase();
 156              $query = $db->getQuery(true)
 157                  ->select($db->quoteName(array('name', 'email', 'sendEmail', 'id')))
 158                  ->from($db->quoteName('#__users'))
 159                  ->where($db->quoteName('sendEmail') . ' = 1')
 160                  ->where($db->quoteName('block') . ' = 0');
 161  
 162              $db->setQuery($query);
 163  
 164              try {
 165                  $rows = $db->loadObjectList();
 166              } catch (\RuntimeException $e) {
 167                  $this->setError(Text::sprintf('COM_USERS_DATABASE_ERROR', $e->getMessage()));
 168  
 169                  return false;
 170              }
 171  
 172              // Send mail to all users with users creating permissions and receiving system emails
 173              foreach ($rows as $row) {
 174                  $usercreator = Factory::getUser($row->id);
 175  
 176                  if ($usercreator->authorise('core.create', 'com_users') && $usercreator->authorise('core.manage', 'com_users')) {
 177                      try {
 178                          $mailer = new MailTemplate('com_users.registration.admin.verification_request', $app->getLanguage()->getTag());
 179                          $mailer->addTemplateData($data);
 180                          $mailer->addRecipient($row->email);
 181                          $return = $mailer->send();
 182                      } catch (\Exception $exception) {
 183                          try {
 184                              Log::add(Text::_($exception->getMessage()), Log::WARNING, 'jerror');
 185  
 186                              $return = false;
 187                          } catch (\RuntimeException $exception) {
 188                              Factory::getApplication()->enqueueMessage(Text::_($exception->errorMessage()), 'warning');
 189  
 190                              $return = false;
 191                          }
 192                      }
 193  
 194                      // Check for an error.
 195                      if ($return !== true) {
 196                          $this->setError(Text::_('COM_USERS_REGISTRATION_ACTIVATION_NOTIFY_SEND_MAIL_FAILED'));
 197  
 198                          return false;
 199                      }
 200                  }
 201              }
 202          } elseif (($userParams->get('useractivation') == 2) && $user->getParam('activate', 0)) {
 203              // Admin activation is on and admin is activating the account
 204              $user->set('activation', '');
 205              $user->set('block', '0');
 206  
 207              // Compile the user activated notification mail values.
 208              $data = $user->getProperties();
 209              $user->setParam('activate', 0);
 210              $data['fromname'] = $app->get('fromname');
 211              $data['mailfrom'] = $app->get('mailfrom');
 212              $data['sitename'] = $app->get('sitename');
 213              $data['siteurl'] = Uri::base();
 214              $mailer = new MailTemplate('com_users.registration.user.admin_activated', $app->getLanguage()->getTag());
 215              $mailer->addTemplateData($data);
 216              $mailer->addRecipient($data['email']);
 217  
 218              try {
 219                  $return = $mailer->send();
 220              } catch (\Exception $exception) {
 221                  try {
 222                      Log::add(Text::_($exception->getMessage()), Log::WARNING, 'jerror');
 223  
 224                      $return = false;
 225                  } catch (\RuntimeException $exception) {
 226                      Factory::getApplication()->enqueueMessage(Text::_($exception->errorMessage()), 'warning');
 227  
 228                      $return = false;
 229                  }
 230              }
 231  
 232              // Check for an error.
 233              if ($return !== true) {
 234                  $this->setError(Text::_('COM_USERS_REGISTRATION_ACTIVATION_NOTIFY_SEND_MAIL_FAILED'));
 235  
 236                  return false;
 237              }
 238          } else {
 239              $user->set('activation', '');
 240              $user->set('block', '0');
 241          }
 242  
 243          // Store the user object.
 244          if (!$user->save()) {
 245              $this->setError(Text::sprintf('COM_USERS_REGISTRATION_ACTIVATION_SAVE_FAILED', $user->getError()));
 246  
 247              return false;
 248          }
 249  
 250          return $user;
 251      }
 252  
 253      /**
 254       * Method to get the registration form data.
 255       *
 256       * The base form data is loaded and then an event is fired
 257       * for users plugins to extend the data.
 258       *
 259       * @return  mixed  Data object on success, false on failure.
 260       *
 261       * @since   1.6
 262       * @throws  \Exception
 263       */
 264      public function getData()
 265      {
 266          if ($this->data === null) {
 267              $this->data = new \stdClass();
 268              $app = Factory::getApplication();
 269              $params = ComponentHelper::getParams('com_users');
 270  
 271              // Override the base user data with any data in the session.
 272              $temp = (array) $app->getUserState('com_users.registration.data', array());
 273  
 274              // Don't load the data in this getForm call, or we'll call ourself
 275              $form = $this->getForm(array(), false);
 276  
 277              foreach ($temp as $k => $v) {
 278                  // Here we could have a grouped field, let's check it
 279                  if (is_array($v)) {
 280                      $this->data->$k = new \stdClass();
 281  
 282                      foreach ($v as $key => $val) {
 283                          if ($form->getField($key, $k) !== false) {
 284                              $this->data->$k->$key = $val;
 285                          }
 286                      }
 287                  } elseif ($form->getField($k) !== false) {
 288                      // Only merge the field if it exists in the form.
 289                      $this->data->$k = $v;
 290                  }
 291              }
 292  
 293              // Get the groups the user should be added to after registration.
 294              $this->data->groups = array();
 295  
 296              // Get the default new user group, guest or public group if not specified.
 297              $system = $params->get('new_usertype', $params->get('guest_usergroup', 1));
 298  
 299              $this->data->groups[] = $system;
 300  
 301              // Unset the passwords.
 302              unset($this->data->password1, $this->data->password2);
 303  
 304              // Get the dispatcher and load the users plugins.
 305              PluginHelper::importPlugin('user');
 306  
 307              // Trigger the data preparation event.
 308              Factory::getApplication()->triggerEvent('onContentPrepareData', array('com_users.registration', $this->data));
 309          }
 310  
 311          return $this->data;
 312      }
 313  
 314      /**
 315       * Method to get the registration form.
 316       *
 317       * The base form is loaded from XML and then an event is fired
 318       * for users plugins to extend the form with extra fields.
 319       *
 320       * @param   array    $data      An optional array of data for the form to interrogate.
 321       * @param   boolean  $loadData  True if the form is to load its own data (default case), false if not.
 322       *
 323       * @return  Form  A Form object on success, false on failure
 324       *
 325       * @since   1.6
 326       */
 327      public function getForm($data = array(), $loadData = true)
 328      {
 329          // Get the form.
 330          $form = $this->loadForm('com_users.registration', 'registration', array('control' => 'jform', 'load_data' => $loadData));
 331  
 332          if (empty($form)) {
 333              return false;
 334          }
 335  
 336          // When multilanguage is set, a user's default site language should also be a Content Language
 337          if (Multilanguage::isEnabled()) {
 338              $form->setFieldAttribute('language', 'type', 'frontend_language', 'params');
 339          }
 340  
 341          return $form;
 342      }
 343  
 344      /**
 345       * Method to get the data that should be injected in the form.
 346       *
 347       * @return  mixed  The data for the form.
 348       *
 349       * @since   1.6
 350       */
 351      protected function loadFormData()
 352      {
 353          $data = $this->getData();
 354  
 355          if (Multilanguage::isEnabled() && empty($data->language)) {
 356              $data->language = Factory::getLanguage()->getTag();
 357          }
 358  
 359          $this->preprocessData('com_users.registration', $data);
 360  
 361          return $data;
 362      }
 363  
 364      /**
 365       * Override preprocessForm to load the user plugin group instead of content.
 366       *
 367       * @param   Form    $form   A Form object.
 368       * @param   mixed   $data   The data expected for the form.
 369       * @param   string  $group  The name of the plugin group to import (defaults to "content").
 370       *
 371       * @return  void
 372       *
 373       * @since   1.6
 374       * @throws  \Exception if there is an error in the form event.
 375       */
 376      protected function preprocessForm(Form $form, $data, $group = 'user')
 377      {
 378          $userParams = ComponentHelper::getParams('com_users');
 379  
 380          // Add the choice for site language at registration time
 381          if ($userParams->get('site_language') == 1 && $userParams->get('frontend_userparams') == 1) {
 382              $form->loadFile('sitelang', false);
 383          }
 384  
 385          parent::preprocessForm($form, $data, $group);
 386      }
 387  
 388      /**
 389       * Method to auto-populate the model state.
 390       *
 391       * Note. Calling getState in this method will result in recursion.
 392       *
 393       * @return  void
 394       *
 395       * @since   1.6
 396       * @throws  \Exception
 397       */
 398      protected function populateState()
 399      {
 400          // Get the application object.
 401          $app = Factory::getApplication();
 402          $params = $app->getParams('com_users');
 403  
 404          // Load the parameters.
 405          $this->setState('params', $params);
 406      }
 407  
 408      /**
 409       * Method to save the form data.
 410       *
 411       * @param   array  $temp  The form data.
 412       *
 413       * @return  mixed  The user id on success, false on failure.
 414       *
 415       * @since   1.6
 416       * @throws  \Exception
 417       */
 418      public function register($temp)
 419      {
 420          $params = ComponentHelper::getParams('com_users');
 421  
 422          // Initialise the table with Joomla\CMS\User\User.
 423          $user = new User();
 424          $data = (array) $this->getData();
 425  
 426          // Merge in the registration data.
 427          foreach ($temp as $k => $v) {
 428              $data[$k] = $v;
 429          }
 430  
 431          // Prepare the data for the user object.
 432          $data['email'] = PunycodeHelper::emailToPunycode($data['email1']);
 433          $data['password'] = $data['password1'];
 434          $useractivation = $params->get('useractivation');
 435          $sendpassword = $params->get('sendpassword', 1);
 436  
 437          // Check if the user needs to activate their account.
 438          if (($useractivation == 1) || ($useractivation == 2)) {
 439              $data['activation'] = ApplicationHelper::getHash(UserHelper::genRandomPassword());
 440              $data['block'] = 1;
 441          }
 442  
 443          // Bind the data.
 444          if (!$user->bind($data)) {
 445              $this->setError($user->getError());
 446  
 447              return false;
 448          }
 449  
 450          // Load the users plugin group.
 451          PluginHelper::importPlugin('user');
 452  
 453          // Store the data.
 454          if (!$user->save()) {
 455              $this->setError(Text::sprintf('COM_USERS_REGISTRATION_SAVE_FAILED', $user->getError()));
 456  
 457              return false;
 458          }
 459  
 460          $app = Factory::getApplication();
 461          $db = $this->getDatabase();
 462          $query = $db->getQuery(true);
 463  
 464          // Compile the notification mail values.
 465          $data = $user->getProperties();
 466          $data['fromname'] = $app->get('fromname');
 467          $data['mailfrom'] = $app->get('mailfrom');
 468          $data['sitename'] = $app->get('sitename');
 469          $data['siteurl'] = Uri::root();
 470  
 471          // Handle account activation/confirmation emails.
 472          if ($useractivation == 2) {
 473              // Set the link to confirm the user email.
 474              $linkMode = $app->get('force_ssl', 0) == 2 ? Route::TLS_FORCE : Route::TLS_IGNORE;
 475  
 476              $data['activate'] = Route::link(
 477                  'site',
 478                  'index.php?option=com_users&task=registration.activate&token=' . $data['activation'],
 479                  false,
 480                  $linkMode,
 481                  true
 482              );
 483  
 484              $mailtemplate = 'com_users.registration.user.admin_activation';
 485          } elseif ($useractivation == 1) {
 486              // Set the link to activate the user account.
 487              $linkMode = $app->get('force_ssl', 0) == 2 ? Route::TLS_FORCE : Route::TLS_IGNORE;
 488  
 489              $data['activate'] = Route::link(
 490                  'site',
 491                  'index.php?option=com_users&task=registration.activate&token=' . $data['activation'],
 492                  false,
 493                  $linkMode,
 494                  true
 495              );
 496  
 497              $mailtemplate = 'com_users.registration.user.self_activation';
 498          } else {
 499              $mailtemplate = 'com_users.registration.user.registration_mail';
 500          }
 501  
 502          if ($sendpassword) {
 503              $mailtemplate .= '_w_pw';
 504          }
 505  
 506          // Try to send the registration email.
 507          try {
 508              $mailer = new MailTemplate($mailtemplate, $app->getLanguage()->getTag());
 509              $mailer->addTemplateData($data);
 510              $mailer->addRecipient($data['email']);
 511              $return = $mailer->send();
 512          } catch (\Exception $exception) {
 513              try {
 514                  Log::add(Text::_($exception->getMessage()), Log::WARNING, 'jerror');
 515  
 516                  $return = false;
 517              } catch (\RuntimeException $exception) {
 518                  Factory::getApplication()->enqueueMessage(Text::_($exception->errorMessage()), 'warning');
 519  
 520                  $this->setError(Text::_('COM_MESSAGES_ERROR_MAIL_FAILED'));
 521  
 522                  $return = false;
 523              }
 524          }
 525  
 526          // Send mail to all users with user creating permissions and receiving system emails
 527          if (($params->get('useractivation') < 2) && ($params->get('mail_to_admin') == 1)) {
 528              // Get all admin users
 529              $query->clear()
 530                  ->select($db->quoteName(array('name', 'email', 'sendEmail', 'id')))
 531                  ->from($db->quoteName('#__users'))
 532                  ->where($db->quoteName('sendEmail') . ' = 1')
 533                  ->where($db->quoteName('block') . ' = 0');
 534  
 535              $db->setQuery($query);
 536  
 537              try {
 538                  $rows = $db->loadObjectList();
 539              } catch (\RuntimeException $e) {
 540                  $this->setError(Text::sprintf('COM_USERS_DATABASE_ERROR', $e->getMessage()));
 541  
 542                  return false;
 543              }
 544  
 545              // Send mail to all superadministrators id
 546              foreach ($rows as $row) {
 547                  $usercreator = Factory::getUser($row->id);
 548  
 549                  if (!$usercreator->authorise('core.create', 'com_users') || !$usercreator->authorise('core.manage', 'com_users')) {
 550                      continue;
 551                  }
 552  
 553                  try {
 554                      $mailer = new MailTemplate('com_users.registration.admin.new_notification', $app->getLanguage()->getTag());
 555                      $mailer->addTemplateData($data);
 556                      $mailer->addRecipient($row->email);
 557                      $return = $mailer->send();
 558                  } catch (\Exception $exception) {
 559                      try {
 560                          Log::add(Text::_($exception->getMessage()), Log::WARNING, 'jerror');
 561  
 562                          $return = false;
 563                      } catch (\RuntimeException $exception) {
 564                          Factory::getApplication()->enqueueMessage(Text::_($exception->errorMessage()), 'warning');
 565  
 566                          $return = false;
 567                      }
 568                  }
 569  
 570                  // Check for an error.
 571                  if ($return !== true) {
 572                      $this->setError(Text::_('COM_USERS_REGISTRATION_ACTIVATION_NOTIFY_SEND_MAIL_FAILED'));
 573  
 574                      return false;
 575                  }
 576              }
 577          }
 578  
 579          // Check for an error.
 580          if ($return !== true) {
 581              $this->setError(Text::_('COM_USERS_REGISTRATION_SEND_MAIL_FAILED'));
 582  
 583              // Send a system message to administrators receiving system mails
 584              $db = $this->getDatabase();
 585              $query->clear()
 586                  ->select($db->quoteName('id'))
 587                  ->from($db->quoteName('#__users'))
 588                  ->where($db->quoteName('block') . ' = 0')
 589                  ->where($db->quoteName('sendEmail') . ' = 1');
 590              $db->setQuery($query);
 591  
 592              try {
 593                  $userids = $db->loadColumn();
 594              } catch (\RuntimeException $e) {
 595                  $this->setError(Text::sprintf('COM_USERS_DATABASE_ERROR', $e->getMessage()));
 596  
 597                  return false;
 598              }
 599  
 600              if (count($userids) > 0) {
 601                  $jdate     = new Date();
 602                  $dateToSql = $jdate->toSql();
 603                  $subject   = Text::_('COM_USERS_MAIL_SEND_FAILURE_SUBJECT');
 604                  $message   = Text::sprintf('COM_USERS_MAIL_SEND_FAILURE_BODY', $data['username']);
 605  
 606                  // Build the query to add the messages
 607                  foreach ($userids as $userid) {
 608                      $values = [
 609                          ':user_id_from',
 610                          ':user_id_to',
 611                          ':date_time',
 612                          ':subject',
 613                          ':message',
 614                      ];
 615                      $query->clear()
 616                          ->insert($db->quoteName('#__messages'))
 617                          ->columns($db->quoteName(['user_id_from', 'user_id_to', 'date_time', 'subject', 'message']))
 618                          ->values(implode(',', $values));
 619                      $query->bind(':user_id_from', $userid, ParameterType::INTEGER)
 620                          ->bind(':user_id_to', $userid, ParameterType::INTEGER)
 621                          ->bind(':date_time', $dateToSql)
 622                          ->bind(':subject', $subject)
 623                          ->bind(':message', $message);
 624  
 625                      $db->setQuery($query);
 626  
 627                      try {
 628                          $db->execute();
 629                      } catch (\RuntimeException $e) {
 630                          $this->setError(Text::sprintf('COM_USERS_DATABASE_ERROR', $e->getMessage()));
 631  
 632                          return false;
 633                      }
 634                  }
 635              }
 636  
 637              return false;
 638          }
 639  
 640          if ($useractivation == 1) {
 641              return 'useractivate';
 642          } elseif ($useractivation == 2) {
 643              return 'adminactivate';
 644          } else {
 645              return $user->id;
 646          }
 647      }
 648  }


Generated: Wed Sep 7 05:41:13 2022 Chilli.vc Blog - For Webmaster,Blog-Writer,System Admin and Domainer