Пример #1
0
    def test_on_register(self):
        """Test the _on_register method of the tac handler, the successful case."""
        # setup
        self.game._phase = Phase.GAME_REGISTRATION

        incoming_message = self.build_incoming_message(
            message_type=TacMessage,
            performative=TacMessage.Performative.REGISTER,
            dialogue_reference=Dialogues.new_self_initiated_dialogue_reference(
            ),
            agent_name=self.agent_name,
        )

        # before
        assert self.game.registration.nb_agents == 0

        # operation
        with patch.object(self.tac_handler.context.logger,
                          "log") as mock_logger:
            self.tac_handler.handle(incoming_message)

        # after
        mock_logger.assert_any_call(logging.INFO,
                                    f"agent registered: '{self.agent_name}'")
        assert self.game.registration.nb_agents == 1
Пример #2
0
    def test_on_register_agent_name_already_exists(self):
        """Test the _on_register method of the tac handler where the agent name of the sender is already registered."""
        # setup
        self.game._phase = Phase.GAME_REGISTRATION
        self.game._registration.register_agent("some_address", self.agent_name)

        incoming_message = self.build_incoming_message(
            message_type=TacMessage,
            performative=TacMessage.Performative.REGISTER,
            dialogue_reference=Dialogues.new_self_initiated_dialogue_reference(
            ),
            agent_name=self.agent_name,
        )

        # operation
        with patch.object(self.tac_handler.context.logger,
                          "log") as mock_logger:
            self.tac_handler.handle(incoming_message)

        # after
        mock_logger.assert_any_call(
            logging.WARNING,
            f"agent with this name already registered: '{self.agent_name}'",
        )
        self.assert_quantity_in_outbox(1)
        has_attributes, error_str = self.message_has_attributes(
            actual_message=self.get_message_from_outbox(),
            message_type=TacMessage,
            performative=TacMessage.Performative.TAC_ERROR,
            to=COUNTERPARTY_ADDRESS,
            sender=self.skill.skill_context.agent_address,
            target=incoming_message.message_id,
            error_code=TacMessage.ErrorCode.AGENT_NAME_ALREADY_REGISTERED,
        )
        assert has_attributes, error_str
Пример #3
0
    def test_on_register_agent_not_in_whitelist(self):
        """Test the _on_register method of the tac handler where the agent is NOT in the whitelist."""
        # setup
        self.game._phase = Phase.GAME_REGISTRATION
        self.parameters._whitelist = ["some_other_agent", "yet_another_agent"]

        incoming_message = self.build_incoming_message(
            message_type=TacMessage,
            performative=TacMessage.Performative.REGISTER,
            dialogue_reference=Dialogues.new_self_initiated_dialogue_reference(
            ),
            agent_name=self.agent_name,
        )

        # operation
        with patch.object(self.tac_handler.context.logger,
                          "log") as mock_logger:
            self.tac_handler.handle(incoming_message)

        # after
        mock_logger.assert_any_call(
            logging.WARNING,
            f"agent name not in whitelist: '{self.agent_name}'")
        self.assert_quantity_in_outbox(1)
        has_attributes, error_str = self.message_has_attributes(
            actual_message=self.get_message_from_outbox(),
            message_type=TacMessage,
            performative=TacMessage.Performative.TAC_ERROR,
            to=COUNTERPARTY_ADDRESS,
            sender=self.skill.skill_context.agent_address,
            target=incoming_message.message_id,
            error_code=TacMessage.ErrorCode.AGENT_NAME_NOT_IN_WHITELIST,
        )
        assert has_attributes, error_str
Пример #4
0
    def test_handle_cfp_is_matching_supply(self):
        """Test the _handle_cfp method of the fipa handler where is_matching_supply is True."""
        # setup
        proposal = Description({
            "ledger_id": "some_ledger_id",
            "price": 100,
            "currency_id": "FET",
            "service_id": "some_service_id",
            "quantity": 1,
            "tx_nonce": "some_tx_nonce",
        })
        terms = "some_terms"
        data = {"data_type": "data"}

        incoming_message = self.build_incoming_message(
            message_type=FipaMessage,
            performative=FipaMessage.Performative.CFP,
            dialogue_reference=Dialogues.new_self_initiated_dialogue_reference(
            ),
            query="some_query",
        )

        # operation
        with patch.object(
                self.strategy,
                "is_matching_supply",
                return_value=True,
        ):
            with patch.object(
                    self.strategy,
                    "generate_proposal_terms_and_data",
                    return_value=(proposal, terms, data),
            ):
                with patch.object(self.fipa_handler.context.logger,
                                  "log") as mock_logger:
                    self.fipa_handler.handle(incoming_message)

        # after
        mock_logger.assert_any_call(
            logging.INFO,
            f"received CFP from sender={COUNTERPARTY_ADDRESS[-5:]}")
        mock_logger.assert_any_call(
            logging.INFO,
            f"sending a PROPOSE with proposal={proposal.values} to sender={COUNTERPARTY_ADDRESS[-5:]}",
        )

        self.assert_quantity_in_outbox(1)

        has_attributes, error_str = self.message_has_attributes(
            actual_message=self.get_message_from_outbox(),
            message_type=FipaMessage,
            performative=FipaMessage.Performative.PROPOSE,
            to=COUNTERPARTY_ADDRESS,
            sender=self.skill.skill_context.agent_address,
            target=incoming_message.message_id,
            proposal=proposal,
        )
        assert has_attributes, error_str
Пример #5
0
    def build_incoming_message(
        self,
        message_type: Type[Message],
        performative: Message.Performative,
        dialogue_reference: Optional[Tuple[str, str]] = None,
        message_id: Optional[int] = None,
        target: Optional[int] = None,
        to: Optional[Address] = None,
        sender: Address = COUNTERPARTY_ADDRESS,
        **kwargs,
    ) -> Message:
        """
        Quickly create an incoming message with the provided attributes.

        For any attribute not provided, the corresponding default value in message is used.

        :param message_type: the type of the message
        :param dialogue_reference: the dialogue_reference
        :param message_id: the message_id
        :param target: the target
        :param performative: the performative
        :param to: the 'to' address
        :param sender: the 'sender' address
        :param kwargs: other attributes

        :return: the created incoming message
        """
        message_attributes = dict()  # type: Dict[str, Any]

        default_dialogue_reference = Dialogues.new_self_initiated_dialogue_reference()
        dialogue_reference = (
            default_dialogue_reference
            if dialogue_reference is None
            else dialogue_reference
        )
        message_attributes["dialogue_reference"] = dialogue_reference
        if message_id is not None:
            message_attributes["message_id"] = message_id
        if target is not None:
            message_attributes["target"] = target
        message_attributes["performative"] = performative
        message_attributes.update(kwargs)

        incoming_message = message_type(**message_attributes)
        incoming_message.sender = sender
        incoming_message.to = (
            self.skill.skill_context.agent_address if to is None else to
        )

        return incoming_message
Пример #6
0
    def test_handle_cfp_not_is_matching_supply(self):
        """Test the _handle_cfp method of the fipa handler where is_matching_supply is False."""
        # setup
        incoming_message = self.build_incoming_message(
            message_type=FipaMessage,
            performative=FipaMessage.Performative.CFP,
            dialogue_reference=Dialogues.new_self_initiated_dialogue_reference(
            ),
            query="some_query",
        )

        # operation
        with patch.object(self.strategy,
                          "is_matching_supply",
                          return_value=False):
            with patch.object(self.fipa_handler.context.logger,
                              "log") as mock_logger:
                self.fipa_handler.handle(incoming_message)

        # after
        mock_logger.assert_any_call(
            logging.INFO,
            f"received CFP from sender={COUNTERPARTY_ADDRESS[-5:]}")
        mock_logger.assert_any_call(
            logging.INFO,
            f"declined the CFP from sender={COUNTERPARTY_ADDRESS[-5:]}")

        self.assert_quantity_in_outbox(1)

        has_attributes, error_str = self.message_has_attributes(
            actual_message=self.get_message_from_outbox(),
            message_type=FipaMessage,
            performative=FipaMessage.Performative.DECLINE,
            to=COUNTERPARTY_ADDRESS,
            sender=self.skill.skill_context.agent_address,
            target=incoming_message.message_id,
        )
        assert has_attributes, error_str
Пример #7
0
    def test_on_register_not_pre_reg_phase(self):
        """Test the _on_register method of the tac handler where phase is NOT pre_registration."""
        # setup
        self.game._phase = Phase.PRE_GAME

        incoming_message = self.build_incoming_message(
            message_type=TacMessage,
            performative=TacMessage.Performative.REGISTER,
            dialogue_reference=Dialogues.new_self_initiated_dialogue_reference(
            ),
            agent_name=self.agent_name,
        )

        # operation
        with patch.object(self.tac_handler.context.logger,
                          "log") as mock_logger:
            self.tac_handler.handle(incoming_message)

        # after
        mock_logger.assert_any_call(
            logging.WARNING,
            f"received registration outside of game registration phase: '{incoming_message}'",
        )
Пример #8
0
    def prepare_skill_dialogue(
        self,
        dialogues: Dialogues,
        messages: Tuple[DialogueMessage, ...],
        counterparty: Address = COUNTERPARTY_ADDRESS,
    ) -> Dialogue:
        """
        Quickly create a dialogue.

        The 'messages' argument is a tuple of DialogueMessages.
        For every DialogueMessage (performative, contents, is_incoming, target):
            - if 'is_incoming' is not provided: for the first message it is assumed False (outgoing),
            for any other message, it is the opposite of the one preceding it.
            - if 'target' is not provided: for the first message it is assumed 0,
            for any other message, it is the index of the message before it in the tuple of messages + 1.

        :param dialogues: a dialogues class
        :param counterparty: the message_id
        :param messages: the dialogue_reference

        :return: the created incoming message
        """
        if len(messages) == 0:
            raise AEAEnforceError("the list of messages must be positive.")

        (
            performative,
            contents,
            message_id,
            is_incoming,
            target,
        ) = self._extract_message_fields(messages[0], index=0, last_is_incoming=True)

        if is_incoming:  # first message from the opponent
            dialogue_reference = dialogues.new_self_initiated_dialogue_reference()
            message = self.build_incoming_message(
                message_type=dialogues.message_class,
                dialogue_reference=dialogue_reference,
                message_id=message_id,
                target=target,
                performative=performative,
                to=self.skill.skill_context.agent_address,
                sender=counterparty,
                **contents,
            )
            dialogue = cast(Dialogue, dialogues.update(message))
            if dialogue is None:
                raise AEAEnforceError(
                    "Cannot update the dialogue with message number {}".format(
                        message_id
                    )
                )
        else:  # first message from self
            _, dialogue = dialogues.create(
                counterparty=counterparty, performative=performative, **contents
            )

        for idx, dialogue_message in enumerate(messages[1:]):
            (
                performative,
                contents,
                message_id,
                is_incoming,
                target,
            ) = self._extract_message_fields(dialogue_message, idx + 1, is_incoming)
            if is_incoming:  # messages from the opponent
                dialogue_reference = self._non_initial_incoming_message_dialogue_reference(
                    dialogue
                )
                message = self.build_incoming_message(
                    message_type=dialogues.message_class,
                    dialogue_reference=dialogue_reference,
                    message_id=message_id,
                    target=target,
                    performative=performative,
                    to=self.skill.skill_context.agent_address,
                    sender=counterparty,
                    **contents,
                )
                dialogue = cast(Dialogue, dialogues.update(message))
                if dialogue is None:
                    raise AEAEnforceError(
                        "Cannot update the dialogue with message number {}".format(
                            message_id
                        )
                    )
            else:  # messages from self
                dialogue.reply(performative=performative, target=target, **contents)

        return dialogue