Refactor session cookie handling into State
This commit is contained in:
@@ -115,8 +115,8 @@ class Client(object):
|
|||||||
It may be a bad idea to do this in an exception handler, if you have a better method, please suggest it!
|
It may be a bad idea to do this in an exception handler, if you have a better method, please suggest it!
|
||||||
"""
|
"""
|
||||||
if error_code == "1357004":
|
if error_code == "1357004":
|
||||||
log.warning("Got error #1357004. Doing a _postLogin, and resending request")
|
log.warning("Got error #1357004. Refreshing state and resending request")
|
||||||
self._postLogin()
|
self._state = State.from_session(session=self._state._session)
|
||||||
return True
|
return True
|
||||||
return False
|
return False
|
||||||
|
|
||||||
@@ -263,15 +263,6 @@ class Client(object):
|
|||||||
self._uid = None
|
self._uid = None
|
||||||
self._client_id = hex(int(random() * 2147483648))[2:]
|
self._client_id = hex(int(random() * 2147483648))[2:]
|
||||||
|
|
||||||
def _postLogin(self):
|
|
||||||
self._uid = self._state._session.cookies.get_dict().get("c_user")
|
|
||||||
if self._uid is None:
|
|
||||||
raise FBchatException("Could not find c_user cookie")
|
|
||||||
self._uid = str(self._uid)
|
|
||||||
|
|
||||||
r = self._get("/")
|
|
||||||
self._state = State.from_base_request(self._state._session, r.text)
|
|
||||||
|
|
||||||
def _login(self, email, password):
|
def _login(self, email, password):
|
||||||
soup = bs(self._get("https://m.facebook.com/").text, "html.parser")
|
soup = bs(self._get("https://m.facebook.com/").text, "html.parser")
|
||||||
data = dict(
|
data = dict(
|
||||||
@@ -294,7 +285,10 @@ class Client(object):
|
|||||||
r = self._get("https://m.facebook.com/login/save-device/cancel/")
|
r = self._get("https://m.facebook.com/login/save-device/cancel/")
|
||||||
|
|
||||||
if "home" in r.url:
|
if "home" in r.url:
|
||||||
self._postLogin()
|
self._state = State.from_session(session=self._state._session)
|
||||||
|
self._uid = self._state.get_user_id()
|
||||||
|
if self._uid is None:
|
||||||
|
raise FBchatException("Could not find c_user cookie")
|
||||||
return True, r.url
|
return True, r.url
|
||||||
else:
|
else:
|
||||||
return False, r.url
|
return False, r.url
|
||||||
@@ -378,7 +372,7 @@ class Client(object):
|
|||||||
:return: A dictionay containing session cookies
|
:return: A dictionay containing session cookies
|
||||||
:rtype: dict
|
:rtype: dict
|
||||||
"""
|
"""
|
||||||
return self._state._session.cookies.get_dict()
|
return self._state.get_cookies()
|
||||||
|
|
||||||
def setSession(self, session_cookies):
|
def setSession(self, session_cookies):
|
||||||
"""Loads session cookies
|
"""Loads session cookies
|
||||||
@@ -394,14 +388,16 @@ class Client(object):
|
|||||||
|
|
||||||
try:
|
try:
|
||||||
# Load cookies into current session
|
# Load cookies into current session
|
||||||
self._state._session.cookies = requests.cookies.merge_cookies(
|
self._state = State.from_cookies(session_cookies)
|
||||||
self._state._session.cookies, session_cookies
|
|
||||||
)
|
|
||||||
self._postLogin()
|
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
log.exception("Failed loading session")
|
log.exception("Failed loading session")
|
||||||
self._resetValues()
|
self._state = State()
|
||||||
return False
|
return False
|
||||||
|
uid = self._state.get_user_id()
|
||||||
|
if uid is None:
|
||||||
|
log.warning("Could not find c_user cookie")
|
||||||
|
return False
|
||||||
|
self._uid = uid
|
||||||
return True
|
return True
|
||||||
|
|
||||||
def login(self, email, password, max_tries=5):
|
def login(self, email, password, max_tries=5):
|
||||||
|
@@ -21,6 +21,12 @@ class State(object):
|
|||||||
_counter = attr.ib(0)
|
_counter = attr.ib(0)
|
||||||
_logout_h = attr.ib(None)
|
_logout_h = attr.ib(None)
|
||||||
|
|
||||||
|
def get_user_id(self):
|
||||||
|
rtn = self.get_cookies().get("c_user")
|
||||||
|
if rtn is None:
|
||||||
|
return None
|
||||||
|
return str(rtn)
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def logout_h(self):
|
def logout_h(self):
|
||||||
return self._logout_h
|
return self._logout_h
|
||||||
@@ -37,17 +43,19 @@ class State(object):
|
|||||||
}
|
}
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
def from_base_request(cls, session, content):
|
def from_session(cls, session):
|
||||||
soup = bs4.BeautifulSoup(content, "html.parser")
|
r = session.get(_util.prefix_url("/"))
|
||||||
|
|
||||||
|
soup = bs4.BeautifulSoup(r.text, "html.parser")
|
||||||
|
|
||||||
fb_dtsg_element = soup.find("input", {"name": "fb_dtsg"})
|
fb_dtsg_element = soup.find("input", {"name": "fb_dtsg"})
|
||||||
if fb_dtsg_element:
|
if fb_dtsg_element:
|
||||||
fb_dtsg = fb_dtsg_element["value"]
|
fb_dtsg = fb_dtsg_element["value"]
|
||||||
else:
|
else:
|
||||||
# Fall back to searching with a regex
|
# Fall back to searching with a regex
|
||||||
fb_dtsg = FB_DTSG_REGEX.search(content).group(1)
|
fb_dtsg = FB_DTSG_REGEX.search(r.text).group(1)
|
||||||
|
|
||||||
revision = int(content.split('"client_revision":', 1)[1].split(",", 1)[0])
|
revision = int(r.text.split('"client_revision":', 1)[1].split(",", 1)[0])
|
||||||
|
|
||||||
logout_h_element = soup.find("input", {"name": "h"})
|
logout_h_element = soup.find("input", {"name": "h"})
|
||||||
logout_h = logout_h_element["value"] if logout_h_element else None
|
logout_h = logout_h_element["value"] if logout_h_element else None
|
||||||
@@ -55,3 +63,12 @@ class State(object):
|
|||||||
return cls(
|
return cls(
|
||||||
session=session, fb_dtsg=fb_dtsg, revision=revision, logout_h=logout_h
|
session=session, fb_dtsg=fb_dtsg, revision=revision, logout_h=logout_h
|
||||||
)
|
)
|
||||||
|
|
||||||
|
def get_cookies(self):
|
||||||
|
return self._session.cookies.get_dict()
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def from_cookies(cls, cookies):
|
||||||
|
session = requests.session()
|
||||||
|
session.cookies = requests.cookies.merge_cookies(session.cookies, cookies)
|
||||||
|
return cls.from_session(session=session)
|
||||||
|
Reference in New Issue
Block a user