Я пытаюсь интегрировать медиавики на свой сайт, но у меня проблемы. Я думаю, что проблема имеет какое-то отношение к файлам cookie, потому что я получаю успех от API mediawiki.
Вот мой код:
function mw_session_manager($Action = "") { $Root = $_SERVER['SERVER_ADDR']; $API_Location = "${Root}/w/api.php"; $expire = 60*60*24*14 + time(); $CookieFilePath = tempnam("/tmp/thedirectory", "CURLCOOKIE"); $CookiePrefix = 'theprefix'; $Domain = 'thedomain'; if($Action == 'login') { // Retrieves email address and password from sign-in form $Email = $_POST['LogInEmail']; $LgPassword = $_POST['LogInPassword']; // Query to retrieve username from database based on email. It is implied that authentication has already succeeded. $Query = "SELECT Username FROM Accounts WHERE Email = '$Email'"; $ResultSet = mysql_query($Query); $ResultArray = mysql_fetch_array($ResultSet); $LgName = $ResultArray[0]; // Username // set variables to use in curl_setopts $PostFields = "action=login&lgname=$LgName&lgpassword=$LgPassword&format=php"; // first http post to sign in to MediaWiki $ch = curl_init(); curl_setopt($ch, CURLOPT_URL, "$API_Location"); curl_setopt($ch, CURLOPT_POSTFIELDS, "$PostFields"); curl_setopt($ch, CURLOPT_POST, 1); curl_setopt($ch, CURLOPT_COOKIEJAR, $CookieFilePath); curl_setopt($ch, CURLOPT_COOKIEFILE, $CookieFilePath); curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); $ResultSerialized = curl_exec($ch); curl_close($ch); // curl closed $ResultUnserialized = unserialize($ResultSerialized); $Token = $ResultUnserialized[login][token]; // cookie must be set using session id from first response $WikiSessionID = $ResultUnserialized[login][sessionid]; setcookie("${CookiePrefix}_session", $WikiSessionID, $expire, '/', $Domain); // second http post to finish sign in $ch = curl_init(); curl_setopt($ch, CURLOPT_URL, "$API_Location"); curl_setopt($ch, CURLOPT_POSTFIELDS, "action=login&lgname=${LgName}&lgpassword=${LgPassword}&lgtoken=${Token}&format=php"); curl_setopt($ch, CURLOPT_POST, 1); curl_setopt($ch, CURLOPT_COOKIEJAR, $CookieFilePath); curl_setopt($ch, CURLOPT_COOKIEFILE, $CookieFilePath); curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); $ResultSerialized = curl_exec($ch); curl_close($ch); // curl closed $ResultUnserialized = unserialize($ResultSerialized); // set persistent cookies $LgToken = $ResultUnserialized["login"]["lgtoken"]; $LgUserID = $ResultUnserialized["login"]["lguserid"]; $LgUserName = $ResultUnserialized["login"]["lgusername"]; setcookie("${CookiePrefix}UserName", $LgUserName, $expire, '/', $Domain); setcookie("${CookiePrefix}UserID", $LgUserID, $expire, '/', $Domain); setcookie("${CookiePrefix}Token", $LgToken, $expire, '/', $Domain); // Delete cURL cookie unlink($CookieFilePath); return $somedebuggingvariable; } if($Action = "logout") { $ch = curl_init(); curl_setopt($ch, CURLOPT_URL, "$API_Location"); curl_setopt($ch, CURLOPT_POSTFIELDS, "action=logout"); curl_setopt($ch, CURLOPT_POST, 1); curl_setopt($ch, CURLOPT_COOKIEJAR, $CookieFilePath); curl_setopt($ch, CURLOPT_COOKIEFILE, $CookieFilePath); curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); $ResultSerialized = curl_exec($ch); $LogoutReturn = unserialize($ResultSerialized); $_SESSION['APIReturn'] = $LogoutReturn; curl_close($ch); // curl closed // destroys persistent cookies and ends session $expire = time() - 60*60*24*90; setcookie('Session', '', $expire, '/', $Domain); setcookie("${CookiePrefix}_session", '', $expire, '/', $Domain); setcookie("${CookiePrefix}UserName", '', $expire, '/', $Domain); setcookie("${CookiePrefix}UserID", '', $expire, '/', $Domain); setcookie("${CookiePrefix}Token", '', $expire, '/', $Domain); // delete cURL cookie unlink($CookieFilePath); } }
Я также заметил, что если я поставлю плохой токен, API все равно вернется к успеху, так что я тоже не могу обойти это.
Редактирование: теперь я отлично его работаю и обновил код до текущего рабочего кода.
Похоже, вы пытаетесь реализовать единый механизм входа для своего сайта и MediaWiki, используя PHP-скрипт на своем веб-сайте, который регистрирует пользователя в MediaWiki с помощью API.
Проблема заключается в том, что, хотя ваш сценарий действительно успешно регистрируется в MediaWiki с использованием учетных данных пользователя, он не передает файлы cookie проверки подлинности MediaWiki обратно пользователю.
Есть несколько способов решить эту проблему:
Возможно, самым простым решением было бы полностью обрабатывать процесс входа в MediaWiki на стороне клиента с помощью JavaScript / AJAX. Таким образом, файлы cookie будут отправляться непосредственно в браузер пользователя. С другой стороны, конечно, это не будет работать для пользователей, которые не могут или не хотят запускать JavaScript (но вы всегда можете позволить им просто войти в MediaWiki обычным способом).
Вы также можете сделать только первый шаг процесса входа (получение маркера) на стороне сервера, а затем запросить URL-адрес второго шага напрямую, используя его как источник невидимого iframe
на возвращенной странице HTML. Это не требует JavaScript, но связано с отправкой пароля пользователя и логина входа между сервером и клиентом, что может открыть проблемы с безопасностью. По крайней мере, вы должны убедиться, что вы отключили кеширование страницы, содержащей iframe
чтобы пароль не сохранялся в кеше браузера.
Поскольку ваш сайт и установка MediaWiki предположительно живут в одном домене, вы также можете просто использовать свой текущий код, а затем вручную установить необходимые файлы cookie , например:
setcookie( $cookieprefix . '_session', $sessionid ); setcookie( $cookieprefix . 'UserName', $lgusername ); setcookie( $cookieprefix . 'UserID', $lguserid ); setcookie( $cookieprefix . 'Token', $lgtoken );
Наконец, вы также можете включить эту проблему и написать плагин MediaWiki для обмена полномочиями, чтобы делегировать аутентификацию пользователя MediaWiki на систему проверки подлинности вашего веб-сайта. Это имело бы преимущество, позволяя вам полностью связывать две системы вместе, чтобы они пользовались одной и той же пользовательской базой данных и одинаковыми файлами cookie. (MediaWiki все еще настаивает на создании собственных записей пользователя для хранения своих собственных метаданных, но при написании AuthPlugin вы можете полностью переопределить части аутентификации системы, если хотите.)