diff --git a/duniterpy/documents/transaction.py b/duniterpy/documents/transaction.py index eba7def48870c32955ee4706316461451b9918b4..d2802757303157e4da04f8d9aee79beae34ae4a9 100644 --- a/duniterpy/documents/transaction.py +++ b/duniterpy/documents/transaction.py @@ -467,6 +467,7 @@ class Unlock: TransactionType = TypeVar("TransactionType", bound="Transaction") +# pylint: disable=W0223 class Transaction(Document): """ .. note:: A transaction document is specified by the following format : @@ -549,7 +550,7 @@ class Transaction(Document): outputs: List[OutputSource], comment: str, time: Optional[int] = None, - signing_key: SigningKey = None, + signing_keys: Optional[List[SigningKey]] = None, version: int = VERSION, currency: str = G1_CURRENCY_CODENAME, ) -> None: @@ -564,7 +565,7 @@ class Transaction(Document): :param outputs: List of OutputSource instances :param comment: Comment field :param time: time when the transaction enters the blockchain - :param signing_key: SigningKey instance to sign the document (default=None) + :param signing_keys: SigningKey instance to sign the document (default=None) :param version: Document version (default=transaction.VERSION) :param currency: Currency codename (default=constants.CURRENCY_CODENAME_G1) """ @@ -579,8 +580,8 @@ class Transaction(Document): self.time = time self.signatures: List[str] = list() - if signing_key is not None: - self.sign(signing_key) + if signing_keys is not None: + self.multi_sign(signing_keys) def __eq__(self, other: Any) -> bool: """ @@ -591,7 +592,6 @@ class Transaction(Document): return ( self.version == other.version and self.currency == other.currency - and self.signature == other.signature and self.signatures == other.signatures and self.blockstamp == other.blockstamp and self.locktime == other.locktime @@ -608,7 +608,6 @@ class Transaction(Document): ( self.version, self.currency, - self.signature, self.signatures, self.blockstamp, self.locktime, @@ -744,10 +743,7 @@ Comment: {comment} ) # return transaction with signatures - if len(signatures) > 1: - transaction.signatures = signatures - else: - transaction.signature = signatures[0] + transaction.signatures = signatures return transaction @classmethod @@ -837,11 +833,7 @@ Comment: {comment} ) # return transaction with signatures - if len(signatures) > 1: - transaction.signatures = signatures - else: - transaction.signature = signatures[0] - + transaction.signatures = signatures return transaction def raw(self) -> str: @@ -917,11 +909,8 @@ Currency: {1} doc += "{0}\n".format(o.inline()) if self.comment != "": doc += "{0}\n".format(self.comment) - if self.signature is not None: - doc += "{0}\n".format(self.signature) - else: - for signature in self.signatures: - doc += "{0}\n".format(signature) + for signature in self.signatures: + doc += "{0}\n".format(signature) return doc @@ -931,25 +920,22 @@ Currency: {1} :return: """ - if self.signature is None and len(self.signatures) == 0: + if not self.signatures: raise MalformedDocumentError("No signature, can not create raw format") - raw = self.raw() - if self.signature is not None: - signed_raw = raw + self.signature + "\n" - else: - signed_raw = raw - for signature in self.signatures: - signed_raw += "{0}\n".format(signature) + signed_raw = self.raw() + for signature in self.signatures: + signed_raw += f"{signature}\n" return signed_raw + def sign(self, key: SigningKey) -> None: + raise NotImplementedError("sign() is not implemented, use multi_sign([key])") + def multi_sign(self, keys: List[SigningKey]) -> None: """ Sign the current document with multiple keys - Warning : current signatures will be replaced with the new ones. - :param keys: List of libnacl keys instance """ self.signatures = list() @@ -958,6 +944,11 @@ Currency: {1} logging.debug("Signature : \n%s", signature.decode("ascii")) self.signatures.append(signature.decode("ascii")) + def check_signature(self, pubkey: str): + raise NotImplementedError( + "check_signature() is not implemented, use check_signatures([pubkey])" + ) + def check_signatures(self, pubkeys: List[str]): """ Check if the signatures matches the pubkeys @@ -966,7 +957,7 @@ Currency: {1} :return: """ - if len(self.signatures) == 0: + if not self.signatures: raise Exception("No signatures, can not check signatures") if len(self.signatures) != len(pubkeys): @@ -1000,7 +991,7 @@ class SimpleTransaction(Transaction): outputs: List[OutputSource], comment: str, time: int = 0, - signing_key: SigningKey = None, + signing_keys: Optional[List[SigningKey]] = None, version: int = VERSION, currency: str = G1_CURRENCY_CODENAME, ) -> None: @@ -1015,7 +1006,7 @@ class SimpleTransaction(Transaction): :param outputs: List of OutputSource instances :param comment: Comment field :param time: time when the transaction enters the blockchain (default=0) - :param signing_key: SigningKey instance to sign the document (default=None) + :param signing_keys: SigningKey instance to sign the document (default=None) :param version: Document version (default=transaction.VERSION) :param currency: Currency codename (default=constants.CURRENCY_CODENAME_G1) """ @@ -1028,7 +1019,7 @@ class SimpleTransaction(Transaction): outputs, comment, time=time, - signing_key=signing_key, + signing_keys=signing_keys, version=version, currency=currency, ) diff --git a/examples/send_transaction.py b/examples/send_transaction.py index 7560facd53bfb1bf756256b2aa5153dba14d8c0e..d65643d008c7a98c2d798e1d355399de9c82bee5 100644 --- a/examples/send_transaction.py +++ b/examples/send_transaction.py @@ -15,6 +15,7 @@ import getpass import urllib +from typing import List from duniterpy.api import bma from duniterpy.api.client import Client @@ -42,7 +43,7 @@ def get_transaction_document( source: dict, from_pubkey: str, to_pubkey: str, - signing_key: SigningKey, + signing_keys: List[SigningKey], ) -> Transaction: """ Return a Transaction document @@ -96,7 +97,7 @@ def get_transaction_document( unlocks=unlocks, outputs=outputs, comment="", - signing_key=signing_key, + signing_keys=signing_keys, currency=current_block["currency"], ) @@ -142,7 +143,7 @@ def send_transaction(): # create the transaction document transaction = get_transaction_document( - current_block, source, pubkey_from, pubkey_to, key + current_block, source, pubkey_from, pubkey_to, [key] ) # send the Transaction document to the node diff --git a/tests/key/test_verifying_key.py b/tests/key/test_verifying_key.py index c6ffb7aed812312dca076169237216ccf3baf715..38016937b67d00cd8d3ee90b7024d29075aca922 100644 --- a/tests/key/test_verifying_key.py +++ b/tests/key/test_verifying_key.py @@ -147,4 +147,4 @@ Solde huile Millepertuis rgjOmzFH5h+hkDbJLk1b88X7Z83HMgTa5rBckeMSdF/yZtItN3zMn09MphcXjffdrKcK+MebwoisLJqV+jXrDg== """ tx = Transaction.from_compact(transaction_document, "g1") - self.assertTrue(tx.check_signature(tx.issuers[0])) + self.assertTrue(tx.check_signatures(tx.issuers))