Skip to content

Commit 3c4ab0e

Browse files
committed
add retweet method
1 parent b6d30b1 commit 3c4ab0e

File tree

1 file changed

+45
-38
lines changed

1 file changed

+45
-38
lines changed

appengine_twitter.py

Lines changed: 45 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -2,62 +2,70 @@
22
# -*- coding: utf-8 -*-
33
'''
44
AppEngine-Twitter
5-
5+
66
Twitter API wrapper for applications on Google App Engine
7-
7+
88
See: http://0-oo.net/sbox/python-box/appengine-twitter
99
License: http://0-oo.net/pryn/MIT_license.txt (The MIT license)
10-
10+
1111
See also:
1212
http://apiwiki.twitter.com/Twitter-API-Documentation
1313
http://code.google.com/intl/ja/appengine/docs/python/urlfetch/
1414
'''
15-
15+
1616
__author__ = '[email protected]'
1717
__version__ = '0.1.0'
18-
19-
18+
19+
2020
import base64
2121
import urllib
2222
from appengine_oauth import AppEngineOAuth
2323
from django.utils import simplejson
2424
from google.appengine.api import urlfetch
25-
26-
25+
26+
2727
class AppEngineTwitter(object):
28-
28+
2929
def __init__(self, tw_name='', tw_pswd=''):
3030
'''
3131
Note: Some actions require password or OAuth.
3232
'''
3333
self._api_url = 'https://twitter.com'
3434
self._search_url = 'http://search.twitter.com'
35-
35+
3636
self.tw_name = tw_name
3737
self._oauth = None
38-
38+
3939
self._headers = {}
4040
if tw_pswd != '':
4141
auth = base64.encodestring(tw_name + ':' + tw_pswd)[:-1]
4242
self._headers['Authorization'] = 'Basic ' + auth
43-
44-
43+
44+
4545
def update(self, message):
4646
'''
4747
Post a tweet
4848
Sucess => Retrun 200 / Fialed => Return other HTTP status
4949
'''
5050
return self._post('/statuses/update.json', {'status': message})
51-
52-
51+
52+
# ref : https://dev.twitter.com/docs/api/1/post/statuses/retweet/%3Aid
53+
def retweet(self, id):
54+
'''
55+
Post a tweet
56+
Sucess => Retrun 200 / Fialed => Return other HTTP status
57+
'''
58+
return self._post('/statuses/retweet/' + id + '.json', {})
59+
60+
5361
def follow(self, target_name):
5462
'''
5563
Sucess => Return 200 / Already following => Return 403 /
5664
Fialed => Return other HTTP status
5765
'''
5866
return self._post('/friendships/create.json', {'screen_name': target_name})
59-
60-
67+
68+
6169
def is_following(self, target_name):
6270
'''
6371
Yes => Return True / No => Return False /
@@ -68,61 +76,61 @@ def is_following(self, target_name):
6876
self.verify()
6977
user_info = simplejson.loads(self.last_response.content)
7078
self.tw_name = user_info['screen_name']
71-
79+
7280
status = self._get('/friendships/exists.json',
7381
{'user_a': self.tw_name, 'user_b': target_name})
7482
if status == 200:
7583
return (self.last_response.content == 'true')
7684
else:
7785
return status
78-
79-
86+
87+
8088
def verify(self):
8189
'''
8290
Verify user_name and password, and get user info
8391
Sucess => Return 200 / Fialed => Return other HTTP status
8492
'''
8593
return self._get('/account/verify_credentials.json', {})
86-
87-
94+
95+
8896
def search(self, keyword, params={}):
8997
'''
9098
Sucess => Return Array of dict / Fialed => Return HTTP status except 200
9199
'''
92100
params['q'] = keyword
93101
return self._search('/search.json', params)
94-
95-
102+
103+
96104
# OAuth methods
97105
# (See http://0-oo.net/sbox/python-box/appengine-oauth )
98-
106+
99107
def set_oauth(self, key, secret, acs_token='', acs_token_secret=''):
100108
'''
101109
Set OAuth parameters
102110
'''
103111
self._oauth = AppEngineOAuth(key, secret, acs_token, acs_token_secret)
104-
105-
112+
113+
106114
def prepare_oauth_login(self):
107115
'''
108116
Get request token, request token secret and login URL
109117
'''
110118
dic = self._oauth.prepare_login(self._api_url + '/oauth/request_token/')
111119
dic['url'] = self._api_url + '/oauth/authorize?' + dic['params']
112120
return dic
113-
114-
121+
122+
115123
def exchange_oauth_tokens(self, req_token, req_token_secret):
116124
'''
117125
Exchange request token for access token
118126
'''
119127
return self._oauth.exchange_tokens(self._api_url + '/oauth/access_token/',
120128
req_token,
121129
req_token_secret)
122-
123-
130+
131+
124132
# Private methods
125-
133+
126134
def _post(self, path, params):
127135
url = self._api_url + path
128136
if self._oauth != None:
@@ -133,8 +141,8 @@ def _post(self, path, params):
133141
headers=self._headers)
134142
self.last_response = res
135143
return res.status_code
136-
137-
144+
145+
138146
def _get(self, path, params):
139147
url = self._api_url + path
140148
if self._oauth != None:
@@ -143,21 +151,20 @@ def _get(self, path, params):
143151
res = urlfetch.fetch(url=url, method='GET', headers=self._headers)
144152
self.last_response = res
145153
return res.status_code
146-
147-
154+
155+
148156
def _search(self, path, params):
149157
'''
150158
FYI http://apiwiki.twitter.com/Rate-limiting (Especially 503 error)
151159
'''
152160
url = url=self._search_url + path + '?' + urllib.urlencode(params)
153161
res = urlfetch.fetch(url=url, method='GET')
154162
self.last_response = res
155-
163+
156164
if res.status_code == 200:
157165
return simplejson.loads(res.content)['results']
158166
elif res.status_code == 503:
159167
err_msg = 'Rate Limiting: Retry After ' + res.headers['Retry-After']
160168
else:
161169
err_msg = 'Error: HTTP Status is ' + str(res.status_code)
162-
163170
raise Exception('Twitter Search API ' + err_msg)

0 commit comments

Comments
 (0)