<reponame>ltonetwork/lto-api.python
from LTO.Accounts.AccountFactoryED25519 import AccountED25519 as AccountFactory
from LTO.Transactions.Association import Association
from unittest import mock
from time import time

class TestAssociation:

    ACCOUNT_SEED = "<KEY>"
    account = AccountFactory('T').createFromSeed(ACCOUNT_SEED)

    def testContruct(self):
        transaction = Association('3N3Cn2pYtqzj7N9pviSesNe8KG9Cmb718Y1', 1)
        assert transaction.txFee == 100000000
        assert transaction.associationType == 1
        assert transaction.recipient == '3N3Cn2pYtqzj7N9pviSesNe8KG9Cmb718Y1'


    def testSignWith(self):
        transaction = Association('3N3Cn2pYtqzj7N9pviSesNe8KG9Cmb718Y1', 1)
        assert transaction.isSigned() is False
        transaction.signWith(self.account)
        assert transaction.isSigned() is True
        timestamp = int(time() * 1000)
        assert str(transaction.timestamp)[:-3] == str(timestamp)[:-3]
        assert transaction.sender == '3MtHYnCkd3oFZr21yb2vEdngcSGXvuNNCq2'
        assert transaction.senderPublicKey == '<KEY>'
        assert self.account.verifySignature(transaction.toBinary(), transaction.proofs[0])


    def expectedV1(self):
        return({'associationType': 1,
                'fee': 100000000,
                'hash': 'HiorsQW6E76Cp4AD51zcKcWu644ZzzraXQL286Jjzufh7U7qJroTKt7KMMpv',
                'proofs': ['<KEY>'],
                'recipient': '<KEY>',
                'sender': '<KEY>',
                'senderPublicKey': '<KEY>',
                'timestamp': 1629883934685,
                'type': 16,
                'version': 1})


    def expectedV3(self):
        return({
            "type": 16,
            "version": 3,
            "sender": "<KEY>",
            "senderKeyType": "ed25519",
            "senderPublicKey": '<KEY>',
            "recipient": '<KEY>',
            "associationType": 1,
            "hash": 'HiorsQW6E76Cp4AD51zcKcWu644ZzzraXQL286Jjzufh7U7qJroTKt7KMMpv',
            "timestamp": 1629883934685,
            "expires": 1841961856000,
            "fee": 100000000,
            "proofs": ['<KEY>'],
        })


    def testToJson(self):
        transaction = Association('3N3Cn2pYtqzj7N9pviSesNe8KG9Cmb718Y1', 1, anchor='<KEY>', expires= 1841961856000)
        #transaction = Association('3N3Cn2pYtqzj7N9pviSesNe8KG9Cmb718Y1', 1, anchor='<KEY>', expires=1841961856000)
        transaction.timestamp = 1629883934685
        transaction.signWith(self.account)

        if transaction.version == 1:
            expected = self.expectedV1()
        elif transaction.version == 3:
            expected = self.expectedV3()
        else:
            expected = ''

        assert transaction.toJson() == expected

    @mock.patch('src.LTO.PublicNode')
    def testBroadcast(self, mock_Class):
        transaction = Association('3N3Cn2pYtqzj7N9pviSesNe8KG9Cmb718Y1', 1, anchor='<KEY>')
        broadcastedTransaction = Association('3N3Cn2pYtqzj7N9pviSesNe8KG9Cmb718Y1', 1, anchor='<KEY>')
        broadcastedTransaction.id = '7cCeL1qwd9i6u8NgMNsQjBPxVhrME2BbfZMT1DF9p4Yi'
        mc = mock_Class.return_value
        mc.broadcast.return_value = broadcastedTransaction
        assert mc.broadcast(transaction) == broadcastedTransaction

    def testFromData(self):
        data = {
            "type": 16,
            "version": 3,
            "recipient": "3N9ChkxWXqgdWLLErWFrSwjqARB6NtYsvZh",
            "associationType": 1,
            "hash": "3yMApqCuCjXDWPrbjfR5mjCPTHqFG8Pux1TxQrEM35jj",
            "id": "1uZqDjRjaehEceSxrVxz6WD6wt8su8TBHyDLQ1KFnJo",
            "sender": "3NBcx7AQqDopBj3WfwCVARNYuZyt1L9xEVM",
            "senderPublicKey": "<KEY>",
            "timestamp": 1610404930000,
            "expires": 1841961856000,
            "fee": 100000000,
            "proofs": [
                "<KEY>"
            ],
            "height": 1225712
        }
        transaction = Association(recipient='', associationType='').fromData(data)

        for key in data:
            assert data[key] == transaction.__getattr__(key)
