Python初心者がはじめるGoogleAppEngine(Picasa連携してみました)

レコーディングダイエット用のブログサイトみたいのを作ろうと、
Ruby on Railsでコードを書き始めてたのですが、
せっかくだから何かやった事ないのがイイかなと思ってGoogleAppEngineでPython。
 
■ Pythonのインタプリタ
自分のUbuntuマシンには2.7が入っていました。

$ python -V
Python 2.7.3

 
■ Google App Engine SDK for Pythonのインストール
Googleのサイトからzipアーカイブをダウンロードしてきます。

$ wget http://googleappengine.googlecode.com/files/google_appengine_1.7.3.zip
$ unzip google_appengine_1.7.3.zip
Archive: google_appengine_1.7.3.zip
 creating: google_appengine/
 inflating: google_appengine/BUGS
 inflating: google_appengine/LICENSE
 inflating: google_appengine/README

↓この辺の.pyコマンドを使ってアレやコレやしてくことになるみたいです。

google_appengine $ ls
api_server.py  bulkload_client.py  dev_appserver.py      gen_protorpc.py  lib                   README               tools
appcfg.py      bulkloader.py       download_appstats.py  google           LICENSE               RELEASE_NOTES        VERSION
BUGS           demos               endpointscfg.py       google_sql.py    new_project_template  remote_api_shell.py

 
■ ローカルのWebサーバーでHello World
↓こんなPythonスクリプト(helloworld.py)書いて、

print ‘Content-Type: text/plain’
print ”
print ‘Hello, world!’

↓こんなYaml(app.yaml)書いて、

application: helloworld
version: 1
runtime: python
api_version: 1
 
handlers:
– url: /.*
script: helloworld.py

開発用のスクリプトな dev_appserver.py 使って起動します。
引数は上記でPythonとYamlを置いたディレクトリ

$ google_appengine/dev_appserver.py helloworld/
WARNING  2012-11-01 07:03:37,139 rdbms_mysqldb.py:74] The rdbms API is not available because the MySQLdb library could not be loaded.
Warning: You are using a Python runtime (2.7) that is more recent than the production runtime environment (2.5). Your application may use features that are not available in the production environment and may not work correctly when deployed to production.
Notice: The Python 2.7 runtime is now available, and comes with a range of new features including concurrent requests and more libraries. Learn how simple it is to migrate your application to Python 2.7 at https://developers.google.com/appengine/docs/python/python25/migrate27.
Allow dev_appserver to check for updates on startup? (Y/n): Y
~略~
INFO     2012-11-01 07:03:39,748 dev_appserver_multiprocess.py:655] Running application dev~helloworld on port 8080: http://localhost:8080
INFO     2012-11-01 07:03:39,748 dev_appserver_multiprocess.py:657] Admin console is available at: http://localhost:8080/_ah/admin

で、 http://localhost:8080/ にアクセスしてみると
↓のようにHello, world!キターーー的な。

 
ログ的にも↓アクセスきてるのが確認できます。

INFO 2012-11-01 07:04:24,406 dev_appserver.py:3092] “GET / HTTP/1.1” 200 –
INFO 2012-11-01 07:04:24,442 dev_appserver.py:3092] “GET /favicon.ico HTTP/1.1” 200 –

サーバー上げた時のログをみてちょっと気になったのが↓

console is available at: http://localhost:8080/_ah/admin

アクセスしてみると↓こんな感じ。

あんな事やこんな事が出来そう、、と期待が膨らみます。
 
てか、ログみると↓この管理画面はDjangoで出来てるっぽいですね。
下に出てくるwebappじゃないんかい、っていうw

WARNING  2012-11-01 07:38:21,845 __init__.py:98] You are using the default Django version (0.96). The default Django version will change in an App Engine release in the near future. Please call use_library() to explicitly select a Django version. For more information see https://developers.google.com/appengine/docs/python/tools/libraries#Django

 
■ フレームワーク webapp
App Engineにはフレームワークが同梱されてるらしい。その名もwebapp。
んー、ネーミング的には愛せるかどうかは別として、とりあえず進めてみます。

from google.appengine.ext import webapp
from google.appengine.ext.webapp.util import run_wsgi_app

こんな感じでwebappのライブラリをインポート出来るみたいです。
WSGI stands for Web Server Gateway Interfaceって事で、
Rails界隈のRackとかもこいつ一派だって言われています。
んま、サーバーとアプリケーションを繋ぐアレって感じですかね。
んでもって、クラスを作って、この閉じない感じ新鮮よねー、と。

class MainPage(webapp.RequestHandler):
 def get(self):
  self.response.headers[‘Content-Type’] = ‘text/plain’
  self.response.out.write(‘Hello, webapp World!’)

URLとクラスのマッピングを設定して、
(debug=true入れると、落ちた時にスタックトレース出してくれるみたい)

application = webapp.WSGIApplication([(‘/’, MainPage)], debug=True)

main文叩きますよ、と。

def main():
 run_wsgi_app(application)
 
if __name__ == “__main__”:
 main()

最後のif __name__ ってのは何かな?って調べてみたら、
↓がわかり易かったです。
if __name__ == '__main__': について – へたれプログラマな日々
普通に実行するとifの中に入るけど、importされた時は実行されません、と。
 
ただ、それでもこのif文がよく分からなくて。
コレがimportされるかどうかって関係あるのだろうかと…。
って事で↓のようにif文をコメントアウトしても普通に動くんですよね。

#if __name__ == “__main__”:
main()

んま、内部的に __name__ 使いたい時があるんだろうな。きっと。
 
■ Picasaから写真データを取得
Google App Engineから叩く写真サービスで何がイイかな?
って思ってフォト蔵とかみてたのですが、Picasaがあるじゃないですか、と。
んでググっていくと、どうもこいつ↓を使いなさいって事みたい。
Retrieving Authenticated Google Data Feeds with Google App Engine
 
■ クライアントライブラリをダウンロード
↓gdata-2.0.17.zipが最新みたいなのでそれを落とします。
https://code.google.com/p/gdata-python-client/downloads/list
wgetしたら↓みたいにSSLで落ちてしまったのでブラウザから、、、

$ wget https://gdata-python-client.googlecode.com/files/gdata-2.0.17.zip
~略~
Proxy tunneling failed: Bad RequestUnable to establish SSL connection.
$ unzip gdata-2.0.17.zip
Archive: gdata-2.0.17.zip
 inflating: gdata-2.0.17/INSTALL.txt
 inflating: gdata-2.0.17/README.txt
~略~

 
■ クライアントライブラリからPicasaにアクセス
↓に日本語で素敵なブログを発見しました…。
写真管理サービス Picasa Web Albums と GAE(Google App Engine)のマッシュアップ – Object Design

こちらに従って、上記のgdata-2.0.17.zipを解凍して出てきた
ライブラリを先ほど上記でHelloWorldしてきたディレクトリにコピーします。

cd gdata-2.0.17/src
cp -r atom/ gdata/ ../../helloworld/

 
■ Googleのアカウントを使う
↓こんな感じでMainPageクラスの中に入れてあげると、、

from google.appengine.api import users
~略~
user = users.get_current_user()
if user==None:
 self.redirect(users.create_login_url(self.request.uri))
 return

↓のようにemailを入力する画面にリダイレクトされます。

 
■ Picasaからアルバムリストを取得する
↓的なおまじないをした後

import gdata.service
import gdata.photos.service
import gdata.alt.appengine
~略~
client = gdata.photos.service.PhotosService()
gdata.alt.appengine.run_on_appengine(client)

↓のように別メソッドにして。

photolist=getPhotolist(client,user)

詳細は↓こんな感じ

def getPhotolist(client,username):
 photolist=[]
 photos=None
 albums = client.GetUserFeed(user=username)
 for album in albums.entry:
  logging.info(
   ’title: %s, number of photos: %s, id: %s’ %
   (album.title.text,album.numphotos.text, album.gphoto_id.text))
 
 return photolist

 
■ ログ出力したアルバムリストを確認する

INFO     2012-11-01 08:52:39,444 helloworld.py:20] title: October 31, 2012, number of photos: 12, id: 5805393509008449009
INFO     2012-11-01 08:52:39,446 helloworld.py:20] title: October 25, 2012, number of photos: 4, id: 5803070908854390001
INFO     2012-11-01 08:52:39,446 helloworld.py:20] title: October 22, 2012, number of photos: 3, id: 5802083116233658209
~略~

おぉ、、取れました~ヽ(=´▽`=)ノ
 
■ 最後に、、
思ったよりお手軽に出来てナイスでした。Pythonもなんかイイなー。
んで↓みると、Picasaへの各種操作も簡単に出来そうですし。
Developer's Guide: Python – Picasa Web Albums Data API — Google Developers

ちょっとコレで進めてみようかなと思いやす。
 

プログラミング Google App Engine
Dan Sanderson
オライリージャパン
売り上げランキング: 273824

コメントを残す

以下に詳細を記入するか、アイコンをクリックしてログインしてください。

WordPress.com ロゴ

WordPress.com アカウントを使ってコメントしています。 ログアウト /  変更 )

Google フォト

Google アカウントを使ってコメントしています。 ログアウト /  変更 )

Twitter 画像

Twitter アカウントを使ってコメントしています。 ログアウト /  変更 )

Facebook の写真

Facebook アカウントを使ってコメントしています。 ログアウト /  変更 )

%s と連携中