Implement authentication and timeline retrieval

This commit is contained in:
Klaus-Uwe Mitterer 2017-02-10 18:41:28 +01:00
parent 3cb5d8861c
commit 9457a83e02
4 changed files with 97 additions and 11 deletions

66
bot.py
View file

@ -1,6 +1,6 @@
#!/usr/bin/env python3 #!/usr/bin/env python3
import dbtools, logging, setuptools, strings, telegram.ext import ast, dbtools, logging, setuptools, strings, telegram.ext, twitools, tweepy
logging.basicConfig(format='%(asctime)s - %(name)s - %(levelname)s - %(message)s', level=logging.INFO) logging.basicConfig(format='%(asctime)s - %(name)s - %(levelname)s - %(message)s', level=logging.INFO)
logger = logging.getLogger(__name__) logger = logging.getLogger(__name__)
@ -10,11 +10,43 @@ def log(bot, update, error):
updater = telegram.ext.Updater(token=setuptools.token()) updater = telegram.ext.Updater(token=setuptools.token())
def noauth(update):
update.message.reply_text(strings.noauth)
def start(bot, update): def start(bot, update):
update.message.reply_text(strings.start % (setuptools.botname(), setuptools.botname())) update.message.reply_text(strings.start % (setuptools.botname(), setuptools.botname()))
def auth(bot, update): def auth(bot, update):
update.message.reply_text("Ooops. Not implemented yet.") db = dbtools.dbHelper()
cid = update.message.chat_id
if not (db.ato(cid) or db.ase(cid)):
auth = tweepy.OAuthHandler(setuptools.cke(), setuptools.cse())
update.message.reply_text(strings.auth % auth.get_authorization_url())
dbtools.dbHelper().storeToken(cid, auth.request_token)
else:
update.message.reply_text(strings.authimp)
def verify(bot, update, args):
db = dbtools.dbHelper()
cid = update.message.chat_id
if db.ato(cid) and not db.ase(cid):
auth = tweepy.OAuthHandler(setuptools.cke(), setuptools.cse())
auth.request_token = ast.literal_eval(db.ato(cid))
try:
auth.get_access_token(args[0])
dbtools.dbHelper().storeUser(cid, auth.access_token, auth.access_token_secret)
update.message.reply_text(strings.verify)
except Exception as e:
dbtools.dbHelper().deleteUser(update.message.chat_id)
update.message.reply_text(strings.verifyfail)
else:
update.message.reply_text(strings.verifyimp)
def unauth(bot, update): def unauth(bot, update):
dbtools.dbHelper().deleteUser(update.message.chat_id) dbtools.dbHelper().deleteUser(update.message.chat_id)
@ -24,28 +56,50 @@ def fish(bot, update):
dbtools.dbHelper().addFish(update.message.chat_id) dbtools.dbHelper().addFish(update.message.chat_id)
update.message.reply_text("Yummy! Thanks! :3") update.message.reply_text("Yummy! Thanks! :3")
def explicitTweet(bot, update): def explicitTweet(bot, update, args):
update.message.reply_text("Ooops. Not implemented yet.") update.message.reply_text("Ooops. Not implemented yet.")
def tweet(bot, update): def tweet(bot, update):
update.message.reply_text("Ooops. Not implemented yet.") try:
if dbtools.dbHelper().getTStatus(update.message.chat_id):
explicitTweet(bot, update, update.message.text)
except:
noauth(update)
def timeline(bot, update, args = [10]):
try:
count = int(args[0])
except:
count = 10
two = twitools.twoHelper(update.message.chat_id)
for status in two.api.home_timeline(count=count):
update.message.reply_text("%s (%s) at %s: %s" % (status.author.name, status.author.screen_name, status.created_at, status.text))
def toggleTweet(bot, update): def toggleTweet(bot, update):
try: try:
update.message.reply_text(strings.toggleTweet % ("on" if dbtools.dbHelper().toggleTweet(update.message.chat_id) else "off")) update.message.reply_text(strings.toggleTweet % ("on" if dbtools.dbHelper().toggleTweet(update.message.chat_id) else "off"))
except: except:
update.message.reply_text(strings.noauth) noauth(update)
def unknown(bot, update): def unknown(bot, update):
update.message.reply_text("Sorry, I didn't understand that command.") update.message.reply_text("Sorry, I didn't understand that command.")
def test(bot, update, args):
print(args)
unknown(bot, update)
updater.dispatcher.add_handler(telegram.ext.CommandHandler("auth", auth)) updater.dispatcher.add_handler(telegram.ext.CommandHandler("auth", auth))
updater.dispatcher.add_handler(telegram.ext.CommandHandler("fish", fish)) updater.dispatcher.add_handler(telegram.ext.CommandHandler("fish", fish))
updater.dispatcher.add_handler(telegram.ext.CommandHandler("help", start)) updater.dispatcher.add_handler(telegram.ext.CommandHandler("help", start))
updater.dispatcher.add_handler(telegram.ext.CommandHandler("start", start)) updater.dispatcher.add_handler(telegram.ext.CommandHandler("start", start))
updater.dispatcher.add_handler(telegram.ext.CommandHandler("test", test, pass_args=True))
updater.dispatcher.add_handler(telegram.ext.CommandHandler("timeline", timeline))
updater.dispatcher.add_handler(telegram.ext.CommandHandler("toggletweet", toggleTweet)) updater.dispatcher.add_handler(telegram.ext.CommandHandler("toggletweet", toggleTweet))
updater.dispatcher.add_handler(telegram.ext.CommandHandler("tweet", explicitTweet)) updater.dispatcher.add_handler(telegram.ext.CommandHandler("tweet", explicitTweet, pass_args=True))
updater.dispatcher.add_handler(telegram.ext.CommandHandler("unauth", unauth)) updater.dispatcher.add_handler(telegram.ext.CommandHandler("unauth", unauth))
updater.dispatcher.add_handler(telegram.ext.CommandHandler("verify", verify, pass_args=True))
updater.dispatcher.add_handler(telegram.ext.MessageHandler(telegram.ext.Filters.text, tweet)) updater.dispatcher.add_handler(telegram.ext.MessageHandler(telegram.ext.Filters.text, tweet))
updater.dispatcher.add_handler(telegram.ext.MessageHandler(telegram.ext.Filters.command, unknown)) updater.dispatcher.add_handler(telegram.ext.MessageHandler(telegram.ext.Filters.command, unknown))

View file

@ -68,6 +68,7 @@ class dbObject:
self.commit() self.commit()
def storeUser(self, cid, ato, ase): def storeUser(self, cid, ato, ase):
self.executeQuery("DELETE FROM tokens WHERE cid = %i;" % int(cid))
self.executeQuery("INSERT INTO tokens(cid, ato, ase) VALUES(%i, '%s', '%s');" % (int(cid), ato, ase)) self.executeQuery("INSERT INTO tokens(cid, ato, ase) VALUES(%i, '%s', '%s');" % (int(cid), ato, ase))
self.commit() self.commit()
@ -104,6 +105,11 @@ class dbObject:
self.executeQuery("UPDATE tokens SET fish = fish + 1 WHERE cid = %i;" % int(cid)) self.executeQuery("UPDATE tokens SET fish = fish + 1 WHERE cid = %i;" % int(cid))
self.commit() self.commit()
def storeToken(self, cid, ato):
self.executeQuery('INSERT INTO tokens(cid, ato) VALUES(%i, "%s");' % (int(cid), ato))
self.commit()
def dbHelper(): def dbHelper():
if setuptools.dbtype() == SQLITE: if setuptools.dbtype() == SQLITE:
return dbObject(dbtype=SQLITE, path=setuptools.dbpath()) return dbObject(dbtype=SQLITE, path=setuptools.dbpath())

View file

@ -1,3 +1,17 @@
auth = '''To get authenticated with Twitter, please visit this URL and sign in:
* %s
You will receive a six-digit PIN. Please send it to me like this:
* /verify 123456'''
authimp = '''I can't currently start a new authentication process for you as you are either already authenticated or an authentication process has been started.
Please unauthenticate using /unauth first if you are sure you want to re-authenticate.'''
noauth = '''You are not authenticated. Please use /auth to sign in with Twitter.''' noauth = '''You are not authenticated. Please use /auth to sign in with Twitter.'''
@ -32,3 +46,12 @@ I hope you had a good time with me. If there is anything you would like to tell
Your data has been deleted. Of course, you can always just re-authenticate using /auth. Your data has been deleted. Of course, you can always just re-authenticate using /auth.
It was great having you here. So long, and thanks for all the /fish!''' It was great having you here. So long, and thanks for all the /fish!'''
verify = '''Thanks for authenticating. You can now use all of my features!'''
verifyfail = '''Oops, something went wrong during the authentication. Please try again:
* /auth'''
verifyimp = '''There is not currently an authentication process running for you. You may already be logged in, or you have not yet sent me an /auth command.'''

View file

@ -1,4 +1,4 @@
import tweepy, setuptools import dbtools, tweepy, setuptools
class twObject: class twObject:
@ -24,21 +24,24 @@ class twObject:
def tweet(self, text, reply = 0): def tweet(self, text, reply = 0):
return self.api.update_status(text, reply) return self.api.update_status(text, reply)
def getFollowerIDs(two=twObject()): def getFollowerIDs(two):
''' Returns 5,000 follower IDs at most ''' ''' Returns 5,000 follower IDs at most '''
for id in list(two.api.followers_ids(screen_name=twObject().whoami())): for id in list(two.api.followers_ids(screen_name=twObject().whoami())):
yield int(id) yield int(id)
def getFollowingIDs(two=twObject()): def getFollowingIDs(two):
for id in list(two.api.friends_ids(screen_name=twObject().whoami())): for id in list(two.api.friends_ids(screen_name=twObject().whoami())):
yield int(id) yield int(id)
def getNameByID(uid, two=twObject()): def getNameByID(uid, two):
return two.api.get_user(uid).screen_name return two.api.get_user(uid).screen_name
def getNamesByIDs(fids=getFollowerIDs(), two=twObject()): def getNamesByIDs(fids, two):
for page in setuptools.paginate(fids, 100): for page in setuptools.paginate(fids, 100):
followers = two.api.lookup_users(user_ids=page) followers = two.api.lookup_users(user_ids=page)
for follower in followers: for follower in followers:
yield {"id": follower.id, "name": follower.screen_name} yield {"id": follower.id, "name": follower.screen_name}
def twoHelper(cid):
db = dbtools.dbHelper()
return twObject(db.ato(cid), db.ase(cid))