pixivから画像をダウンロードするスクリプトを公開したら、pixivの事務局から怒られたでござるの巻。
どうやら不特定多数への配布がまずい臭いので、プログラムの解説だけ書いておく。
誰かが既に書いてそうだけど、まぁいいや。
どうやら不特定多数への配布がまずい臭いので、プログラムの解説だけ書いておく。
誰かが既に書いてそうだけど、まぁいいや。
ログインのプロセスは次のようになる。
- 初回アクセス時はcookieがからっぽの状態でログインサーバにアクセスする。
- ログインサーバは初回アクセスフラグを立てたCookieを返す。
- ユーザーはログインIDとパスワードを入力する際に、サーバから受け取ったCookieも同時に送信する。
- サーバはIDとパスが一致していることを確認し、自身が送ったCookieが正しく送られていることを確認する
- サーバはログイン状態フラグを立てたCookieを送信する。
- 以後クライアントはログイン状態のCookieを使うことで、セッションを継続することができる。
そういうわけで、まずはHTTPのアクセスにCooikeを使えるようにしなきゃならない。
Pythonの標準ライブラリのurllib2とcookielibを使うことでこれは実現できる。
Pythonの標準ライブラリのurllib2とcookielibを使うことでこれは実現できる。
import urllib2, cookielib cj = cookielib.CookieJar() cjhdr = urllib2.HTTPCookieProcessor(cj) opener = urllib2.build_opener(cjhdr) opener.addheaders = [('User-agent', 'Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 5.1; SV1)'), ('Referer', '')]
opener.addheadersはタプルのリストを突っ込んでおくと、それが自動的にヘッダに追加される。
UAを書き換えてブラウザからのアクセスに見せかけないと、弾かれる。
また、Refererは初回アクセスなので、とりあえずからっぽにする。
UAを書き換えてブラウザからのアクセスに見せかけないと、弾かれる。
また、Refererは初回アクセスなので、とりあえずからっぽにする。
次にpixivにログインするプロセス。
usernameとpasswordの部分は適宜書き換えて。
pixivのログインページのソースを見れば、ログインフォームのIDがわかるので、
そいつを先ほど作ったcookie管理機能付きのopenerから、postメソッドを使って送ってやる。
基本的にopenしてreadするだけでOK。
これでCookieにログイン情報が書き込まれる。
pixivのログインページのソースを見れば、ログインフォームのIDがわかるので、
そいつを先ほど作ったcookie管理機能付きのopenerから、postメソッドを使って送ってやる。
基本的にopenしてreadするだけでOK。
これでCookieにログイン情報が書き込まれる。
def loginPixiv(): pixivLoginURL = "http://www.pixiv.net/index.php" postdata = {} postdata["pixiv_id"] = username postdata["pass"] = password params = urllib.urlencode(postdata) opener.open(pixivLoginURL, params).read()
これでログイン状態にすることができた。
以後openerでpixivのURLにアクセスすれば、ログイン状態のcookieがあるので、ログイン後の機能を利用することができる。
以後openerでpixivのURLにアクセスすれば、ログイン状態のcookieがあるので、ログイン後の機能を利用することができる。
つぎは画像のダウンロードプロセス。
でっかい画像を表示すると次のようなURLがあらわれる。(XXXXは数字)
http://www.pixiv.net/member_illust.php?mode=big&illust_id=XXXXX
このページのソースを読むと、画像の実体は次のようなURLであることがわかる。
でっかい画像を表示すると次のようなURLがあらわれる。(XXXXは数字)
http://www.pixiv.net/member_illust.php?mode=big&illust_id=XXXXX
このページのソースを読むと、画像の実体は次のようなURLであることがわかる。
http://img18.pixiv.net/img/USERNAME/XXXXX.png
しかしこのURLに直接アクセスしても、画像ファイルを取得することはできない。
これはRefererの問題で、正常ルート以外でアクセスした場合に表示させないためである。
しかしこのURLに直接アクセスしても、画像ファイルを取得することはできない。
これはRefererの問題で、正常ルート以外でアクセスした場合に表示させないためである。
なので、Refererを正規ルートであるように見せかける。
Iria先生のReferer偽装とかが懐かしいね。
Iria先生のReferer偽装とかが懐かしいね。
bigIllustPageURLは「http://www.pixiv.net/member_illust.php?mode=big&illust_id=XXXXX」これとかのURLね。
正規表現で適当に抜いてきて、でっかい画像を落とす
正規表現で適当に抜いてきて、でっかい画像を落とす
def downloadImage(bigIllustPageURL): bigIllustPage = opener.open(bigIllustPageURL).read() illustFile = re.search(r'<img src="(?P<url>http://img\d+\.pixiv\.net/img/.+?/\d+\..+)" border="0">', bigIllustPage) if illustFile: fileurl = illustFile.group("url") #イラストの実体URL illustFilename = fileurl.split("/")[-1] #イラストファイル名 opener.addheaders[1] = ('Referer', bigIllustPageURL) #refererを書き換えて、アクセス制限を回避 fp = open(illustFilename, "wb") #書き込む fp.write(opener.open(fileurl).read()) fp.close()
これで画像ファイルが落ちてくるんじゃないかな。
- 怒られたにもかかわらず解説載せるって・・・・どんだけですか -- 名無しさん (2008-09-24 01:15:44)