django-tastypie 0.9.12-alphaではApiKeyAuthenticationの認証パラメータでヘッダで渡せる

先日django-tastypieのApiKeyAuthenticatinを試してみました。


認証パラメータ(username/api_key)はGETかPOSTで渡すしかないので、登録や更新などの場合は(POSTパラメータのjsonにつっこんでも見てくれないので)、クエリパラメータで渡してたんですが、POSTなのにクエリパラメータ?という違和感ありました。

auth_params = {
    "username": u"user2",
    "api_key": u"430b1c2faed2328fd7a4133edefea90a4f06324b"
    }
auth_query = urllib.urlencode(auth_params)

# 登録
payload = {'title': u'Python Cook Book', 'pub_date': "2012/9/25"}
r = requests.post('http://localhost:8000/api/book/?' + auth_query,
                  data=json.dumps(payload),
                  headers={"Content-Type": "application/json"} )

そこで調べてみたら開発バージョンの0.9.12-alphaでは認証パラメータをヘッダ(Authorization)で渡せるようになったようなので、そちらを試してみます。
0.9.12-alphaはgithubからinstallできます。

pip install git+https://github.com/toastdriven/django-tastypie

ヘッダで認証パラメータを渡すサンプル(requests使用)

# coding=utf-8
import urllib
import requests
import json

auth_params = {
    "username": u"user2",
    "api_key": u"430b1c2faed2328fd7a4133edefea90a4f06324b"
}

headers = {"Authorization": "ApiKey %(username)s:%(api_key)s" % (auth_params),
           "Content-Type": "application/json"}


# データを全部削除
r = requests.delete('http://localhost:8000/api/book/', headers=headers)
assert(r.status_code == 204)

# データが全て消えていることを確認
r = requests.get('http://localhost:8000/api/book/', headers=headers)
assert(json.loads(r.text)["meta"]["total_count"] == 0)

# 登録
payload = {'title': u'Python Cook Book', 'pub_date': "2012/9/25"}
r = requests.post('http://localhost:8000/api/book/',
                  data=json.dumps(payload),
                  headers=headers)
assert(r.status_code == 201)

# 取得
r = requests.get('http://localhost:8000/api/book/', headers=headers)
res = json.loads(r.text)
assert(len(res["objects"]) == 1)
assert(res["objects"][0]["title"] == u"Python Cook Book")
assert(int(res["objects"][0]["id"]) == 1) # 0.9.12-alphaではintで帰ってくる。0.9.11ではstr

# idを指定して取得
r = requests.get('http://localhost:8000/api/book/1', headers=headers)
res = json.loads(r.text)
assert(int(res["id"]) == 1) # 0.9.12-alphaではintで帰ってくる。0.9.11ではstr
assert(res["title"] == u"Python Cook Book")

# 更新
payload = {'id': 1,
           'title': u'Python Cook Book 2nd Edition',
           'pub_date': "2013/1/25"}
r = requests.post('http://localhost:8000/api/book/',
                  data=json.dumps(payload),
                  headers=headers)
assert(r.status_code == 201)


# 更新内容を確認
r = requests.get('http://localhost:8000/api/book/1', headers=headers)
res = json.loads(r.text)
assert(int(res["id"]) == 1)  # 0.9.12-alphaではintで帰ってくる。0.9.11ではstr
assert(res["title"] == u"Python Cook Book 2nd Edition")


# idを指定して削除
r = requests.delete('http://localhost:8000/api/book/1', headers=headers)
assert(r.status_code == 204)

# データが消えていることを確認
r = requests.get('http://localhost:8000/api/book/1', headers=headers)
assert(r.status_code == 404)

ヘッダで認証パラメータを渡せました。

データ取得で返されるidは0.9.11ではstrだったのですが、0.9.12-alphaではintになりました。
アップグレードする場合は注意が必要だと思います。