Выбор группы пользователем из выпадающего списка при регистрации — различия между версиями

Материал из Umicms
Перейти к:навигация, поиск
Строка 63: Строка 63:
  
  
Находим файл /classes/modules/webforms/, полностью копируем оттуда метод send и вставляем в файл __custom.php, в этой же директории.  
+
Теперь нам нужно написать метод, который обработает введенные пользователем данные и запишет его в выбранную им же группу.
Переименуем его, например, в send_custom.
+
Для этого можно воспользоваться стандартным методом registrate_do, немного его изменив. Идем в  /classes/modules/users/_register.php,
 +
полностью копируем оттуда метод registrate_do и вставляем в файл __custom.php, в этой же директории.  
 +
Переименуем его, например, в registrate_do_custom.
 
Начальный код метода:
 
Начальный код метода:
  
 
<source lang="php">
 
<source lang="php">
public function send_custom() {
+
public
 
+
$objectTypeId = $objectTypes->getBaseType("users", "user");
// Check captcha to know we should do anything
+
if ($customObjectTypeId = getRequest('type-id')) {
if (isset($_REQUEST['captcha'])) {
+
$childClasses = $objectTypes->getChildClasses($objectTypeId);
$_SESSION['user_captcha'] = md5((int) $_REQUEST['captcha']);
+
if (in_array($customObjectTypeId, $childClasses)) {
}
+
$objectTypeId = $customObjectTypeId;
if (!umiCaptcha::checkCaptcha()) {
 
$this->errorNewMessage("%errors_wrong_captcha%");
 
$this->errorPanic();
 
}
 
if (defined('CURRENT_VERSION_LINE') && CURRENT_VERSION_LINE=='demo') {
 
$url = getRequest('ref_onsuccess');
 
if (!$url) $url = $this->pre_lang . "/webforms/posted/";
 
$this->redirect($url);
 
}
 
 
 
//-------------------------------------------------------------------
 
// Get necessary data
 
$sMsgBody    = '';
 
$oTypes      = umiObjectTypesCollection::getInstance();
 
$iBaseTypeId = $oTypes->getBaseType("webforms", "form");
 
$iFormTypeId = getRequest('system_form_id');
 
$sSenderIP  = getServer('REMOTE_ADDR');
 
$iTime      = new umiDate( time() );
 
$aAddresses  = getRequest('system_email_to');
 
if(!is_array($aAddresses)) $aAddresses = array($aAddresses);
 
$aRecipients = array();
 
foreach($aAddresses as $address){
 
$sEmailTo = $this->guessAddressValue($address);
 
$sAddress = $this->guessAddressName($address);
 
$aRecipients[] = array('email'=>$sEmailTo, 'name'=>$sAddress);
 
}
 
 
 
if(!$oTypes->isExists($iFormTypeId) || $oTypes->getParentClassId($iFormTypeId) != $iBaseTypeId) {
 
$this->errorNewMessage("%wrong_form_type%");
 
$this->errorPanic();
 
}//
 
if(($ef = $this->checkRequiredFields($iFormTypeId)) !== true) {
 
$this->errorNewMessage(getLabel('error-required_list').$this->assembleErrorFields($ef));
 
}
 
//-------------------------------------------------------------------
 
// Saving message and preparing it for sending
 
$_REQUEST['data']['new']['sender_ip'] = $sSenderIP;  // Hack for saving files-only-forms
 
$oObjectsCollection = umiObjectsCollection::getInstance();
 
$iObjectId          = $oObjectsCollection->addObject($sAddress, $iFormTypeId);
 
cmsController::getInstance()->getModule('data')->saveEditedObject($iObjectId, true);
 
$oObject            = $oObjectsCollection->getObject($iObjectId);
 
$oObject->setValue('destination_address', $sEmailTo);
 
$oObject->setValue('sender_ip', $sSenderIP);
 
$oObject->setValue('sending_time', $iTime);
 
$aMessage          = $this->formatMessage($iObjectId, true);
 
//--------------------------------------------------------------------
 
// Make an e-mail
 
$oMail = new umiMail();
 
//--------------------------------------------------------------------
 
// Determine file fields
 
$aFTypes    = array('file', 'img_file', 'swf_file');
 
$aFields    = $oTypes->getType($oObject->getTypeId())->getAllFields();
 
$aFileFields = array();
 
foreach($aFields as $oField) {
 
$oType  = $oField->getFieldType();
 
if(in_array($oType->getDataType(), $aFTypes)) {
 
$oFile = $oObject->getValue($oField->getName());
 
 
 
if($oFile instanceof umiFile) {
 
$oMail->attachFile($oFile);
 
} /*else {
 
$this->errorNewMessage("%errors_wrong_file_type%");
 
$this->errorPanic();
 
}*/
 
 
 
}
 
}
 
$recpCount = 0;
 
foreach($aRecipients as $recipient) {
 
foreach(explode(',', $recipient['email']) as $sAddress) {
 
if(strlen(trim($sAddress))) {
 
$oMail->addRecipient( trim($sAddress), $recipient['name'] );
 
$recpCount++;
 
 
}
 
}
 
}
 
}
}
+
 
if(!$recpCount) {
+
$this->errorNewMessage(getLabel('error-no_recipients'));
+
}
+
$registrationMail->setFrom($email_from, $fio_from);
$oMail->setFrom($aMessage['from_email_template'], $aMessage['from_template']);
+
$registrationMail->setSubject($mailSubject);
$oMail->setSubject($aMessage['subject_template']);
+
$registrationMail->setContent($mailContent);
$oMail->setContent($aMessage['master_template']);
+
$registrationMail->commit();
$oMail->commit();
+
$r
$oMail->send();
+
//--------------------------------------------------------------------
+
// Send autoreply if should
+
if(strlen($aMessage['autoreply_template'])) {
 
$oMailReply = new umiMail();
 
$oMailReply->addRecipient( $aMessage['from_email_template'], $aMessage['from_template'] );
 
$oMailReply->setFrom($aMessage['autoreply_from_email_template'], $aMessage['autoreply_from_template']);
 
$oMailReply->setSubject($aMessage['autoreply_subject_template']);
 
$oMailReply->setContent($aMessage['autoreply_template']);
 
$oMailReply->commit();
 
$oMailReply->send();
 
}
 
//--------------------------------------------------------------------
 
// Process events
 
$oEventPoint = new umiEventPoint("webforms_post");
 
$oEventPoint->setMode("after");
 
$oEventPoint->setParam("email", $aMessage['from_email_template']);
 
$oEventPoint->setParam("message_id", $iObjectId);
 
$oEventPoint->setParam("form_id", $iFormTypeId);
 
$oEventPoint->setParam("fio", $aMessage['from_template']);
 
$this->setEventPoint($oEventPoint);
 
//--------------------------------------------------------------------
 
// Redirecting
 
$sRedirect = getRequest('ref_onsuccess');
 
if($sRedirect) $this->redirect($sRedirect);
 
//--------------------------------------------------------------------
 
// Or showing the message
 
$sTemplateName = getRequest('system_template');
 
if($sTemplateName) {
 
list($sSuccessString) = def_module::loadTemplates("data/reflection/".$sTemplateName, "send_successed");
 
if(strlen($sSuccessString)) return $sSuccessString;
 
}
 
//--------------------------------------------------------------------
 
// If we're still here
 
if(isset($_SERVER['HTTP_REFERER'])) $this->redirect($_SERVER['HTTP_REFERER']);
 
return '';
 
}
 
 
</source>
 
</source>
 
Так как на сайте может использоваться много форм, а нам необходимо, чтобы адреса менялись только у одной, добавим проверку на принадлежность сообщения к форме после строки:
 
Так как на сайте может использоваться много форм, а нам необходимо, чтобы адреса менялись только у одной, добавим проверку на принадлежность сообщения к форме после строки:
Строка 205: Строка 100:
  
 
<source lang="php">
 
<source lang="php">
if($iFormTypeId=='id_формы_обратной_связи'){
+
public function registrate_do($template = "default") {
$apteca = $_REQUEST['data']['new']['идентификатор_поля_выпадающего_списка'];
+
if ($this->is_auth()) {
if($value=='id_позиции в справочнике'){
+
$this->redirect($this->pre_lang . "/");
+
}
$AdressObject = umiObjectsCollection::getObject('id_объекта_список_адресов');
+
if (!($template = getRequest('template'))) {
$sEmailTo=$AdressObject->getValue('address_list');
+
$template = 'default';
$sAddress=$AdressObject->getName();
+
}
trim($sEmailTo);
+
$objectTypes = umiObjectTypesCollection::getInstance();
 +
$regedit = regedit::getInstance();
 +
 
 +
$refererUrl = getServer('HTTP_REFERER');
 +
$without_act = (bool) $regedit->getVal("//modules/users/without_act");
 +
 
 +
$objectTypeId = $objectTypes->getBaseType("users", "user");
 +
if ($customObjectTypeId = getRequest('type-id')) {
 +
$childClasses = $objectTypes->getChildClasses($objectTypeId);
 +
if (in_array($customObjectTypeId, $childClasses)) {
 +
$objectTypeId = $customObjectTypeId;
 +
}
 +
}
 +
 
 +
$objectType = $objectTypes->getType($objectTypeId);
 +
 
 +
$this->errorSetErrorPage($refererUrl);
 +
 
 +
$login = $this->validateLogin(getRequest('login'), false, true);
 +
$password = $this->validatePassword(getRequest('password'), getRequest('password_confirm'), getRequest('login'), true);
 +
$email = $this->validateEmail(getRequest('email'), false, !$without_act);
 +
 
 +
//Captcha validation
 +
if (isset($_REQUEST['captcha'])) {
 +
$_SESSION['user_captcha'] = md5((int) getRequest('captcha'));
 +
}
 +
 
 +
if (!umiCaptcha::checkCaptcha()) {
 +
$this->errorAddErrors('errors_wrong_captcha');
 +
}
 +
 
 +
$this->errorThrow('public');
 +
 
 +
$oEventPoint = new umiEventPoint("users_registrate");
 +
$oEventPoint->setMode("before");
 +
$oEventPoint->setParam("login", $login);
 +
$oEventPoint->addRef("password", $password);
 +
$oEventPoint->addRef("email", $email);
 +
$this->setEventPoint($oEventPoint);
 +
 
 +
//Creating user...
 +
$objectId = umiObjectsCollection::getInstance()->addObject($login, $objectTypeId);
 +
$activationCode = md5($login . time());
 +
 
 +
$object = umiObjectsCollection::getInstance()->getObject($objectId);
 +
 
 +
$object->setValue("login", $login);
 +
$object->setValue("password", md5($password));
 +
$object->setValue("e-mail", $email);
 +
 
 +
$object->setValue("is_activated", $without_act);
 +
$object->setValue("activate_code", $activationCode);
 +
$object->setValue("referer", urldecode(getSession("http_referer")));
 +
$object->setValue("target", urldecode(getSession("http_target")));
 +
$object->setValue("register_date", umiDate::getCurrentTimeStamp());
 +
$object->setOwnerId($objectId);
 +
 
 +
if ($without_act) {
 +
$_SESSION['cms_login'] = $login;
 +
$_SESSION['cms_pass'] = md5($password);
 +
$_SESSION['user_id'] = $objectId;
 +
 
 +
session_commit();
 +
}
 +
 
 +
$group_id = regedit::getInstance()->getVal("//modules/users/def_group");
 +
$object->setValue("groups", Array($group_id));
 +
 
 +
cmsController::getInstance()->getModule('data');
 +
$data_module = cmsController::getInstance()->getModule('data');
 +
$data_module->saveEditedObjectWithIgnorePermissions($objectId, true, true);
 +
 
 +
$object->commit();
 +
 
 +
if ($eshop_module = cmsController::getInstance()->getModule('eshop')) {
 +
$eshop_module->discountCardSave($objectId);
 +
}
 +
 
 +
//Forming mail...
 +
list(
 +
$template_mail, $template_mail_subject, $template_mail_noactivation, $template_mail_subject_noactivation
 +
) = def_module::loadTemplatesForMail("users/register/".$template,
 +
"mail_registrated", "mail_registrated_subject", "mail_registrated_noactivation", "mail_registrated_subject_noactivation"
 +
);
 +
 
 +
if ($without_act && $template_mail_noactivation && $template_mail_subject_noactivation) {
 +
$template_mail = $template_mail_noactivation;
 +
$template_mail_subject = $template_mail_subject_noactivation;
 
}
 
}
else if($value=='id_позиции в справочнике'){
+
 
$AdressObject = umiObjectsCollection::getObject('id_объекта_список_адресов');
+
$mailData = array(
$sEmailTo=$AdressObject->getValue('address_list');
+
'user_id' => $objectId,
$sAddress=$AdressObject->getName();
+
'domain' => $domain = cmsController::getInstance()->getCurrentDomain()->getCurrentHostName(),
trim($sEmailTo);
+
'activate_link' => "http://" . $domain . $this->pre_lang . "/users/activate/" . $activationCode . "/",
+
'login' => $login,
 +
'password' => $password,
 +
'lname' => $object->getValue("lname"),
 +
'fname' => $object->getValue("fname"),
 +
'father_name' => $object->getValue("father_name"),
 +
);
 +
 
 +
$mailContent = def_module::parseTemplateForMail($template_mail, $mailData, false, $objectId);
 +
$mailSubject = def_module::parseTemplateForMail($template_mail_subject, $mailData, false, $objectId);
 +
 
 +
$fio = $object->getValue("lname") . " " . $object->getValue("fname") . " " . $object->getValue("father_name");
 +
 
 +
$email_from = regedit::getInstance()->getVal("//settings/email_from");
 +
$fio_from = regedit::getInstance()->getVal("//settings/fio_from");
 +
 
 +
 
 +
$registrationMail = new umiMail();
 +
$registrationMail->addRecipient($email, $fio);
 +
$registrationMail->setFrom($email_from, $fio_from);
 +
$registrationMail->setSubject($mailSubject);
 +
$registrationMail->setContent($mailContent);
 +
$registrationMail->commit();
 +
$registrationMail->send();
 +
 
 +
$oEventPoint = new umiEventPoint("users_registrate");
 +
$oEventPoint->setMode("after");
 +
$oEventPoint->setParam("user_id", $objectId);
 +
$oEventPoint->setParam("login", $login);
 +
$this->setEventPoint($oEventPoint);
 +
 
 +
if ($without_act) {
 +
$this->redirect($this->pre_lang . "/users/registrate_done/?result=without_activation");
 +
} else {
 +
$this->redirect($this->pre_lang . "/users/registrate_done/");
 
}
 
}
                        ......//продолжите, если необходимо
+
}
 
}
 
 
</source>
 
</source>
  

Версия 14:42, 31 января 2014

Актуально для версии 2.9.5

Данное решение рассмотрено на примере интернет-магазина "Современный", шаблон demodizzy.

Задача

Предположим, необходимо дать пользователю при регистрации возможность выбрать группу. Например, пользователь может зарегистрироваться как оптовый покупатель или розничный покупатель.

Решение

В первую очередь, необходимо написать кастомный макрос, который будет выбирать определенные группы пользователей для вывода их в выпадающем списке, так, чтобы в выборку не были включены группы "зарегистрированные пользователи" и "супервайзеры". Добавим в модуле шаблоны данных для типа "группы пользователей" поле типа чекбокс с названием, например, "для регистрации" и отметим в модуле пользователи этот чекбокс у необходимых групп.

Открываем файл /classes/modules/users/_custom.php и вставляем туда следующий метод:

public function selected_groups($template = 'default'){
		
	$groups = new selector('objects');
	$groups->types('object-type')->id('36');
	$groups->where('for_registration')->equals('1');
			
	list($itemsTemplate, $itemTemplate) = def_module::loadTemplates("users/{$template}", "items", "item");	
	$item = array();
	$items = array();
	foreach($groups as $group){
		$item['attribute:id'] = $group->getId();
		$item['attribute:name'] =  $group->getValue('nazvanie');
		$items[] = def_module::parseTemplate($itemTemplate, $item);
	}
	$items = array('subnodes:items' => $items);
	return def_module::parseTemplate($itemsTemplate, $items);
}

Теперь,идем в шаблон, по которому выводится форма регистрации(templates/demodizzy/xslt/modules/users/registration.xsl) и добавим туда вызов макроса:

<div>
     <label class="required">
         <span>
	      <xsl:text>группа:</xsl:text>
	</span>
	<xsl:apply-templates select="document('udata://users/selected_groups/')/udata" />
     </label>
</div>

и шаблон обработки результатов, который будет выводить выбранные группы в выпадающем списке:

<xsl:template match="udata[@module = 'users'][@method = 'selected_groups']">
	<select name = 'group' id = 'group'>
		<xsl:for-each select = "./items/item">
			<option value = "{./@id}">
			         <xsl:value-of select = "./@name"/>
			</option>
		</xsl:for-each>
	</select>
</xsl:template>


Теперь нам нужно написать метод, который обработает введенные пользователем данные и запишет его в выбранную им же группу. Для этого можно воспользоваться стандартным методом registrate_do, немного его изменив. Идем в /classes/modules/users/_register.php, полностью копируем оттуда метод registrate_do и вставляем в файл __custom.php, в этой же директории. Переименуем его, например, в registrate_do_custom. Начальный код метода:

public
			$objectTypeId = $objectTypes->getBaseType("users", "user");
			if ($customObjectTypeId = getRequest('type-id')) {
				$childClasses = $objectTypes->getChildClasses($objectTypeId);
				if (in_array($customObjectTypeId, $childClasses)) {
					$objectTypeId = $customObjectTypeId;
				}
			}

		
			
			$registrationMail->setFrom($email_from, $fio_from);
			$registrationMail->setSubject($mailSubject);
			$registrationMail->setContent($mailContent);
			$registrationMail->commit();
			$r

Так как на сайте может использоваться много форм, а нам необходимо, чтобы адреса менялись только у одной, добавим проверку на принадлежность сообщения к форме после строки:

$iTime       = new umiDate( time() );

Если идентификатор формы обратной связи тот, который необходим, то, далее метод проверяет значение поля и, в зависимости от значения, выбирает нужный адрес и получателя:

public function registrate_do($template = "default") {
			if ($this->is_auth()) {
				$this->redirect($this->pre_lang . "/");
			}
			if (!($template = getRequest('template'))) {
				$template = 'default';
			}
			$objectTypes = umiObjectTypesCollection::getInstance();
			$regedit = regedit::getInstance();

			$refererUrl = getServer('HTTP_REFERER');
			$without_act = (bool) $regedit->getVal("//modules/users/without_act");

			$objectTypeId = $objectTypes->getBaseType("users", "user");
			if ($customObjectTypeId = getRequest('type-id')) {
				$childClasses = $objectTypes->getChildClasses($objectTypeId);
				if (in_array($customObjectTypeId, $childClasses)) {
					$objectTypeId = $customObjectTypeId;
				}
			}

			$objectType = $objectTypes->getType($objectTypeId);

			$this->errorSetErrorPage($refererUrl);

			$login = $this->validateLogin(getRequest('login'), false, true);
			$password = $this->validatePassword(getRequest('password'), getRequest('password_confirm'), getRequest('login'), true);
			$email = $this->validateEmail(getRequest('email'), false, !$without_act);

			//Captcha validation
			if (isset($_REQUEST['captcha'])) {
				$_SESSION['user_captcha'] = md5((int) getRequest('captcha'));
			}

			if (!umiCaptcha::checkCaptcha()) {
				$this->errorAddErrors('errors_wrong_captcha');
			}

			$this->errorThrow('public');

			$oEventPoint = new umiEventPoint("users_registrate");
			$oEventPoint->setMode("before");
			$oEventPoint->setParam("login", $login);
			$oEventPoint->addRef("password", $password);
			$oEventPoint->addRef("email", $email);
			$this->setEventPoint($oEventPoint);

			//Creating user...
			$objectId = umiObjectsCollection::getInstance()->addObject($login, $objectTypeId);
			$activationCode = md5($login . time());

			$object = umiObjectsCollection::getInstance()->getObject($objectId);

			$object->setValue("login", $login);
			$object->setValue("password", md5($password));
			$object->setValue("e-mail", $email);

			$object->setValue("is_activated", $without_act);
			$object->setValue("activate_code", $activationCode);
			$object->setValue("referer", urldecode(getSession("http_referer")));
			$object->setValue("target", urldecode(getSession("http_target")));
			$object->setValue("register_date", umiDate::getCurrentTimeStamp());
			$object->setOwnerId($objectId);

			if ($without_act) {
				$_SESSION['cms_login'] = $login;
				$_SESSION['cms_pass'] = md5($password);
				$_SESSION['user_id'] = $objectId;

				session_commit();
			}

			$group_id = regedit::getInstance()->getVal("//modules/users/def_group");
			$object->setValue("groups", Array($group_id));

			cmsController::getInstance()->getModule('data');
			$data_module = cmsController::getInstance()->getModule('data');
			$data_module->saveEditedObjectWithIgnorePermissions($objectId, true, true);

			$object->commit();

			if ($eshop_module = cmsController::getInstance()->getModule('eshop')) {
				$eshop_module->discountCardSave($objectId);
			}

			//Forming mail...
			list(
				$template_mail, $template_mail_subject, $template_mail_noactivation, $template_mail_subject_noactivation
			) = def_module::loadTemplatesForMail("users/register/".$template,
				"mail_registrated", "mail_registrated_subject", "mail_registrated_noactivation", "mail_registrated_subject_noactivation"
			);

			if ($without_act && $template_mail_noactivation && $template_mail_subject_noactivation) {
				$template_mail = $template_mail_noactivation;
				$template_mail_subject = $template_mail_subject_noactivation;
			}

			$mailData = array(
				'user_id' => $objectId,
				'domain' => $domain = cmsController::getInstance()->getCurrentDomain()->getCurrentHostName(),
				'activate_link' => "http://" . $domain . $this->pre_lang . "/users/activate/" . $activationCode . "/",
				'login' => $login,
				'password' => $password,
				'lname' => $object->getValue("lname"),
				'fname' => $object->getValue("fname"),
				'father_name' => $object->getValue("father_name"),
			);

			$mailContent = def_module::parseTemplateForMail($template_mail, $mailData, false, $objectId);
			$mailSubject = def_module::parseTemplateForMail($template_mail_subject, $mailData, false, $objectId);

			$fio = $object->getValue("lname") . " " . $object->getValue("fname") . " " . $object->getValue("father_name");

			$email_from = regedit::getInstance()->getVal("//settings/email_from");
			$fio_from = regedit::getInstance()->getVal("//settings/fio_from");


			$registrationMail = new umiMail();
			$registrationMail->addRecipient($email, $fio);
			$registrationMail->setFrom($email_from, $fio_from);
			$registrationMail->setSubject($mailSubject);
			$registrationMail->setContent($mailContent);
			$registrationMail->commit();
			$registrationMail->send();

			$oEventPoint = new umiEventPoint("users_registrate");
			$oEventPoint->setMode("after");
			$oEventPoint->setParam("user_id", $objectId);
			$oEventPoint->setParam("login", $login);
			$this->setEventPoint($oEventPoint);

			if ($without_act) {
				$this->redirect($this->pre_lang . "/users/registrate_done/?result=without_activation");
			} else {
				$this->redirect($this->pre_lang . "/users/registrate_done/");
			}
		}

Стандартное получение адреса заключим в else{}:

else{
			$aAddresses  = getRequest('system_email_to');
			if(!is_array($aAddresses)) $aAddresses = array($aAddresses);
			$aRecipients = array();
			foreach($aAddresses as $address){
				$sEmailTo = $this->guessAddressValue($address);
				$sAddress = $this->guessAddressName($address);
				$aRecipients[] = array('email'=>$sEmailTo, 'name'=>$sAddress);
			}
}

Далее, добавим проверку на то, каким образом мы получаем адрес, и смену адреса, в случае, если сообщение отправлено с "нужной" формы, после строки:

$recpCount = 0;

Проверка:

		if (isset($aRecipients)){
			foreach($aRecipients as $recipient) {
				foreach(explode(',', $recipient['email']) as $sAddress) {
					if(strlen(trim($sAddress))) {
						$oMail->addRecipient( trim($sAddress), $recipient['name'] );

						$recpCount++;
					}
				}
			}
		}
		else{
		
			$oMail->addRecipient( $sEmailTo, $sAddress );
				if(!empty($sEmailTo)){
					$recpCount++;
				}
		}

Теперь, осталось только изменить в шаблоне формы обратной связи action на "%pre_lang%/webforms/send_custom/ и добавить permissions.custom.php в директорию класса webforms