Как стать автором
Обновить

Авторизация на сайте средствами phpBB/XenForo

Время на прочтение5 мин
Количество просмотров4.7K
Примерно год назад мне потребовалось дать возможность пользователям зарегистрированным на форуме (phpBB) авторизовываться на сайте (modX). На тот момент форум уже работал и пользователи активно общались. Решения MODxBB тогда еще не было и пришлось фантазировать.

В итоге получилось что-то вроде этого
<?php
global $modx, $phpbb_root_path, $phpEx, $user, $db, $config, $cache, $template, $auth;

$phpbb_root_path = $modx->config['base_path'] . 'forum/';
define('IN_PHPBB', true);
$phpEx = "php";

include($phpbb_root_path . 'includes/functions_install.' . $phpEx);
include($phpbb_root_path . 'includes/functions_display.' . $phpEx);
include($phpbb_root_path . 'common.' . $phpEx);
include($phpbb_root_path . 'includes/captcha/captcha_factory.' . $phpEx);

$user->session_begin();
$auth->acl($user->data);

$user->setup('ucp');

$login = array();

if(isset($_POST['logoutForum']) && $user->data['user_id'] != ANONYMOUS) $user->session_kill(); //Покидаем кабинет

if(isset($_POST['login']) && $user->data['user_id'] == ANONYMOUS){
	$username = request_var('username', '', true);
	$password = request_var('password', '', true);
	$autologin	= (!empty($_POST['autologin'])) ? true : false;
	$viewonline	= (!empty($_POST['viewonline'])) ? false : true;
	$login = $auth->login($username, $password, $autologin, $viewonline);
}

header('Content-type: text/html; charset=UTF-8');
header('Cache-Control: private, no-cache="set-cookie"');
header('Expires: 0');
header('Pragma: no-cache');

if((!empty($login) && $login['status'] == LOGIN_SUCCESS) || $user->data['user_id'] != ANONYMOUS){
	if(!empty($login)) $auth->acl($user->data);
	
	$modx->setPlaceholder('UserName',get_username_string('full', $user->data['user_id'], $user->data['username'], $user->data['user_colour']));
	echo $modx->getChunk('ExitBlock');
	/*
		Hello [+UserName+] <form method="post" action="/[~[*id*]~]"><input type="submit" name="logoutForum" value="Выход" /></form>
	*/
}
else{
	if(isset($login['error_msg']) && $login['error_msg']){ //Обработка ошибок
		$err = $user->lang[$login['error_msg']];
		if ($login['error_msg'] == 'LOGIN_ERROR_USERNAME' || $login['error_msg'] == 'LOGIN_ERROR_PASSWORD'){
			$err = (!$config['board_contact']) ? sprintf($user->lang[$login['error_msg']], '', '') : sprintf($user->lang[$login['error_msg']], '<a hrеf="mailtо:' . htmlspecialchars($config['board_contact']) . '">', '</a>');
		}	

		if($login['error_msg']=='LOGIN_ERROR_ATTEMPTS'){ //Брут?
			$captcha = & phpbb_captcha_factory::get_instance($config['captcha_plugin']);
			$captcha->init(CONFIRM_LOGIN);
			$template->assign_vars(array('CAPTCHA_TEMPLATE'	=> $captcha->get_template()));
			$err = $user->lang[$login['error_msg']];
			$err.='<br /><img srс="/forum/ucp.php?mode=confirm&confirm_id='.$template->_rootref['CONFIRM_IMAGE_LINK'].'" alt="Код подтверждения"  /><br />
			Код с картинки: <input type="text" name="confirm_code" id="confirm_code" size="8" maxlength="8"  title="Код подтверждения" /><input type="hidden" name="confirm_id" id="confirm_id" value="'.$template->_rootref['CONFIRM_ID'].'" title="Код  подтверждения" /><br />';	
		}
		$modx->setPlaceholder('ErrorMsg',$err);
	}
	echo $modx->getChunk('forumLoginForm');
	/*
		<form method="post" action="">
		[+ErrorMsg+]<BR>
		Логин: <input type="text" name="username" id="username" size="10" title="login" /><br />
		Пароль: <input type="password" name="password" id="password" size="10" title="password" /><br />
		<input type="submit" name="login" value="Вход" />
		</form>
	*/
}
?>


Код конечно не идеальный, но он работал безотказно.
Топик бы на этом и закончился, если бы в один прекрасный день не пришла в голову мысль сменить движок форума. Побродив по интернету было решено ставить XenForo. Определяющими факторами стали такие пункты как:
  1. Социальные плюшки из коробки
  2. Возможность импорта пользователей, топиков и сообщений с форума phpBB 3.0
  3. Комфортный код
  4. Активное сообщество


Download, Install, Import... Причем импорт делался с сохранением ID-шников, чтобы можно было без заморочек перенаправить пользователя зашедшего на сайт по ссылке старого форума на новую страницу.
Теперь было необходимо восстановить работоспособность формы авторизации на самом сайте. Как оказалось это не так уж и сложно, ведь код XenForo предельно понятен.
<?php
$noauth=isset($noauth)? $noauth : ''; //еще не авторизованым что показывать?

$fileDir=$modx->config['base_path'].'forum/';
$startTime = microtime(true);
require ($fileDir . '/library/XenForo/Autoloader.php');
XenForo_Autoloader::getInstance()->setupAutoloader($fileDir . '/library');

XenForo_Application::modxParserActive(); //Говорим XenForo, что у нас свой обработчик ошибок
XenForo_Application::initialize($fileDir . '/library', $fileDir);
XenForo_Application::set('page_start_time', $startTime);

XenForo_Session::startPublicSession();
$xfUser = XenForo_Visitor::getInstance();
$data=array();

if($xfUser->get('user_id')=='0'){
	$data['back']=isset($_SERVER['REQUEST_URI'])?$_SERVER['REQUEST_URI']:'/';
    $data['linkauth']='forum/login/login';
	$data['noauth']=$modx->getChunk($noauth); //Вам нужно авторизоваться
	echo $modx->parseChunk('forumLoginForm', $data,'[+','+]');
/*[+noauth+]<BR>
		<form action="/[+linkauth+]" mеthod="post" сlass="xenForm " id="login" style="display: block">
			<р>Логин/e-mail: <inрut type="text" name="login" id="LoginControl" class="textCtrl" tabindex="101">&nbsp;&nbsp;&nbsp;&nbsp;Пароль:<inрut type="password" name="password" class="textCtrl" id="ctrl_password" tabindex="102">&nbsp;&nbsp;&nbsp;&nbsp;<inрut type="submit" class="button primary" value="Вход" tabindex="104"></р>
				<inрut type="hidden" name="remember" value="1" id="ctrl_remember">
		  <inрut type="hidden" name="cookie_check" value="1">
		  <inрut type="hidden" name="redirect" value="[+back+]">
		  <inрut type="hidden" name="_xfToken" value="">
		</fоrm>*/
	
}else{
	$data['UserName']=$xfUser->get('username');
	echo $modx->parseChunk('ExitBlock', $data,'[+','+]');
}
?>


А вот теперь начинается самое интересно: я поясню что же это за загадочная функция modxParserActive.

Открываем файл Application.php из папки library/XenForo/ и в класс XenForo_Application дописываем определение новой переменной
protected static $_modxParser = false;

Затем определяем новые функции

public static function modxParserActive()
{
	self::$_modxParser = true;
}
public static function GetModxParser()
{
	return self::$_modxParser;
}

И последний штрих. В функции beginApplication оборачиваем код
@ini_set('output_buffering', false);

// see http://bugs.php.net/bug.php?id=36514
if (!@ini_get('output_handler')) while (@ob_end_clean());

error_reporting(E_ALL | E_STRICT & ~8192);
set_error_handler(array('XenForo_Application', 'handlePhpError'));
set_exception_handler(array('XenForo_Application', 'handleException'));


в следующее условие

if(!self::GetModxParser()){
…...
}


Да, я знаю, что лезть код движка не самая лучшая идея, но это именно в этом то и была вся соль. Данного поста. Пока это единственный способ, которым я смог обойти конфликт совместимости modx и XenForo. Дело в том, что modx парсит чанки, сниппеты с использованием именно ob_end_clean; А т. к. эта функция была вызвана ранее modx получает пустой буфер со всеми вытекающими последствиями.
Теги:
Хабы:
Если эта публикация вас вдохновила и вы хотите поддержать автора — не стесняйтесь нажать на кнопку
Всего голосов 4: ↑4 и ↓0+4
Комментарии2

Публикации

Истории

Ближайшие события

2 – 18 декабря
Yandex DataLens Festival 2024
МоскваОнлайн
11 – 13 декабря
Международная конференция по AI/ML «AI Journey»
МоскваОнлайн
25 – 26 апреля
IT-конференция Merge Tatarstan 2025
Казань