diff --git a/fbchat/graphql.py b/fbchat/graphql.py index 1335893..81f7411 100644 --- a/fbchat/graphql.py +++ b/fbchat/graphql.py @@ -26,12 +26,11 @@ class ConcatJSONDecoder(json.JSONDecoder): def graphql_color_to_enum(color): if color is None: return None - if len(color) == 0: + if not color: return ThreadColor.MESSENGER_BLUE - try: - return ThreadColor('#{}'.format(color[2:].lower())) - except ValueError: - raise FBchatException('Could not get ThreadColor from color: {}'.format(color)) + color = color[2:] # Strip the alpha value + color_value = '#{}'.format(color.lower()) + return enum_extend_if_invalid(ThreadColor, color_value) def get_customization_info(thread): if thread is None or thread.get('customization_info') is None: @@ -285,7 +284,10 @@ def graphql_to_message(message): rtn.unsent = False if message.get('unread') is not None: rtn.is_read = not message['unread'] - rtn.reactions = {str(r['user']['id']):MessageReaction(r['reaction']) for r in message.get('message_reactions')} + rtn.reactions = { + str(r['user']['id']): enum_extend_if_invalid(MessageReaction, r['reaction']) + for r in message.get('message_reactions') + } if message.get('blob_attachments') is not None: rtn.attachments = [graphql_to_attachment(attachment) for attachment in message['blob_attachments']] if message.get('extensible_attachment') is not None: diff --git a/fbchat/models.py b/fbchat/models.py index ac38455..e6bc193 100644 --- a/fbchat/models.py +++ b/fbchat/models.py @@ -1,7 +1,7 @@ # -*- coding: UTF-8 -*- from __future__ import unicode_literals -import enum +import aenum class FBchatException(Exception): @@ -602,7 +602,7 @@ class Plan(object): def __unicode__(self): return ''.format(self.uid, repr(self.title), self.time, repr(self.location), repr(self.location_id)) -class Enum(enum.Enum): +class Enum(aenum.Enum): """Used internally by fbchat to support enumerations""" def __repr__(self): # For documentation: diff --git a/fbchat/utils.py b/fbchat/utils.py index c39e652..2e1a39a 100644 --- a/fbchat/utils.py +++ b/fbchat/utils.py @@ -11,6 +11,7 @@ from os.path import basename import warnings import logging import requests +import aenum from .models import * try: @@ -300,6 +301,14 @@ def get_files_from_paths(filenames): for fn, fp, ft in files: fp.close() +def enum_extend_if_invalid(enumeration, value): + try: + return enumeration(value) + except ValueError: + log.warning("Failed parsing {.__name__}({!r}). Extending enum.".format(enumeration, value)) + aenum.extend_enum(enumeration, "UNKNOWN_{}".format(value).upper(), value) + return enumeration(value) + def get_url_parameters(url, *args): params = parse_qs(urlparse(url).query) return [params[arg][0] for arg in args if params.get(arg)] diff --git a/requirements.txt b/requirements.txt index 9cb2a6c..40ce5a1 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,3 +1,3 @@ requests beautifulsoup4 -enum34; python_version < '3.4' +aenum diff --git a/setup.cfg b/setup.cfg index b554b7b..45cdd3b 100644 --- a/setup.cfg +++ b/setup.cfg @@ -43,9 +43,6 @@ include_package_data = True packages = find: python_requires = >=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, <4.0 install_requires = + aenum requests beautifulsoup4 - # May not work in pip with bdist_wheel - # See https://wheel.readthedocs.io/en/latest/#defining-conditional-dependencies - # It is therefore defined in setup.py - # enum34; python_version < '3.4' diff --git a/setup.py b/setup.py index 1157ca5..3216505 100755 --- a/setup.py +++ b/setup.py @@ -5,4 +5,4 @@ from __future__ import unicode_literals from setuptools import setup -setup(extras_require={':python_version < "3.4"': ['enum34']}) +setup()