diff --git a/src/keria/testing/testing_helper.py b/src/keria/testing/testing_helper.py index 167576ba..30ac6313 100644 --- a/src/keria/testing/testing_helper.py +++ b/src/keria/testing/testing_helper.py @@ -468,7 +468,7 @@ def createAid(client, name, salt, wits=None, toad="0", delpre=None): salter = core.Salter(raw=salt) encrypter = core.Encrypter(verkey=signers[0].verfer.qb64) - sxlt = encrypter.encrypt(salter.qb64).qb64 + sxlt = encrypter.encrypt(ser=salter.qb64).qb64 sigers = [signer.sign(ser=serder.raw, index=0).qb64 for signer in signers] diff --git a/tests/app/test_agenting.py b/tests/app/test_agenting.py index 61afd8a9..3782595e 100644 --- a/tests/app/test_agenting.py +++ b/tests/app/test_agenting.py @@ -8,23 +8,20 @@ import json import os import shutil -import time -import unittest -from unittest.mock import patch, MagicMock import pytest import falcon -from falcon import testing import hio +from falcon import testing from hio.base import doing, tyming from hio.core import http, tcp from hio.help import decking from keri import kering -from keri.app import configing, habbing, indirecting, oobiing, querying +from keri.app import habbing, configing, indirecting, oobiing, querying from keri.app.agenting import Receiptor, WitnessReceiptor from keri import core -from keri.core import coring, eventing, indexing, parsing, serdering +from keri.core import coring, serdering from keri.core.coring import MtrDex from keri.db import basing, dbing from keri.help import nowIso8601 @@ -35,16 +32,14 @@ from keria.core import longrunning from keria.testing.testing_helper import SCRIPTS_DIR + def test_setup_no_http(): doers = agenting.setup(name="test", bran=None, adminPort=1234, bootPort=5678) assert len(doers) == 3 assert isinstance(doers[0], agenting.Agency) is True - def test_setup(): - doers = agenting.setup( - "test", bran=None, adminPort=1234, bootPort=5678, httpPort=9999 - ) + doers = agenting.setup("test", bran=None, adminPort=1234, bootPort=5678, httpPort=9999) assert len(doers) == 4 @@ -117,23 +112,15 @@ def test_load_tocks_config(helpers): def test_agency(): - salt = b"0123456789abcdef" + salt = b'0123456789abcdef' salter = core.Salter(raw=salt) - cf = configing.Configer( - name="keria", headDirPath=SCRIPTS_DIR, temp=True, reopen=True, clear=False - ) + cf = configing.Configer(name="keria", headDirPath=SCRIPTS_DIR, temp=True, reopen=True, clear=False) with habbing.openHby(name="keria", salt=salter.qb64, temp=True, cf=cf) as hby: hab = hby.makeHab(name="test") - agency = agenting.Agency( - name="agency", - base="", - bran=None, - temp=True, - configFile="keria", - configDir=SCRIPTS_DIR, - ) + agency = agenting.Agency(name="agency", base="", bran=None, temp=True, configFile="keria", + configDir=SCRIPTS_DIR) assert agency.cf is not None assert agency.cf.path.endswith("scripts/keri/cf/keria.json") is True @@ -165,22 +152,17 @@ def test_agency(): base = "keria-temp" # Clean up afterwards - if os.path.exists(f"/usr/local/var/keri/db/{base}"): - shutil.rmtree(f"/usr/local/var/keri/db/{base}") - if os.path.exists(f"/usr/local/var/keri/ks/{base}"): - shutil.rmtree(f"/usr/local/var/keri/ks/{base}") - if os.path.exists(f"/usr/local/var/keri/ks/{base}"): - shutil.rmtree(f"/usr/local/var/keri/ks/{base}") - if os.path.exists(f"/usr/local/var/keri/adb/{base}"): - shutil.rmtree(f"/usr/local/var/keri/adb/{base}") - - agency = agenting.Agency( - name="agency", - base=base, - bran=None, - configFile="keria", - configDir=SCRIPTS_DIR, - ) + if os.path.exists(f'/usr/local/var/keri/db/{base}'): + shutil.rmtree(f'/usr/local/var/keri/db/{base}') + if os.path.exists(f'/usr/local/var/keri/ks/{base}'): + shutil.rmtree(f'/usr/local/var/keri/ks/{base}') + if os.path.exists(f'/usr/local/var/keri/ks/{base}'): + shutil.rmtree(f'/usr/local/var/keri/ks/{base}') + if os.path.exists(f'/usr/local/var/keri/adb/{base}'): + shutil.rmtree(f'/usr/local/var/keri/adb/{base}') + + agency = agenting.Agency(name="agency", base=base, bran=None, configFile="keria", + configDir=SCRIPTS_DIR) assert agency.cf is not None assert agency.cf.path.endswith("scripts/keri/cf/keria.json") is True @@ -194,27 +176,22 @@ def test_agency(): assert agent.pre == "EEXekkGu9IAzav6pZVJhkLnjtjM5v3AcyA-pdKUcaGei" # Rcreate the agency to see if agent is reloaded from disk - agency = agenting.Agency( - name="agency", - base=base, - bran=None, - configFile="keria", - configDir=SCRIPTS_DIR, - ) + agency = agenting.Agency(name="agency", base=base, bran=None, configFile="keria", + configDir=SCRIPTS_DIR) doist.enter(doers=[agency]) agent = agency.get(caid) assert agent.pre == "EEXekkGu9IAzav6pZVJhkLnjtjM5v3AcyA-pdKUcaGei" # Clean up afterwards - if os.path.exists(f"/usr/local/var/keri/db/{base}"): - shutil.rmtree(f"/usr/local/var/keri/db/{base}") - if os.path.exists(f"/usr/local/var/keri/ks/{base}"): - shutil.rmtree(f"/usr/local/var/keri/ks/{base}") - if os.path.exists(f"/usr/local/var/keri/ks/{base}"): - shutil.rmtree(f"/usr/local/var/keri/ks/{base}") - if os.path.exists(f"/usr/local/var/keri/adb/{base}"): - shutil.rmtree(f"/usr/local/var/keri/adb/{base}") + if os.path.exists(f'/usr/local/var/keri/db/{base}'): + shutil.rmtree(f'/usr/local/var/keri/db/{base}') + if os.path.exists(f'/usr/local/var/keri/ks/{base}'): + shutil.rmtree(f'/usr/local/var/keri/ks/{base}') + if os.path.exists(f'/usr/local/var/keri/ks/{base}'): + shutil.rmtree(f'/usr/local/var/keri/ks/{base}') + if os.path.exists(f'/usr/local/var/keri/adb/{base}'): + shutil.rmtree(f'/usr/local/var/keri/adb/{base}') def test_boot_ends(helpers): @@ -235,13 +212,9 @@ def test_boot_ends(helpers): icp=serder.ked, sig=sigers[0].qb64, salty=dict( - stem="signify:aid", - pidx=0, - tier="low", - sxlt="OBXYZ", - icodes=[MtrDex.Ed25519_Seed], - ncodes=[MtrDex.Ed25519_Seed], - ), + stem='signify:aid', pidx=0, tier='low', sxlt='OBXYZ', + icodes=[MtrDex.Ed25519_Seed], ncodes=[MtrDex.Ed25519_Seed] + ) ) rep = client.simulate_post("/boot", body=json.dumps(body).encode("utf-8")) @@ -250,12 +223,13 @@ def test_boot_ends(helpers): rep = client.simulate_post("/boot", body=json.dumps(body).encode("utf-8")) assert rep.status_code == 400 assert rep.json == { - "title": "agent already exists", - "description": "agent for controller EK35JRNdfVkO4JwhXaSTdV4qzB_ibk_tGJmSVcY4pZqx already exists", + 'title': 'agent already exists', + 'description': 'agent for controller EK35JRNdfVkO4JwhXaSTdV4qzB_ibk_tGJmSVcY4pZqx already exists' } -def test_witnesser(): - salt = b"0123456789abcdef" + +def test_witnesser(helpers): + salt = b'0123456789abcdef' salter = core.Salter(raw=salt) with habbing.openHby(name="keria", salt=salter.qb64, temp=True) as hby: @@ -272,189 +246,19 @@ def test_witnesser(): doist.recur(deeds) -def test_submitter(seeder, helpers): - with helpers.openKeria() as (agency, agent, app, client), habbing.openHby( - name="wes", salt=core.Salter(raw=b"wess-the-witness").qb64, temp=True - ) as wesHby, habbing.openHby( - name="wan", salt=core.Salter(raw=b"wann-the-witness").qb64, temp=True - ) as wanHby: - - wesHab = wesHby.makeHab(name="wes", transferable=False) - assert not wesHab.kever.prefixer.transferable - - wanPort = 5642 - wanDoers = indirecting.setupWitness( - alias="wan", hby=wanHby, tcpPort=5632, httpPort=wanPort - ) - wanHab = wanHby.habByName(name="wan") - assert not wanHab.kever.prefixer.transferable - witHabs = [wesHab, wanHab] - witPrefixes = [] - for witHab in witHabs: - witPrefixes.append(witHab.pre) - - seeder.seedWitEnds(agent.hby.db, witHabs=witHabs) - - # Register the identifier endpoint so we can create an AID for the test - end = aiding.IdentifierCollectionEnd() - app.add_route("/identifiers", end) - - opColEnd = longrunning.OperationCollectionEnd() - app.add_route("/operations", opColEnd) - opResEnd = longrunning.OperationResourceEnd() - app.add_route("/operations/{name}", opResEnd) - - salt = b"0123456789abcdef" - alias = "pal" - createAidOp = helpers.createAid(client, name=alias, salt=salt, wits=witPrefixes, toad="1") - hab = agent.hby.habByName(alias) - serder = hab.iserder - - # no wigs yet - dgkey = dbing.dgKey(serder.preb, hab.kever.serder.saidb) - wigs = hab.db.getWigs(dgkey) - assert len(wigs) == 0 - - # no id key state in wit hab yet - assert hab.pre not in wesHab.kvy.kevers - - # Intentionally manually process a single receipt from only one witness in order to reach the toad (threshold of acceptable duplicity) - # while at the same time setting up the opportunity to submit the KEL to the other witness, later - hab = agent.hby.habByName(alias) - sn = 0 - msg = hab.makeOwnEvent(sn=sn) - rctMsgs = helpers.witnessMsg(hab=hab, msg=msg, sn=sn, witHabs=[wesHab]) - wigs = hab.db.getWigs(dgkey) - assert len(wigs) == 1 # only witnessed by one witness - assert len(wesHab.kvy.db.getWigs(dgkey)) == 1 # only witnessed by one witness - assert len(wanHab.kvy.db.getWigs(dgkey)) == 0 # only witnessed by the other witness - assert len(wesHab.kvy.cues) == 0 # witness cues are empty - assert hab.pre in wesHab.kvy.kevers # id key state in wit hab - assert hab.pre not in wanHab.kvy.kevers # id key state not in wit hab yet - - witAidOp = client.simulate_get(path=f'/operations/{createAidOp["name"]}') # witnessing of created aid completed - assert witAidOp.json["done"] is True # succeed because toad is 1 - assert witAidOp.json["response"]["i"] == hab.pre - - # Now we will setup to 'submit' (resubmit) the KEL to both witnesses - limit = 5.0 - tock = 0.03125 - wdoist = doing.Doist(limit=limit, tock=tock, doers=wanDoers) - wdoist.enter() - tymer = tyming.Tymer(tymth=wdoist.tymen(), duration=wdoist.limit) - aidEnd = aiding.IdentifierResourceEnd() - app.add_route("/identifiers/{name}/submit", aidEnd) - resSubmit = client.simulate_post( - path=f"/identifiers/{alias}/submit", - body=json.dumps(dict(submit=alias)).encode("utf-8"), - ) - submitter = agent.submitter # get the submitter that was triggered by the submit request - sdoist = doing.Doist(limit=1.0, tock=0.03125, real=True) - sdeeds = sdoist.enter(doers=[submitter]) - submitter.recur(tyme=1.0, deeds=sdeeds) # run the submitter to get witness receipts (with WitnessReceiptor) for sn=0 of the KEL - assert len(submitter.doers) == 1 - rectDoer = submitter.doers[0] - assert isinstance(rectDoer, WitnessReceiptor) is True - resSubmit = client.simulate_get(path=f'/operations/{resSubmit.json["name"]}') - assert resSubmit.json["done"] is False - - stamp = nowIso8601() # need same time stamp or not duplicate - agent.witq.query(src=hab.pre, pre=wanHab.pre, stamp=stamp, wits=wanHab.kever.wits) - agent.witq.query(src=hab.pre, pre=wanHab.pre, stamp=stamp, wits=wanHab.kever.wits) - agent.witq.query(src=hab.pre, pre=wanHab.pre, stamp=stamp, wits=wanHab.kever.wits) - - # while not (resSubmit.json["done"] or tymer.expired): - submitter.recur(tyme=1.0, deeds=sdeeds) # run the submitter to check for witness receipts (with WitnessReceiptor) for sn=0 of the KEL - resSubmit = client.simulate_get(path=f'/operations/{resSubmit.json["name"]}') - - limit = 5.0 - tock = 0.03125 - doist = doing.Doist(limit=limit, tock=tock) - doers = wanDoers + [rectDoer] - doist.do(doers=doers) - doist.recur() - - assert hab.pre in wanHab.kvy.kevers # id key state in wit hab - assert wanHab.kvy.kevers[hab.pre].sn == 0 - wanHab.processCues(wanHab.kvy.cues) # process cue returns rct msg - assert len(wanHab.kvy.db.getWigs(dgkey)) == 2 # now witnessed by the other witness - assert len(wanHab.kvy.cues) == 0 # witness cues are empty - assert hab.pre in wanHab.kvy.kevers # id key state in wit hab yet - assert wanHby.db.fullyWitnessed(hab.kever.serder) # fully witnessed - - rctMsg = wanHab.replyToOobi(aid=hab.pre, role='controller') - hab.psr.parse(ims=bytearray(rctMsg), kvy=hab.kvy, local=True) - witMsg = wanHab.replyToOobi(aid=wanHab.pre, role='controller') - hab.psr.parse(ims=bytearray(witMsg), kvy=hab.kvy, local=True) - assert wanHab.pre in hab.kvy.kevers - wigs = hab.db.getWigs(dgkey) - assert len(wigs) == 2 - - rectDoer.cues.append(dict(pre=hab.pre, sn=0)) # append expected cue - submitter.recur(tyme=1.0, deeds=sdeeds) - resSubmit = client.simulate_get(path=f'/operations/{resSubmit.json["name"]}') - assert resSubmit.status_code == 200 - assert resSubmit.text == json.dumps( - dict( - name="submit.EKOrePIIU8ynKwOOLxs56ZxxQswUFNV8-cyYFt3nBJHR", - metadata={"alias": "pal", "sn": 0}, - done=True, - error=None, - response={ - "vn": [1, 0], - "i": "EKOrePIIU8ynKwOOLxs56ZxxQswUFNV8-cyYFt3nBJHR", - "s": "0", - "p": "", - "d": "EKOrePIIU8ynKwOOLxs56ZxxQswUFNV8-cyYFt3nBJHR", - "f": "0", - "dt": resSubmit.json["response"]["dt"], - "et": "icp", - "kt": "1", - "k": ["DDNGgXzEO4LD8G1z1uD7eIDF2pDj6Y7hVx-nqhYZmU_8"], - "nt": "1", - "n": ["EHj7rmVHVkQKqnfeer068PiYvYm-WFSTVZZpFGsClfT-"], - "bt": "1", - "b": ["BN8t3n1lxcV0SWGJIIF46fpSUqA7Mqre5KJNN3nbx3mr","BOigXdxpp1r43JhO--czUTwrCXzoWrIwW8i41KWDlr8s"], - "c": [], - "ee": { - "s": "0", - "d": "EKOrePIIU8ynKwOOLxs56ZxxQswUFNV8-cyYFt3nBJHR", - "br": [], - "ba": [], - }, - "di": "", - }, - ) - ) - - # submitter = agenting.Submitter(hby=agent.hby, submits=decking.Deck(), witRec=WitnessReceiptor(hby=agent.hby)) - - # # no wits, should not be added for processing - # helpers.createAid(client, "test2", salt) - # submitter.submits.append(dict(alias="test2")) - # submitter.recur(1.0, deeds=deeds) - # assert len(submitter.doers) == 1 - - def test_keystate_ends(helpers): caid = "ELI7pg979AdhmvrjDeam2eAO2SR5niCgnjAJXJHtJose" - salt = b"0123456789abcdef" + salt = b'0123456789abcdef' salter = core.Salter(raw=salt) - cf = configing.Configer( - name="keria", headDirPath=SCRIPTS_DIR, temp=True, reopen=True, clear=False - ) + cf = configing.Configer(name="keria", headDirPath=SCRIPTS_DIR, temp=True, reopen=True, clear=False) with habbing.openHby(name="keria", salt=salter.qb64, temp=True, cf=cf) as hby: hab = hby.makeHab(name="test") agency = agenting.Agency(name="agency", bran=None, temp=True) agentHab = hby.makeHab(caid, ns="agent", transferable=True, data=[caid]) - rgy = credentialing.Regery( - hby=hby, name=agentHab.name, base=hby.base, temp=True - ) - agent = agenting.Agent( - hby=hby, rgy=rgy, agentHab=agentHab, agency=agency, caid=caid - ) + rgy = credentialing.Regery(hby=hby, name=agentHab.name, base=hby.base, temp=True) + agent = agenting.Agent(hby=hby, rgy=rgy, agentHab=agentHab, agency=agency, caid=caid) end = agenting.KeyStateCollectionEnd() @@ -469,23 +273,20 @@ def test_keystate_ends(helpers): assert len(states) == 1 state = states[0] - assert state["i"] == hab.pre - assert state["d"] == "EIaGMMWJFPmtXznY1IIiKDIrg-vIyge6mBl2QV8dDjI3" - assert state["et"] == "icp" - assert state["k"] == ["DGmIfLmgErg4zFHfPwaDckLNxsLqc5iS_P0QbLjbWR0I"] - assert state["n"] == ["EJhRr10e5p7LVB6JwLDIcgqsISktnfe5m60O_I2zZO6N"] - assert state["ee"] == { - "ba": [], - "br": [], - "d": "EIaGMMWJFPmtXznY1IIiKDIrg-vIyge6mBl2QV8dDjI3", - "s": "0", - } + assert state['i'] == hab.pre + assert state['d'] == "EIaGMMWJFPmtXznY1IIiKDIrg-vIyge6mBl2QV8dDjI3" + assert state['et'] == 'icp' + assert state['k'] == ['DGmIfLmgErg4zFHfPwaDckLNxsLqc5iS_P0QbLjbWR0I'] + assert state['n'] == ['EJhRr10e5p7LVB6JwLDIcgqsISktnfe5m60O_I2zZO6N'] + assert state['ee'] == {'ba': [], + 'br': [], + 'd': 'EIaGMMWJFPmtXznY1IIiKDIrg-vIyge6mBl2QV8dDjI3', + 's': '0'} def test_oobi_ends(seeder, helpers): - with helpers.openKeria() as (agency, agent, app, client), habbing.openHby( - name="wes", salt=core.Salter(raw=b"wess-the-witness").qb64 - ) as wesHby: + with helpers.openKeria() as (agency, agent, app, client), \ + habbing.openHby(name="wes", salt=core.Salter(raw=b'wess-the-witness').qb64) as wesHby: wesHab = wesHby.makeHab(name="wes", transferable=False) result = client.simulate_get(path="/oobi/pal?role=witness") @@ -493,14 +294,12 @@ def test_oobi_ends(seeder, helpers): # Add witness endpoints url = "http://127.0.0.1:9999" - agent.hby.db.locs.put( - keys=(wesHab.pre, kering.Schemes.http), val=basing.LocationRecord(url=url) - ) + agent.hby.db.locs.put(keys=(wesHab.pre, kering.Schemes.http), val=basing.LocationRecord(url=url)) # Register the identifier endpoint so we can create an AID for the test end = aiding.IdentifierCollectionEnd() app.add_route("/identifiers", end) - salt = b"0123456789abcdef" + salt = b'0123456789abcdef' helpers.createAid(client, "pal", salt, wits=[wesHab.pre], toad="1") palPre = "EEkruFP-J0InOD9cYbNLlBxQtkLAbmJPNecSnBzJixP0" @@ -525,34 +324,23 @@ def test_oobi_ends(seeder, helpers): # Add controller endpoints url = "http://127.0.0.1:9999" - agent.hby.db.locs.put( - keys=(palPre, kering.Schemes.http), val=basing.LocationRecord(url=url) - ) + agent.hby.db.locs.put(keys=(palPre, kering.Schemes.http), val=basing.LocationRecord(url=url)) result = client.simulate_get(path="/oobi/pal?role=controller") assert result.status == falcon.HTTP_200 # Missing OOBI controller endpoints assert result.json == { - "oobis": [ - "http://127.0.0.1:9999/oobi/EEkruFP-J0InOD9cYbNLlBxQtkLAbmJPNecSnBzJixP0/controller" - ], - "role": "controller", - } + 'oobis': ['http://127.0.0.1:9999/oobi/EEkruFP-J0InOD9cYbNLlBxQtkLAbmJPNecSnBzJixP0/controller'], + 'role': 'controller'} # Seed with witness endpoints - seeder.seedWitEnds( - agent.hby.db, - witHabs=[wesHab], - protocols=[kering.Schemes.http, kering.Schemes.tcp], - ) + seeder.seedWitEnds(agent.hby.db, witHabs=[wesHab], protocols=[kering.Schemes.http, kering.Schemes.tcp]) result = client.simulate_get(path="/oobi/pal?role=witness") assert result.status == falcon.HTTP_200 assert result.json == { - "oobis": [ - "http://127.0.0.1:5644/oobi/EEkruFP-J0InOD9cYbNLlBxQtkLAbmJPNecSnBzJixP0/witness/BN8t3n1lxcV0SWGJIIF" - "46fpSUqA7Mqre5KJNN3nbx3mr" - ], - "role": "witness", - } + 'oobis': [ + 'http://127.0.0.1:5644/oobi/EEkruFP-J0InOD9cYbNLlBxQtkLAbmJPNecSnBzJixP0/witness/BN8t3n1lxcV0SWGJIIF' + '46fpSUqA7Mqre5KJNN3nbx3mr'], + 'role': 'witness'} # Post without a URL or RPY data = dict() @@ -566,19 +354,14 @@ def test_oobi_ends(seeder, helpers): result = client.simulate_post(path="/oobi", body=b) assert result.status == falcon.HTTP_501 - data = dict( - url="http://127.0.0.1:5644/oobi/E6Dqo6tHmYTuQ3Lope4mZF_4hBoGJl93cBHRekr_iD_A/witness/" - ) + data = dict(url="http://127.0.0.1:5644/oobi/E6Dqo6tHmYTuQ3Lope4mZF_4hBoGJl93cBHRekr_iD_A/witness/") b = json.dumps(data).encode("utf-8") result = client.simulate_post(path="/oobi", body=b) assert result.status == falcon.HTTP_202 assert oobiery.hby.db.oobis.cntAll() == 1 (url,), item = next(oobiery.hby.db.oobis.getItemIter()) assert item is not None - assert ( - url - == "http://127.0.0.1:5644/oobi/E6Dqo6tHmYTuQ3Lope4mZF_4hBoGJl93cBHRekr_iD_A/witness/" - ) + assert url == 'http://127.0.0.1:5644/oobi/E6Dqo6tHmYTuQ3Lope4mZF_4hBoGJl93cBHRekr_iD_A/witness/' oobiery.hby.db.oobis.rem(keys=(url,)) # Post an RPY @@ -588,78 +371,54 @@ def test_oobi_ends(seeder, helpers): assert result.status == falcon.HTTP_501 # POST without an oobialias - data = dict( - url="http://127.0.0.1:5644/oobi/E6Dqo6tHmYTuQ3Lope4mZF_4hBoGJl93cBHRekr_iD_A/witness/" - ) + data = dict(url="http://127.0.0.1:5644/oobi/E6Dqo6tHmYTuQ3Lope4mZF_4hBoGJl93cBHRekr_iD_A/witness/") b = json.dumps(data).encode("utf-8") result = client.simulate_post(path="/oobi", body=b) assert result.status == falcon.HTTP_202 assert oobiery.hby.db.oobis.cntAll() == 1 (url,), item = next(oobiery.hby.db.oobis.getItemIter()) assert item is not None - assert ( - url - == "http://127.0.0.1:5644/oobi/E6Dqo6tHmYTuQ3Lope4mZF_4hBoGJl93cBHRekr_iD_A/witness/" - ) + assert url == 'http://127.0.0.1:5644/oobi/E6Dqo6tHmYTuQ3Lope4mZF_4hBoGJl93cBHRekr_iD_A/witness/' assert item.oobialias is None oobiery.hby.db.oobis.rem(keys=(url,)) - data = dict( - oobialias="sal", - url="http://127.0.0.1:5644/oobi/E6Dqo6tHmYTuQ3Lope4mZF_4hBoGJl93cBHRekr_iD_A" - "/witness/", - ) + data = dict(oobialias="sal", url="http://127.0.0.1:5644/oobi/E6Dqo6tHmYTuQ3Lope4mZF_4hBoGJl93cBHRekr_iD_A" + "/witness/") b = json.dumps(data).encode("utf-8") result = client.simulate_post(path="/oobi", body=b) assert result.status == falcon.HTTP_202 assert oobiery.hby.db.oobis.cntAll() == 1 (url,), item = next(oobiery.hby.db.oobis.getItemIter()) assert item is not None - assert ( - url - == "http://127.0.0.1:5644/oobi/E6Dqo6tHmYTuQ3Lope4mZF_4hBoGJl93cBHRekr_iD_A/witness/" - ) - assert item.oobialias == "sal" + assert url == 'http://127.0.0.1:5644/oobi/E6Dqo6tHmYTuQ3Lope4mZF_4hBoGJl93cBHRekr_iD_A/witness/' + assert item.oobialias == 'sal' op = helpers.createAid(client, "aggie", salt) aid = op["response"] - aggiePre = aid["i"] + aggiePre = aid['i'] assert aggiePre == "EHgwVwQT15OJvilVvW57HE4w0-GPs_Stj2OFoAHZSysY" keys = (aggiePre, kering.Roles.agent, agent.agentHab.pre) ender = basing.EndpointRecord(allowed=True) agent.hby.db.ends.pin(keys=keys, val=ender) # overwrite url = "http://127.0.0.1:3902" - agent.hby.db.locs.put( - keys=(agent.agentHab.pre, kering.Schemes.http), - val=basing.LocationRecord(url=url), - ) + agent.hby.db.locs.put(keys=(agent.agentHab.pre, kering.Schemes.http), val=basing.LocationRecord(url=url)) result = client.simulate_get(path="/oobi/aggie?role=agent") assert result.status == falcon.HTTP_200 - assert result.json == { - "oobis": [ - "http://127.0.0.1:3902/oobi/EHgwVwQT15OJvilVvW57HE4w0-GPs_Stj2OFoAHZSysY/agent" - "/EI7AkI40M11MS7lkTCb10JC9-nDt-tXwQh44OHAFlv_9" - ], - "role": "agent", - } + assert result.json == {'oobis': ['http://127.0.0.1:3902/oobi/EHgwVwQT15OJvilVvW57HE4w0-GPs_Stj2OFoAHZSysY/agent' + '/EI7AkI40M11MS7lkTCb10JC9-nDt-tXwQh44OHAFlv_9'], + 'role': 'agent'} + def test_querier(helpers): with helpers.openKeria() as (agency, agent, app, client): - qry = agenting.Querier( - hby=agent.hby, - agentHab=agent.agentHab, - queries=decking.Deck(), - kvy=agent.kvy, - ) + qry = agenting.Querier(hby=agent.hby, agentHab=agent.agentHab, queries=decking.Deck(), kvy=agent.kvy) doist = doing.Doist(limit=1.0, tock=0.03125, real=True) deeds = doist.enter(doers=[qry]) - qry.queries.append( - dict(pre="EI7AkI40M11MS7lkTCb10JC9-nDt-tXwQh44OHAFlv_9", sn="1") - ) + qry.queries.append(dict(pre="EI7AkI40M11MS7lkTCb10JC9-nDt-tXwQh44OHAFlv_9", sn="1")) qry.recur(1.0, deeds=deeds) assert len(qry.doers) == 1 @@ -671,9 +430,7 @@ def test_querier(helpers): qry.doers.remove(seqNoDoer) # Anchor not implemented yet - qry.queries.append( - dict(pre="EI7AkI40M11MS7lkTCb10JC9-nDt-tXwQh44OHAFlv_9", anchor={}) - ) + qry.queries.append(dict(pre="EI7AkI40M11MS7lkTCb10JC9-nDt-tXwQh44OHAFlv_9", anchor={})) qry.recur(1.0, deeds=deeds) assert len(qry.doers) == 1 anchorDoer = qry.doers[0] @@ -692,7 +449,7 @@ def test_querier(helpers): class MockServerTls: - def __init__(self, certify, keypath, certpath, cafilepath, port): + def __init__(self, certify, keypath, certpath, cafilepath, port): pass @@ -707,12 +464,11 @@ def test_createHttpServer(monkeypatch): server = agenting.createHttpServer(port, app) assert isinstance(server, http.Server) - monkeypatch.setattr(hio.core.tcp, "ServerTls", MockServerTls) - monkeypatch.setattr(hio.core.http, "Server", MockHttpServer) + monkeypatch.setattr(hio.core.tcp, 'ServerTls', MockServerTls) + monkeypatch.setattr(hio.core.http, 'Server', MockHttpServer) - server = agenting.createHttpServer( - port, app, keypath="keypath", certpath="certpath", cafilepath="cafilepath" - ) + server = agenting.createHttpServer(port, app, keypath='keypath', certpath='certpath', + cafilepath='cafilepath') assert isinstance(server, MockHttpServer) assert isinstance(server.servant, MockServerTls) @@ -723,21 +479,19 @@ def test_seeker_doer(helpers): cues = decking.Deck() seeker = agenting.SeekerDoer(agent.seeker, cues) - creder = serdering.SerderACDC( - sad={ - "v": "ACDC10JSON000197_", - "d": "EG7ZlUq0Z6a1EUPTM_Qg1LGEg1BWiypHLAekxo8crGzK", - "i": "EPbOCiPM7IItIMzMwslKWfPM4tqNIKUCyVVuYJNQHwMB", - "ri": "EE5upBEf9JlH0ZCkZwLcNOOQYkiowcF7QBa-SDZg3GLo", - "s": "EBfdlu8R27Fbx-ehrqwImnK-8Cm79sqbAQ4MmvEAYqao", - "a": { - "d": "EH8sB2FZuSYBi6dj8edmPMxS-ZoikR2ova3LAVJvelMe", - "i": "ECfRBXooQPoNNQC4i0bkwNfKm-VwV3QsUce14uFfejyj", - "dt": "2023-11-07T23:38:05.508152+00:00", - "LEI": "5493001KJTIIGC8Y1R17", - }, + creder = serdering.SerderACDC(sad={ + "v": "ACDC10JSON000197_", + "d": "EG7ZlUq0Z6a1EUPTM_Qg1LGEg1BWiypHLAekxo8crGzK", + "i": "EPbOCiPM7IItIMzMwslKWfPM4tqNIKUCyVVuYJNQHwMB", + "ri": "EE5upBEf9JlH0ZCkZwLcNOOQYkiowcF7QBa-SDZg3GLo", + "s": "EBfdlu8R27Fbx-ehrqwImnK-8Cm79sqbAQ4MmvEAYqao", + "a": { + "d": "EH8sB2FZuSYBi6dj8edmPMxS-ZoikR2ova3LAVJvelMe", + "i": "ECfRBXooQPoNNQC4i0bkwNfKm-VwV3QsUce14uFfejyj", + "dt": "2023-11-07T23:38:05.508152+00:00", + "LEI": "5493001KJTIIGC8Y1R17" } - ) + }) assert creder.said == "EG7ZlUq0Z6a1EUPTM_Qg1LGEg1BWiypHLAekxo8crGzK" @@ -746,3 +500,158 @@ def test_seeker_doer(helpers): result = seeker.recur() assert result is False assert len(cues) == 1 + +def test_submitter(seeder, helpers): + with helpers.openKeria() as (agency, agent, app, client), habbing.openHby( + name="wes", salt=core.Salter(raw=b"wess-the-witness").qb64, temp=True + ) as wesHby, habbing.openHby( + name="wan", salt=core.Salter(raw=b"wann-the-witness").qb64, temp=True + ) as wanHby: + + wesHab = wesHby.makeHab(name="wes", transferable=False) + assert not wesHab.kever.prefixer.transferable + + wanPort = 5642 + wanDoers = indirecting.setupWitness( + alias="wan", hby=wanHby, tcpPort=5632, httpPort=wanPort + ) + wanHab = wanHby.habByName(name="wan") + assert not wanHab.kever.prefixer.transferable + witHabs = [wesHab, wanHab] + witPrefixes = [] + for witHab in witHabs: + witPrefixes.append(witHab.pre) + + seeder.seedWitEnds(agent.hby.db, witHabs=witHabs) + + # Register the identifier endpoint so we can create an AID for the test + end = aiding.IdentifierCollectionEnd() + app.add_route("/identifiers", end) + + opColEnd = longrunning.OperationCollectionEnd() + app.add_route("/operations", opColEnd) + opResEnd = longrunning.OperationResourceEnd() + app.add_route("/operations/{name}", opResEnd) + + salt = b"0123456789abcdef" + alias = "pal" + createAidOp = helpers.createAid(client, name=alias, salt=salt, wits=witPrefixes, toad="1") + hab = agent.hby.habByName(alias) + serder = hab.iserder + + # no wigs yet + dgkey = dbing.dgKey(serder.preb, hab.kever.serder.saidb) + wigs = hab.db.getWigs(dgkey) + assert len(wigs) == 0 + + # no id key state in wit hab yet + assert hab.pre not in wesHab.kvy.kevers + + # Intentionally manually process a single receipt from only one witness in order to reach the toad (threshold of acceptable duplicity) + # while at the same time setting up the opportunity to submit the KEL to the other witness, later + hab = agent.hby.habByName(alias) + sn = 0 + msg = hab.makeOwnEvent(sn=sn) + rctMsgs = helpers.witnessMsg(hab=hab, msg=msg, sn=sn, witHabs=[wesHab]) + wigs = hab.db.getWigs(dgkey) + assert len(wigs) == 1 # only witnessed by one witness + assert len(wesHab.kvy.db.getWigs(dgkey)) == 1 # only witnessed by one witness + assert len(wanHab.kvy.db.getWigs(dgkey)) == 0 # only witnessed by the other witness + assert len(wesHab.kvy.cues) == 0 # witness cues are empty + assert hab.pre in wesHab.kvy.kevers # id key state in wit hab + assert hab.pre not in wanHab.kvy.kevers # id key state not in wit hab yet + + witAidOp = client.simulate_get(path=f'/operations/{createAidOp["name"]}') # witnessing of created aid completed + assert witAidOp.json["done"] is True # succeed because toad is 1 + assert witAidOp.json["response"]["i"] == hab.pre + + # Now we will setup to 'submit' (resubmit) the KEL to both witnesses + limit = 5.0 + tock = 0.03125 + wdoist = doing.Doist(limit=limit, tock=tock, doers=wanDoers) + wdoist.enter() + tymer = tyming.Tymer(tymth=wdoist.tymen(), duration=wdoist.limit) + aidEnd = aiding.IdentifierResourceEnd() + app.add_route("/identifiers/{name}/submit", aidEnd) + resSubmit = client.simulate_post( + path=f"/identifiers/{alias}/submit", + body=json.dumps(dict(submit=alias)).encode("utf-8"), + ) + submitter = agent.submitter # get the submitter that was triggered by the submit request + sdoist = doing.Doist(limit=1.0, tock=0.03125, real=True) + sdeeds = sdoist.enter(doers=[submitter]) + submitter.recur(tyme=1.0, deeds=sdeeds) # run the submitter to get witness receipts (with WitnessReceiptor) for sn=0 of the KEL + assert len(submitter.doers) == 1 + rectDoer = submitter.doers[0] + assert isinstance(rectDoer, WitnessReceiptor) is True + resSubmit = client.simulate_get(path=f'/operations/{resSubmit.json["name"]}') + assert resSubmit.json["done"] is False + + stamp = nowIso8601() # need same time stamp or not duplicate + agent.witq.query(src=hab.pre, pre=wanHab.pre, stamp=stamp, wits=wanHab.kever.wits) + agent.witq.query(src=hab.pre, pre=wanHab.pre, stamp=stamp, wits=wanHab.kever.wits) + agent.witq.query(src=hab.pre, pre=wanHab.pre, stamp=stamp, wits=wanHab.kever.wits) + + # while not (resSubmit.json["done"] or tymer.expired): + submitter.recur(tyme=1.0, deeds=sdeeds) # run the submitter to check for witness receipts (with WitnessReceiptor) for sn=0 of the KEL + resSubmit = client.simulate_get(path=f'/operations/{resSubmit.json["name"]}') + + limit = 5.0 + tock = 0.03125 + doist = doing.Doist(limit=limit, tock=tock) + doers = wanDoers + [rectDoer] + doist.do(doers=doers) + doist.recur() + + assert hab.pre in wanHab.kvy.kevers # id key state in wit hab + assert wanHab.kvy.kevers[hab.pre].sn == 0 + wanHab.processCues(wanHab.kvy.cues) # process cue returns rct msg + assert len(wanHab.kvy.db.getWigs(dgkey)) == 2 # now witnessed by the other witness + assert len(wanHab.kvy.cues) == 0 # witness cues are empty + assert hab.pre in wanHab.kvy.kevers # id key state in wit hab yet + assert wanHby.db.fullyWitnessed(hab.kever.serder) # fully witnessed + + rctMsg = wanHab.replyToOobi(aid=hab.pre, role='controller') + hab.psr.parse(ims=bytearray(rctMsg), kvy=hab.kvy, local=True) + witMsg = wanHab.replyToOobi(aid=wanHab.pre, role='controller') + hab.psr.parse(ims=bytearray(witMsg), kvy=hab.kvy, local=True) + assert wanHab.pre in hab.kvy.kevers + wigs = hab.db.getWigs(dgkey) + assert len(wigs) == 2 + + rectDoer.cues.append(dict(pre=hab.pre, sn=0)) # append expected cue + submitter.recur(tyme=1.0, deeds=sdeeds) + resSubmit = client.simulate_get(path=f'/operations/{resSubmit.json["name"]}') + assert resSubmit.status_code == 200 + assert resSubmit.text == json.dumps( + dict( + name="submit.EKOrePIIU8ynKwOOLxs56ZxxQswUFNV8-cyYFt3nBJHR", + metadata={"alias": "pal", "sn": 0}, + done=True, + error=None, + response={ + "vn": [1, 0], + "i": "EKOrePIIU8ynKwOOLxs56ZxxQswUFNV8-cyYFt3nBJHR", + "s": "0", + "p": "", + "d": "EKOrePIIU8ynKwOOLxs56ZxxQswUFNV8-cyYFt3nBJHR", + "f": "0", + "dt": resSubmit.json["response"]["dt"], + "et": "icp", + "kt": "1", + "k": ["DDNGgXzEO4LD8G1z1uD7eIDF2pDj6Y7hVx-nqhYZmU_8"], + "nt": "1", + "n": ["EHj7rmVHVkQKqnfeer068PiYvYm-WFSTVZZpFGsClfT-"], + "bt": "1", + "b": ["BN8t3n1lxcV0SWGJIIF46fpSUqA7Mqre5KJNN3nbx3mr","BOigXdxpp1r43JhO--czUTwrCXzoWrIwW8i41KWDlr8s"], + "c": [], + "ee": { + "s": "0", + "d": "EKOrePIIU8ynKwOOLxs56ZxxQswUFNV8-cyYFt3nBJHR", + "br": [], + "ba": [], + }, + "di": "", + }, + ) + ) \ No newline at end of file