2006 年 7 月 22 日 23 時 21 分

mixi にログイン


このアーカイブは同期化されません。 mixi の日記が更新されても、このアーカイブには反映されません。


今日は mixi にログインしてみよう。

mixi のログインは、トップページのフォームに入力し、
その内容をサーバに送信することで行われる。
サーバは、認証情報を含む Cookie を返す。

それ以降は、ブラウザが Cookie を送信することで、
サーバは、ログインしていることを認識して、
自動的に個人用のトップページを返却する仕組みだ。

XMLHttpRequest でログインするためには、
まずログインフォームの動作を調べる必要がある。

メールアドレスやパスワードを送信することになるので、
SSL に対応したページでログインしたい。
https://mixi.jp を開き、HTML ソースを調べてみる。

送信フォームは <form> 要素で構成されており、
送信する内容は <input>、<button>、<textarea> のうち、
name 属性がついているものである。

では主要な部分だけ抜粋してみよう。

    <form action=login.pl method=post>
    <input type=hidden name=next_url value="/home.pl">
    メール<INPUT type=text name=email>
    パスワード<INPUT type=password name=password>
    <INPUT type=checkbox name=sticky>
    次回から自動的にログイン
    </FORM>

送信される内容は、名前と値の組み合わせで構成される。
mixi ログインページは以下の仕様であることが分かる。

フォーム送信先: login.pl
HTTP メソッド: post
パラメータ一覧(名前: 値)
    next_url: 「/home.pl」
    email: 利用者の入力したメールアドレス
    password: 利用者の入力したパスワード
    sticky: on(チェックしない場合は送信されない)

では、XMLHttpRequest を使って送信してみよう。

========== Main.js ==========

// application/x-www-form-urlencoded でエンコードする
function _encodeForm(hash) {

    var entries = [];
    var prop, key, value;

    for (prop in hash) {
        key = encodeURIComponent(prop);
        value = encodeURIComponent(hash[prop]);
        entries.push(key + "=" + value);
    }
   
    return entries.join("&"); // 「;」でもいいかも
};

function main() {

    // XMLHttpRequest を用意
    var client = new XMLHttpRequest();

    // ログイン用のパラメータを用意
    var form = {
        next_url: "/home.pl",
        email: "自分のメールアドレス",
        password: "パスワード"
    };

    // POST 用に符号化する
    var content = _encodeForm(form);

    // ログイン処理
    client.open("POST", "https://mixi.jp/login.pl", false);
    client.setRequestHeader("Content-Type",
            "application/x-www-form-urlencoded");
    client.send(content);

    // チェックのため、HTTP レスポンスヘッダを出力
    WScript.Echo(client.getAllResponseHeaders());

    // チェックのため、HTML を出力
    WScript.Echo(client.responseText);

}

main();

========== end of Main.js ==========

一気に長くなったが、順にみていこう。

HTTP メソッドが POST の場合、
open メソッドの第 1 引数を POST にするだけでなく、
送信するデータの種類を意味する、「Content-Type」
HTTP リクエストヘッダを設定しなければならない。

リクエストヘッダは setRequestHeader メソッドで設定する。
フォームの場合「application/x-www-form-urlencoded」だ。

そして、send メソッドには送信されるデータを渡すのだが、
パラメータを上記形式で符号化する必要がある。

application/x-www-form-urlencoded は、
「name=value&name=value……」という形式である。
また、name や value は URL エンコードする必要がある。

その処理を行うのは、_encodeForm 関数である。
引数としてハッシュ風(連想配列風)オブジェクトを取り、
符号化された文字列を返却する。
そうすることで、パラメータを簡単に用意することができる。

    var form = {
        next_url: "/home.pl",
        email: "自分のメールアドレス",
        password: "パスワード"
    };

中括弧は、オブジェクトリテラルの構文であり、
ほぼ以下と同じ意味である。
大括弧といい中括弧といい、Perl に少し似ているな。

    var form = new Object();
    form.next_url = "/home.pl";
    form.email = "自分のメールアドレス";
    form.password = "パスワード";

空のオブジェクトに対して、
プロパティを追加して利用すれば、
連想配列のような使い方ができる。
これらプロパティは、for~in 構文で列挙できるので、
_encodeForm 関数はそれを利用しているのだ。

さて、getAllResponseHeaders() メソッドは、
サーバが返却する HTTP レスポンスヘッダをそのまま返す。
ログインに成功したら Cookie が返却されるはずなので、
それを確認するために出力してみよう。

では、実行してみる。

==================================================

Date: Sat, 22 Jul 2006 13:50:33 GMT
Server: Apache
Set-Cookie: BF_SESSION=(省略); path=/
Set-Cookie: BF_STAMP=(省略); path=/
Vary: Accept-Encoding
Content-Type: text/html; charset=ISO-8859-1
Connection: close
Transfer-Encoding: chunked

<html><head><meta http-equiv="refresh" content="0;url=/check.pl?n=%2Fhome.pl"></head></html>

==================================================

このようになった。

Set-Cookie というレスポンスヘッダが確認できる。
これは、サーバが返した認証情報だ。

ちなみに、パスワードが違うなどの理由で失敗した場合、
レスポンスヘッダに Cookie はなく、
「メールアドレスもしくはパスワードが異なります。」
という文章が HTML 内に確認できる。



Copyright (c) 1994-2007 Project Loafer. All rights reserved.