Merge pull request #53 from JohnathonNow/master

Added support for sending images
This commit is contained in:
Taehoon Kim
2016-08-21 22:35:22 +09:00
committed by GitHub

View File

@@ -12,10 +12,12 @@
"""
import requests
import json
from uuid import uuid1
from random import random, choice
from datetime import datetime
from bs4 import BeautifulSoup as bs
from mimetypes import guess_type
from .utils import *
from .models import *
@@ -35,6 +37,8 @@ BaseURL ="https://www.facebook.com"
MobileURL ="https://m.facebook.com/"
StickyURL ="https://0-edge-chat.facebook.com/pull"
PingURL ="https://0-channel-proxy-06-ash2.facebook.com/active_ping"
UploadURL ="https://upload.facebook.com/ajax/mercury/upload.php"
class Client(object):
"""A client for the Facebook Chat (Messenger).
@@ -119,6 +123,11 @@ class Client(object):
self.req_counter += 1
return self._session.post(url, headers=self._header, data=query, timeout=timeout)
def _postFile(self, url, files=None, timeout=30):
payload=self._generatePayload(None)
return self._session.post(url, data=payload, timeout=timeout, files=files)
def login(self):
if not (self.email and self.password):
raise Exception("id and password or config is needed")
@@ -196,13 +205,14 @@ class Client(object):
users.append(User(entry))
return users # have bug TypeError: __repr__ returned non-string (type bytes)
def send(self, recipient_id, message=None, message_type='user', like=None):
def send(self, recipient_id, message=None, message_type='user', like=None, image_id=None):
"""Send a message with given thread id
:param recipient_id: the user id or thread id that you want to send a message to
:param message: a text that you want to send
:param message_type: determines if the recipient_id is for user or thread
:param like: size of the like sticker you want to send
:param image_id: id for the image to send, gotten from the UploadURL
"""
if message_type.lower() == 'group':
@@ -238,10 +248,13 @@ class Client(object):
'message_batch[0][message_id]' : generateMessageID(self.client_id),
'message_batch[0][manual_retry_cnt]' : '0',
'message_batch[0][thread_fbid]' : thread_id,
'message_batch[0][has_attachment]' : False,
'message_batch[0][has_attachment]' : image_id != None,
'message_batch[0][other_user_fbid]' : user_id
}
if image_id:
data['message_batch[0][image_ids][0]'] = image_id
if like:
try:
sticker = LIKES[like.lower()]
@@ -253,6 +266,39 @@ class Client(object):
r = self._post(SendURL, data)
return r.ok
def sendRemoteImage(self, recipient_id, message=None, message_type='user', image=''):
"""Send an image from a URL
:param recipient_id: the user id or thread id that you want to send a message to
:param message: a text that you want to send
:param message_type: determines if the recipient_id is for user or thread
:param image: URL for an image to download and send
"""
mimetype = guess_type(image)[0]
remote_image = requests.get(image).content
image_id = self.uploadImage({'file': (image, remote_image, mimetype)})
return self.send(recipient_id, message, message_type, None, image_id)
def sendLocalImage(self, recipient_id, message=None, message_type='user', image=''):
"""Send an image from a file path
:param recipient_id: the user id or thread id that you want to send a message to
:param message: a text that you want to send
:param message_type: determines if the recipient_id is for user or thread
:param image: path to a local image to send
"""
mimetype = guess_type(image)[0]
image_id = self.uploadImage({'file': (image, open(image), mimetype)})
return self.send(recipient_id, message, message_type, None, image_id)
def uploadImage(self, image):
"""Upload an image and get the image_id for sending in a message
:param image: a tuple of (file name, data, mime type) to upload to facebook
"""
r = self._postFile(UploadURL, image)
# Strip the start and parse out the returned image_id
return json.loads(r._content[9:])['payload']['metadata'][0]['image_id']
def getThreadInfo(self, userID, start, end=None):
"""Get the info of one Thread