From 1aca28b1f5bf941c08d10963d24147443f86fde8 Mon Sep 17 00:00:00 2001 From: Moul <moul@moul.re> Date: Wed, 10 Nov 2021 18:11:30 +0100 Subject: [PATCH] =?UTF-8?q?[enh]=20#187:=20Implement=20=5F=5Feq=5F=5F=20an?= =?UTF-8?q?d=20=5F=5Fhash=5F=5F=20Certification=E2=80=99s=20methods?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- duniterpy/documents/certification.py | 27 ++++++++++++++++++- tests/documents/test_certification.py | 37 ++++++++++++++++++++++++--- 2 files changed, 59 insertions(+), 5 deletions(-) diff --git a/duniterpy/documents/certification.py b/duniterpy/documents/certification.py index 9b3b857b..0ee90038 100644 --- a/duniterpy/documents/certification.py +++ b/duniterpy/documents/certification.py @@ -14,7 +14,7 @@ # along with this program. If not, see <http://www.gnu.org/licenses/>. import re -from typing import Optional, Type, TypeVar, Union +from typing import Any, Optional, Type, TypeVar, Union from ..constants import ( BLOCK_ID_REGEX, @@ -80,6 +80,31 @@ class Certification(Document): if signing_key is not None: self.sign(signing_key) + def __eq__(self, other: Any) -> bool: + """ + Check Certification instances equality + """ + if not isinstance(other, Certification): + return NotImplemented + return ( + super().__eq__(other) + and self.pubkey_from == other.pubkey_from + and self.identity == other.identity + and self.block_id == other.block_id + ) + + def __hash__(self) -> int: + return hash( + ( + self.pubkey_from, + self.identity, + self.block_id, + self.version, + self.currency, + self.signature, + ) + ) + @classmethod def from_signed_raw( cls: Type[CertificationType], signed_raw: str diff --git a/tests/documents/test_certification.py b/tests/documents/test_certification.py index 94ee5365..dfee42c9 100644 --- a/tests/documents/test_certification.py +++ b/tests/documents/test_certification.py @@ -15,11 +15,16 @@ import unittest -from duniterpy.constants import EMPTY_HASH +import pytest + +from duniterpy.constants import EMPTY_HASH, G1_TEST_CURRENCY_CODENAME +from duniterpy.documents import Certification, Identity, Revocation from duniterpy.documents.block import BlockID -from duniterpy.documents.certification import Certification -from duniterpy.documents.identity import Identity -from duniterpy.documents.revocation import Revocation + +PUBKEY = "A" +UID = "test" +BLOCK_ID = "0-NRSATU" +IDENTITY_KWARGS = [PUBKEY, UID, BLOCK_ID] selfcert_inlines = [ "HnFcSms8jzwngtVomTTnzudZx7SHUQY8sVE1y8yBmULk:\ @@ -223,3 +228,27 @@ SoKwoa8PFfCDJWZ6dNCv7XstezHcc2BbKiJgVDXv82R5zYR83nis9dShLgWJ5w48noVUHimdngzYQneN revocation = Revocation.from_signed_raw(signed_raw) self.assertTrue(isinstance(Revocation.extract_self_cert(signed_raw), Identity)) self.assertEqual(revocation.signed_raw(), signed_raw) + + +def test_certification_equality(): + cert1 = Certification(PUBKEY, Identity(*IDENTITY_KWARGS), BLOCK_ID) + cert2 = Certification(PUBKEY, Identity(*IDENTITY_KWARGS), BLOCK_ID) + assert cert1 == cert2 + + +@pytest.mark.parametrize( + "pubkey, uid, block_id, currency", + [ + ("pubkey", UID, BLOCK_ID, None), + (PUBKEY, "uid", BLOCK_ID, None), + (PUBKEY, UID, "1-TEST", None), + IDENTITY_KWARGS + [G1_TEST_CURRENCY_CODENAME], + ], +) +def test_certification_inequality(pubkey, uid, block_id, currency): + cert1 = Certification(pubkey, Identity(*IDENTITY_KWARGS), block_id) + idty2 = Identity(pubkey, uid, block_id) + cert2 = Certification(pubkey, idty2, block_id) + if currency: + cert2.currency = currency + assert not cert1 == cert2 -- GitLab