如何使用PHP cURL登录到mediawiki? [英] How do I log into mediawiki using PHP cURL?

查看:86
本文介绍了如何使用PHP cURL登录到mediawiki?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试将MediaWiki集成到我的网站中,但是遇到了麻烦。我认为问题与cookie有关,因为我从mediawiki API获得成功。

I'm trying to integrate mediawiki into my website, but I'm having trouble. I think the problem has something to do with the cookies because I get a success from the mediawiki API.

这是我的代码:

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仍会返回成功,因此也不能排除该错误。

I've also noticed that if I supply a bad token, the API still returns a success, so I can't outrule that, either.

编辑:我现在使它运行完美,并将代码更新为当前有效的代码。

I've gotten it working perfectly now and updated the code to the current, working code.

推荐答案

您似乎正在尝试为您的网站和MediaWiki实现单一登录机制通过在网站上使用PHP脚本,使用API​​将用户登录到MediaWiki。

It looks like you're trying to implement a single sign-on mechanism for your website and MediaWiki by having a PHP script on your website log the user into MediaWiki using the API.

问题是,尽管您的脚本确实确实在使用用户的凭据成功登录到MediaWiki。 ,它不会将MediaWiki身份验证cookie传递回用户。

The problem is that, while your script is indeed successfully logging into MediaWiki using the user's credentials, it's not passing the MediaWiki authentication cookies back to the user.

有两种方法可以解决此问题:

There are a couple of ways to solve this issue:


  • 也许最简单的解决方案是使用JavaScript / AJAX在客户端完全处理MediaWiki登录过程。这样,Cookie将直接发送到用户的浏览器。当然,不利的一面是,这对于不能或不想运行JavaScript的用户将不起作用(但是您始终可以让他们仅以通常的方式登录到MediaWiki)。

  • Perhaps the simplest solution would be to handle the MediaWiki login process entirely on the client side using JavaScript / AJAX. That way, the cookies will be sent directly to the users's browser. The down side, of course, is that this won't work for users who cannot or don't want to run JavaScript (but you could always let them just log in to MediaWiki the usual way).

您也可以只在服务器端执行登录过程的第一步(检索令牌),然后让客户端直接请求第二步URL,例如通过将其用作返回的HTML页面上不可见的 iframe 的来源。这不需要JavaScript,但是需要在服务器和客户端之间来回发送用户的密码和登录令牌,这可能会引发安全问题。至少,您应该确保禁用缓存包含 iframe 的页面,这样密码就不会保存在浏览器缓存中。

You could also do only the first step of the login process (retrieving the token) on the server side, and then have the client request the second step URL directly e.g. by using it as the source of an invisible iframe on the returned HTML page. This doesn't require JavaScript, but does involve sending the user's password and login token back and forth between the server and the client, which could open up security issues. At least, you should make sure you disable caching for the page containing the iframe so that the password will not be saved in the browser cache.

由于您的网站和MediaWiki的安装可能位于同一域中,因此您也可以只使用当前代码,然后手动设置必要的cookie ,如下所示:

Since your website and MediaWiki installation presumably live on the same domain, you could also just use your current code and then set the necessary cookies manually, something like this:

setcookie( $cookieprefix . '_session', $sessionid );
setcookie( $cookieprefix . 'UserName', $lgusername );
setcookie( $cookieprefix . 'UserID',   $lguserid );
setcookie( $cookieprefix . 'Token',    $lgtoken );


  • 最后,您也可以解决此问题,并编写 MediaWiki身份验证插件,而是将Me​​diaWiki的用户身份验证委派给您网站的用户身份验证系统。这样做的好处是,您可以将两个系统完全捆绑在一起,以便它们使用相同的用户数据库和相同的身份验证Cookie。 (MediaWiki仍然坚持创建自己的用户记录来存储自己的元数据,但是编写AuthPlugin可以让您如果需要,可以完全覆盖系统的身份验证部分。)

  • Finally, you could also turn the problem around, and write a MediaWiki auth plugin to delegate MediaWiki's user authentication to your website's user authentication system instead. This would have the advantage of allowing you to tie the two systems fully together, so that they'd user the same user database and the same authentication cookies. (MediaWiki does still insist on creating its own user records to store its own metadata, but writing an AuthPlugin let you completely override the authentication parts of the system if you want.)

    这篇关于如何使用PHP cURL登录到mediawiki?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

  • 查看全文
    登录 关闭
    扫码关注1秒登录
    发送“验证码”获取 | 15天全站免登陆