AnonymousWassr というのを作ってみました。

  • もう Twitter には戻れない!!
  • まだ Twitter なの?童貞っぽいね!!
  • 全米ナンバー1ヒット!!

で有名な Wassr に匿名で投稿出来る AnonymousWassr というのを作ってみました。

http://gree.appspot.com/

作成にいたる流れ

朝、おきる。

なんかやる気が出ないのでグダグダ

気がついたら Emacs 開いてたのでなんとなく作りはじめる。

プライベートメッセージ受け取ったら書きこむ的な bot にしよう
と思って作りはじめたのにプライベートメッセージ取得の API が無い事に気づく

しょうがなくwebサービスにする事にする。

サーバ用意するのがメンドイので Google App Engine で作り始める。

骨組出来たところで GAE だと urllib 系が使えない事がわかる。

そろそろやばいので出社する。

とりあえず通信部分だけ作りたくなった。

google.appengine.api.urlfetch で出来そう。

Content-Type を自前で明示的に追加しないといけないのに気がつかなくってハマる。

なんとなく出来たのでてけとうに告知


と、いう感じで合計2時間くらいで最初のは出来ました。
その後、Wassr の timeline もってきたり、迷惑だから自前で持つようにしたりして今にいたります。

ソースはこんなかんじ

index.py

#!/usr/bin/env python
# -*- coding: utf-8 -*-

import wsgiref.handlers, cgi, logging, os ,time

from google.appengine.api import users
from google.appengine.ext import webapp,db
from google.appengine.ext.webapp import template
from django.utils import simplejson

from wassr import Wassr
from models import Status


wassr = Wassr('anonymous','xxxxxxxx')

class MainPage(webapp.RequestHandler):

    def get(self):
        path = os.path.join(os.path.dirname(__file__), 'index.html')
        query = Status().all()
        limit = 20
        items = query.order('-date').fetch(limit=limit)
        values = {
            'items' : items,
            }

        self.response.out.write(template.render(path, values))

    def post(self):
        text = self.request.get("text")
        if text.strip():
            r = wassr.post(text)
            status = Status()
            status.text = text
            status.put()
        self.redirect('/')

def main():
    application = webapp.WSGIApplication(
        [('/',MainPage),
         ],
        debug=True)
    logging.getLogger().setLevel(logging.DEBUG)
    wsgiref.handlers.CGIHandler().run(application)

if __name__ == '__main__':
    main()

wassr.py

#!/usr/bin/env python
# -*- coding: utf-8 -*-
import urllib, base64
from google.appengine.api import urlfetch

class Wassr:
	def __init__(self, user, passwd):
		self.user = user
		self.passwd = passwd

	def post(self, text):
		text = text.encode('utf-8')
		return self.postData('http://api.wassr.jp/statuses/update.json', urllib.urlencode({'status':text,'source':'anonymous'}))


	def getUserTimeline(self):
		return self.getData('http://api.wassr.jp/statuses/user_timeline.json?id='+self.user)

	def getData(self,url):
		return urlfetch.fetch(url=url,
                        method=urlfetch.GET,
                        headers={'User-agent':'WassrClient(http://d.hatena.ne.jp/jYoshiori/)',
				 }
				      )

	def postData(self,url,data):
		base64string = base64.encodestring("%s:%s" % (self.user, self.passwd))[:-1] 
		result = urlfetch.fetch(url=url,
                        payload=data,
                        method=urlfetch.POST,
                        headers={'User-agent':'WassrClient(http://d.hatena.ne.jp/jYoshiori/)',
				 'Content-Type': 'application/x-www-form-urlencoded',
				 'Authorization': 'Basic %s' % base64string 
				 }
					)
		return result


models.py

#!/usr/bin/env python
# -*- coding: utf-8 -*-

from google.appengine.ext import db

class Status(db.Model):
    date = db.DateTimeProperty(auto_now_add=True)
    text = db.TextProperty()


というわけで Wassr 共々 AnonymousWassr もよろしくおねがいいたします>