import copy
import datetime
import json
import random
import uuid
import numpy
import spade


def get_json_from_spade_message(msg):
    return json.loads(msg.body)


def get_spade_message(sender_jid, receiver_jid, body):
    msg = spade.message.Message(to=receiver_jid)
    body["sender"] = str(sender_jid)
    msg.metadata["type"] = body["type"]
    msg.metadata["performative"] = body["performative"]
    msg.body = json.dumps(body)
    return msg


class average_user(spade.agent.Agent):
    def __init__(self, jid, password, connections):
        super().__init__(jid, password, verify_security=False)
        self.connections = connections
        self.msgRCount = 0
        self.msgSCount = 0
        self.friends = []
    
    @property
    def connCount(self):
        return len(self.connections)
    
    def setup(self):
        self.add_behaviour(self.facebook_activity(period=30))
    
    class facebook_activity(spade.behaviour.PeriodicBehaviour):
        async def post_photos(self):
            send = { "type": "facebook_post", "performative": "query", "photos": 0.0, }
            num_photos = 0
            num_photos = numpy.random.normal(21, 37)
            num_photos = round(num_photos)
            send["photos"] = num_photos
            for receiver in self.agent.friends:
                await self.send(get_spade_message(self.agent.jid, receiver, send))
                self.agent.msgSCount += 1
        
        async def run(self):
            await self.post_photos()
    
def generate_graph_structure(domain):
    _num_average_user = round(100 / 100 * 150)
    num_agents = _num_average_user
    random_id = uuid.uuid4().hex
    jids = [f"{i}_{random_id}@{domain}" for i in range(num_agents)]
    agents = []
    next_agent_idx = 0
    for _ in range(_num_average_user):
        num_connections = int(numpy.random.normal(0, 15))
        num_connections = max(min(num_connections, len(jids)), 0)
        agents.append({
            "jid": jids[next_agent_idx],
            "type": "average_user",
            "connections": random.sample(jids, num_connections),
        })
        next_agent_idx += 1
    return json.dumps(agents)
