# Path: golem/core/chat_session.py
# class ChatSession:
# 
#     def __init__(self, interface, unique_id: str, meta=None, profile=None, is_logged=True, is_admin=False, is_test=False):
#         """
#         :param interface: Chat interface object
#         :param unique_id: A string that uniquely identifies the user within the interface
#         :param profile: Profile object
#         :param meta: Any interface-specific data. type: dict
#         """
#         if interface is None:
#             raise ValueError("Interface must be set")
#         elif not isinstance(unique_id, str):
#             raise ValueError("UID must be a string")
#         elif not isinstance(profile, Profile) and profile is not None:
#             raise ValueError("Profile must be instance of class Profile")
#         self.interface = interface
#         self.chat_id = self.interface.prefix + "_" + unique_id
#         self.profile = profile or Profile()
#         self.meta = meta or {}
#         self.is_logged = is_logged
#         self.is_admin = is_admin
#         self.is_test = is_test
# 
#     def to_json(self):
#         return {
#             "interface": self.interface.prefix,
#             "unique_id": self.chat_id.split('_', maxsplit=1)[1],
#             "profile": self.profile.to_json(),
#             "meta": self.meta,
#             "is_logged": self.is_logged,
#             "is_admin": self.is_admin
#         }
# 
#     @staticmethod
#     def from_json(data: dict):
#         interface = create_from_prefix(data['interface'])
#         return ChatSession(
#             interface=interface,
#             unique_id=data['unique_id'],
#             profile=Profile.from_json(data['profile']),
#             meta=data['meta'],
#             is_logged=data['is_logged'],
#             is_admin=data['is_admin']
#         )
# 
# Path: golem/core/message_parser.py
# def parse_text_message(text, num_tries=1):
#     if len(ENTITY_EXTRACTORS) <= 0:
#         logging.warning('No entity extractors configured!')
#         return {'type': 'message', 'entities': {'_message_text': [{'value': text}]}}
# 
#     entities = {}
# 
#     for extractor in ENTITY_EXTRACTORS:
#         append = extractor.extract_entities(text)
#         for entity, values in append.items():
#             entities.setdefault(entity, []).extend(values)
# 
#     logging.debug('Extracted entities:', entities)
#     append = parse_additional_entities(text)
# 
#     for (entity, value) in re.findall(re.compile(r'/([^/]+)/([^/]+)/'), text):
#         if not entity in append:
#             append[entity] = []
#         append[entity].append({'value': value})
# 
#     # add all new entity values
#     for entity, values in append.items():
#         if not entity in entities:
#             entities[entity] = []
#         entities[entity] += values
# 
#     entities['_message_text'] = [{'value': text}]
# 
#     parsed = {'entities': entities, 'type': 'message'}
# 
#     return parsed
# 
# Path: golem/tasks.py
# @shared_task
# def accept_user_message(session: dict, raw_message):
#     from golem.core.dialog_manager import DialogManager
#     session = ChatSession.from_json(session)
#     print("Accepting message - chat id {}, message: {}".format(session.chat_id, raw_message))
# 
#     dialog = DialogManager(session)
#     parsed = session.interface.parse_message(raw_message)
#     _process_message(dialog, parsed)
# 
#     should_log_messages = settings.GOLEM_CONFIG.get('SHOULD_LOG_MESSAGES', False)
# 
#     if should_log_messages and 'text' in raw_message:
#         text = raw_message['text']
#         message_logger.on_message.delay(session, text, dialog, from_user=True)
#     return True  # FIXME
# 
# Path: golem/webgui/models.py
# class WebMessageData(models.Model):
#     uid = models.TextField()
#     is_response = models.BooleanField()  # is this a response from the bot?
#     timestamp = models.DateTimeField(auto_now=True)
#     data = models.TextField()
# 
#     data_json = None
# 
#     def message(self):
#         if not self.data_json:
#             self.data_json = json.loads(self.data)
#         return self.data_json


import json
import logging
import random
from golem.core.chat_session import ChatSession
from golem.core.message_parser import parse_text_message
from golem.tasks import accept_user_message
from .models import WebMessageData
                from golem.core.serialize import json_deserialize
                payload['_message_text'] = [{'value': None}]
                return {'entities': payload, 'type': 'postback'}

    @staticmethod
    def accept_request(msg: WebMessageData):
        uid = str(msg.uid)

        logging.info('[WEBGUI] Received message from {}'.format(uid))
        session = ChatSession(WebGuiInterface, uid, meta={"uid": uid})
        accept_user_message.delay(session.to_json(), {"text": msg.message().get('text')})

    @staticmethod
    def accept_postback(msg: WebMessageData, data):
        uid = str(msg.uid)
        data = json.loads(data)

        logging.info('[WEBGUI] Received postback from {}'.format(uid))
        session = ChatSession(WebGuiInterface, uid, meta={"uid": uid})
        accept_user_message.delay(session.to_json(), {"_message_text": msg.message().get('text'), "payload": data})

    @staticmethod
    def make_uid(username) -> str:
        uid = None
        tries = 0
        while (not uid or len(WebMessageData.objects.filter(uid__exact=uid)) != 0) or tries < 100:
            uid = '_'.join([str(username), str(random.randint(1000, 99999))])
            tries += 1
        # delete messages for old session with this uid, if there was one
        # FIXME invalidate the previous user's session!
        try:

# Path: golem/core/chat_session.py
# class ChatSession:
# 
#     def __init__(self, interface, unique_id: str, meta=None, profile=None, is_logged=True, is_admin=False, is_test=False):
#         """
#         :param interface: Chat interface object
#         :param unique_id: A string that uniquely identifies the user within the interface
#         :param profile: Profile object
#         :param meta: Any interface-specific data. type: dict
#         """
#         if interface is None:
#             raise ValueError("Interface must be set")
#         elif not isinstance(unique_id, str):
#             raise ValueError("UID must be a string")
#         elif not isinstance(profile, Profile) and profile is not None:
#             raise ValueError("Profile must be instance of class Profile")
#         self.interface = interface
#         self.chat_id = self.interface.prefix + "_" + unique_id
#         self.profile = profile or Profile()
#         self.meta = meta or {}
#         self.is_logged = is_logged
#         self.is_admin = is_admin
#         self.is_test = is_test
# 
#     def to_json(self):
#         return {
#             "interface": self.interface.prefix,
#             "unique_id": self.chat_id.split('_', maxsplit=1)[1],
#             "profile": self.profile.to_json(),
#             "meta": self.meta,
#             "is_logged": self.is_logged,
#             "is_admin": self.is_admin
#         }
# 
#     @staticmethod
#     def from_json(data: dict):
#         interface = create_from_prefix(data['interface'])
#         return ChatSession(
#             interface=interface,
#             unique_id=data['unique_id'],
#             profile=Profile.from_json(data['profile']),
#             meta=data['meta'],
#             is_logged=data['is_logged'],
#             is_admin=data['is_admin']
#         )
# 
# Path: golem/core/message_parser.py
# def parse_text_message(text, num_tries=1):
#     if len(ENTITY_EXTRACTORS) <= 0:
#         logging.warning('No entity extractors configured!')
#         return {'type': 'message', 'entities': {'_message_text': [{'value': text}]}}
# 
#     entities = {}
# 
#     for extractor in ENTITY_EXTRACTORS:
#         append = extractor.extract_entities(text)
#         for entity, values in append.items():
#             entities.setdefault(entity, []).extend(values)
# 
#     logging.debug('Extracted entities:', entities)
#     append = parse_additional_entities(text)
# 
#     for (entity, value) in re.findall(re.compile(r'/([^/]+)/([^/]+)/'), text):
#         if not entity in append:
#             append[entity] = []
#         append[entity].append({'value': value})
# 
#     # add all new entity values
#     for entity, values in append.items():
#         if not entity in entities:
#             entities[entity] = []
#         entities[entity] += values
# 
#     entities['_message_text'] = [{'value': text}]
# 
#     parsed = {'entities': entities, 'type': 'message'}
# 
#     return parsed
# 
# Path: golem/tasks.py
# @shared_task
# def accept_user_message(session: dict, raw_message):
#     from golem.core.dialog_manager import DialogManager
#     session = ChatSession.from_json(session)
#     print("Accepting message - chat id {}, message: {}".format(session.chat_id, raw_message))
# 
#     dialog = DialogManager(session)
#     parsed = session.interface.parse_message(raw_message)
#     _process_message(dialog, parsed)
# 
#     should_log_messages = settings.GOLEM_CONFIG.get('SHOULD_LOG_MESSAGES', False)
# 
#     if should_log_messages and 'text' in raw_message:
#         text = raw_message['text']
#         message_logger.on_message.delay(session, text, dialog, from_user=True)
#     return True  # FIXME
# 
# Path: golem/webgui/models.py
# class WebMessageData(models.Model):
#     uid = models.TextField()
#     is_response = models.BooleanField()  # is this a response from the bot?
#     timestamp = models.DateTimeField(auto_now=True)
#     data = models.TextField()
# 
#     data_json = None
# 
#     def message(self):
#         if not self.data_json:
#             self.data_json = json.loads(self.data)
#         return self.data_json


# Path: golem/webgui/interface.py
import json
import logging
import random
from golem.core.chat_session import ChatSession
from golem.core.message_parser import parse_text_message
from golem.tasks import accept_user_message
from .models import WebMessageData
                from golem.core.serialize import json_deserialize

                payload['_message_text'] = [{'value': None}]
                return {'entities': payload, 'type': 'postback'}

    @staticmethod
    def accept_request(msg: WebMessageData):
        uid = str(msg.uid)

        logging.info('[WEBGUI] Received message from {}'.format(uid))
        session = ChatSession(WebGuiInterface, uid, meta={"uid": uid})
        accept_user_message.delay(session.to_json(), {"text": msg.message().get('text')})

    @staticmethod
    def accept_postback(msg: WebMessageData, data):
        uid = str(msg.uid)
        data = json.loads(data)

        logging.info('[WEBGUI] Received postback from {}'.format(uid))
        session = ChatSession(WebGuiInterface, uid, meta={"uid": uid})
        accept_user_message.delay(session.to_json(), {"_message_text": msg.message().get('text'), "payload": data})

    @staticmethod
    def make_uid(username) -> str:
        uid = None
        tries = 0
        while (not uid or len(WebMessageData.objects.filter(uid__exact=uid)) != 0) or tries < 100:
            uid = '_'.join([str(username), str(random.randint(1000, 99999))])
            tries += 1
        # delete messages for old session with this uid, if there was one
        # FIXME invalidate the previous user's session!
        try:

            WebMessageData.objects.get(uid__exact=uid).delete()