Skip to content

Commit

Permalink
Superseding Delegated Rotation and misfit escrow (WebOfTrust#680)
Browse files Browse the repository at this point in the history
* renamed tests

* created test to test supersedeing logic. Just setting up for now not done.

* setting up superseding delegation tests

* more work on superseding test

* add more to supersede test work, plus some cleanup

* added detailed doc string on acceptance rules for delegated events
added cleanup of cue triggers

* more details in doc string

* fixed clarification

* added additional doc string language

* fixed typo

* updated superseding logic to include virtual delegating event when local delegator is processing delegated event acceptance into its local copy of delegatees KEL so as not to corrupt its copy.

* updated doc string

* more doc string goodness

* some refactoring. remaned Kever.delegator to .delpre to follow convention
and the uses renamed.

* added event source record Komer .esrs subdb to Baser so we can track source of event local or remote

* Passing event source to processEvent from all escrow processing routines.

Signed-off-by: pfeairheller <[email protected]>

* updated doc string for Baser for .esrs subdb

* rebasing misfit

Signed-off-by: pfeairheller <[email protected]>

* Add local persistence to escrowing methods.

Signed-off-by: pfeairheller <[email protected]>

* added code in Kever to update event source record

* changed parser logic to support local

* Fix processEscrow events to use correct key for esr

Signed-off-by: pfeairheller <[email protected]>

* updated keys for .esrs usage

* clean up fix merge fail

* added misfit event escrow database .mfes as CesrIoSetSuber instance.

* habery .__init__ creates its default .psr parser with local = True

* added method to Kevery.escrowMFEvent for escrowing misfit events into .mfes

* rebasing misfit

Signed-off-by: pfeairheller <[email protected]>

* fixed unit test and logic for misfit processing

* some clean up refactor in Kever. Added local parameter to process receipt methods in Kevery.

* some cleanup on doc strings and comments

* updated locallyWitnessed to return boolean

* Fix tests that parse events with a lax Kevery to now use `local=true` in the call to parse.

Signed-off-by: pfeairheller <[email protected]>

* removed redundant misfit checks refactored .locallWitnessed method other clean up

* removed potentially buggy redundant inject of db.prefixes into Kever.prefixes as attribute and replaced with property that uses .db.prefixes instead

* added Baser.gids as oset of Group Hab pres (hids)

* changed Baser.mfes to .misfits since CesrIoSetSuber attribute name does not need to match subkey .mfes
x

* added test for prefix in locallyOwned to not be in db.groups.
Changes db.gids to .groups

* some refactor of methos names to distinquish processing of the attached equivalent of receipt versus the actual rct messages
enabled the new local pass in from parser for rct messages.

* added code to filter out local signatures for group messages received remotely (nonlocal not protected)

* refactor Kever.locallyOwned to default to self.prefixer.qb64 if no prefix passed in

* updated code comment

* added cue for remoteMemberedSig to notify when recieving own signature on group multisig event from unprotected source

* refactor logic to set stage for delegation escrow to do the approval of delegation by delegator and any sandboxing
needed or cues to business logic for approval.

* added db Baser.delegables subkey .dees for delegable escrowed events awaiting delegator approval.
Still needs processDelegableEscrows but now Kever escrows them

* updated comments

* rebasing misfit

Signed-off-by: pfeairheller <[email protected]>

* started changing Number class

* more unit texts for Number

* added .validate method to Number to validate if number is ordinal

* added more tests. Replaced some Seqner usages

* cleanup Seqner and tests
Added .seqner property to Number and tests

* removed validateSN function. replaced with Number.validate

* Fix delegator escrow test to match new expectation that delegate have delegator's pre in kevers.

Signed-off-by: pfeairheller <[email protected]>

* Comment delegation script until kli delegation commands can be fixed.

Signed-off-by: pfeairheller <[email protected]>

---------

Signed-off-by: pfeairheller <[email protected]>
Co-authored-by: Samuel M Smith <[email protected]>
  • Loading branch information
pfeairheller and SmithSamuelM authored Feb 15, 2024
1 parent 3e43619 commit 82a202d
Show file tree
Hide file tree
Showing 44 changed files with 2,628 additions and 873 deletions.
6 changes: 3 additions & 3 deletions scripts/demo/test_scripts.sh
Original file line number Diff line number Diff line change
Expand Up @@ -47,10 +47,10 @@ printf "\n************************************\n"
isSuccess

printf "\n************************************\n"
printf "Running multisig-delegate-delegator.sh"
printf "Skipping multisig-delegate-delegator.sh"
printf "\n************************************\n"
"${script_dir}/basic/multisig-delegate-delegator.sh"
isSuccess
#"${script_dir}/basic/multisig-delegate-delegator.sh"
#isSuccess

printf "\n************************************\n"
printf "Running challenge.sh"
Expand Down
4 changes: 2 additions & 2 deletions src/keri/app/agenting.py
Original file line number Diff line number Diff line change
Expand Up @@ -718,7 +718,7 @@ def msgDo(self, tymth=None, tock=0.0, **opts):
Usage:
add result of doify on this method to doers list
"""
yield from self.parser.parsator() # process messages continuously
yield from self.parser.parsator(local=True) # process messages continuously

@property
def idle(self):
Expand Down Expand Up @@ -812,7 +812,7 @@ def msgDo(self, tymth=None, tock=0.0, **opts):
Usage:
add result of doify on this method to doers list
"""
yield from self.parser.parsator() # process messages continuously
yield from self.parser.parsator(local=True) # process messages continuously

@property
def idle(self):
Expand Down
2 changes: 1 addition & 1 deletion src/keri/app/cli/commands/delegate/confirm.py
Original file line number Diff line number Diff line change
Expand Up @@ -111,7 +111,7 @@ def confirmDo(self, tymth, tock=0.0):
elif ilk in (coring.Ilks.drt,):
typ = "rotation"
dkever = self.hby.kevers[eserder.pre]
delpre = dkever.delegator
delpre = dkever.delpre

else:
continue
Expand Down
4 changes: 2 additions & 2 deletions src/keri/app/cli/commands/delegate/request.py
Original file line number Diff line number Diff line change
Expand Up @@ -86,7 +86,7 @@ def requestDo(self, tymth, tock=0.0):

(seqner, saider) = esc[0]
evt = hab.makeOwnEvent(sn=seqner.sn)
delpre = hab.kever.delegator # get the delegator identifier
delpre = hab.kever.delpre # get the delegator identifier

if isinstance(hab, GroupHab):
phab = hab.mhab
Expand All @@ -99,7 +99,7 @@ def requestDo(self, tymth, tock=0.0):
srdr = serdering.SerderKERI(raw=evt) # coring.Serder(raw=evt)
del evt[:srdr.size]
self.postman.send(src=phab.pre, dest=delpre, topic="delegate", serder=srdr, attachment=evt)
self.postman.send(src=phab.pre, dest=hab.kever.delegator, topic="delegate", serder=exn, attachment=atc)
self.postman.send(src=phab.pre, dest=hab.kever.delpre, topic="delegate", serder=exn, attachment=atc)

while True:
while self.postman.cues:
Expand Down
4 changes: 2 additions & 2 deletions src/keri/app/cli/commands/incept.py
Original file line number Diff line number Diff line change
Expand Up @@ -168,7 +168,7 @@ def inceptDo(self, tymth, tock=0.0):
receiptor = agenting.Receiptor(hby=self.hby)
self.extend([witDoer, receiptor])

if hab.kever.delegator:
if hab.kever.delpre:
self.swain.delegation(pre=hab.pre, sn=0, proxy=self.hby.habByName(self.proxy))
print("Waiting for delegation approval...")
while not self.swain.complete(hab.kever.prefixer, coring.Seqner(sn=hab.kever.sn)):
Expand All @@ -183,7 +183,7 @@ def inceptDo(self, tymth, tock=0.0):
while not witDoer.cues:
_ = yield self.tock

if hab.kever.delegator:
if hab.kever.delpre:
yield from self.postman.sendEvent(hab=hab, fn=hab.kever.sn)

print(f'Prefix {hab.pre}')
Expand Down
2 changes: 1 addition & 1 deletion src/keri/app/cli/commands/multisig/continue.py
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ def recover(self, tymth, tock=0.0, **opts):
(seqner, saider) = esc[0]
src = hab.mhab.pre if isinstance(hab, GroupHab) else hab.pre
anchor = dict(i=hab.pre, s=seqner.snh, d=saider.qb64)
self.witq.query(src=src, pre=hab.kever.delegator, anchor=anchor)
self.witq.query(src=src, pre=hab.kever.delpre, anchor=anchor)

print(f"Checking mailboxes for any events to process")
while self.hby.db.cgms.get(keys=(hab.pre, seqner.qb64)) is None:
Expand Down
2 changes: 1 addition & 1 deletion src/keri/app/cli/commands/multisig/incept.py
Original file line number Diff line number Diff line change
Expand Up @@ -174,7 +174,7 @@ def inceptDo(self, tymth, tock=0.0):

yield self.tock

if ghab.kever.delegator:
if ghab.kever.delpre:
yield from self.postman.sendEvent(hab=ghab, fn=ghab.kever.sn)

print()
Expand Down
2 changes: 1 addition & 1 deletion src/keri/app/cli/commands/multisig/rotate.py
Original file line number Diff line number Diff line change
Expand Up @@ -233,7 +233,7 @@ def rotateDo(self, tymth, tock=0.0, **opts):

yield self.tock

if ghab.kever.delegator:
if ghab.kever.delpre:
yield from self.postman.sendEvent(hab=ghab, fn=ghab.kever.sn)

print()
Expand Down
4 changes: 2 additions & 2 deletions src/keri/app/cli/commands/rotate.py
Original file line number Diff line number Diff line change
Expand Up @@ -182,7 +182,7 @@ def rotateDo(self, tymth, tock=0.0):
cuts=list(self.cuts), adds=list(self.adds),
data=self.data)

if hab.kever.delegator:
if hab.kever.delpre:
self.swain.delegation(pre=hab.pre, sn=hab.kever.sn)
print("Waiting for delegation approval...")
while not self.swain.complete(hab.kever.prefixer, coring.Seqner(sn=hab.kever.sn)):
Expand All @@ -206,7 +206,7 @@ def rotateDo(self, tymth, tock=0.0):

self.remove([witDoer])

if hab.kever.delegator:
if hab.kever.delpre:
yield from self.postman.sendEvent(hab=hab, fn=hab.kever.sn)

print(f'Prefix {hab.pre}')
Expand Down
4 changes: 2 additions & 2 deletions src/keri/app/cli/common/displaying.py
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ def printIdentifier(hby, pre, label="Identifier"):
print("Seq No:\t{}".format(kever.sner.num))
if kever.delegated:
print("Delegated Identifier")
sys.stdout.write(f" Delegator: {kever.delegator} ")
sys.stdout.write(f" Delegator: {kever.delpre} ")
if seal:
print(f"{terming.Colors.OKGREEN}{terming.Symbols.CHECKMARK} Anchored{terming.Colors.ENDC}")
else:
Expand Down Expand Up @@ -93,7 +93,7 @@ def printExternal(hby, pre, label="Identifier"):
print("Seq No:\t{}".format(kever.sner.num))
if kever.delegated:
print("Delegated Identifier")
sys.stdout.write(f" Delegator: {kever.delegator} ")
sys.stdout.write(f" Delegator: {kever.delpre} ")
if anchor:
print(f"{terming.Colors.OKGREEN}{terming.Symbols.CHECKMARK} Anchored{terming.Colors.ENDC}")
else:
Expand Down
6 changes: 3 additions & 3 deletions src/keri/app/delegating.py
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,7 @@ def delegation(self, pre, sn=None, proxy=None):

# load the hab of the delegated identifier to anchor
hab = self.hby.habs[pre]
delpre = hab.kever.delegator # get the delegator identifier
delpre = hab.kever.delpre # get the delegator identifier
if delpre not in hab.kevers:
raise kering.ValidationError(f"delegator {delpre} not found, unable to process delegation")

Expand All @@ -81,7 +81,7 @@ def delegation(self, pre, sn=None, proxy=None):
# Send exn message for notification purposes
exn, atc = delegateRequestExn(phab, delpre=delpre, evt=bytes(evt), aids=smids)

self.postman.send(hab=phab, dest=hab.kever.delegator, topic="delegate", serder=exn, attachment=atc)
self.postman.send(hab=phab, dest=hab.kever.delpre, topic="delegate", serder=exn, attachment=atc)

srdr = serdering.SerderKERI(raw=evt)
del evt[:srdr.size]
Expand Down Expand Up @@ -151,7 +151,7 @@ def processUnanchoredEscrow(self):
"""
for (pre, said), serder in self.hby.db.dune.getItemIter(): # group partial witness escrow
kever = self.hby.kevers[pre]
dkever = self.hby.kevers[kever.delegator]
dkever = self.hby.kevers[kever.delpre]

seal = dict(i=serder.pre, s=serder.snh, d=serder.said)
if dserder := self.hby.db.findAnchoringSealEvent(dkever.prefixer.qb64, seal=seal):
Expand Down
4 changes: 2 additions & 2 deletions src/keri/app/directing.py
Original file line number Diff line number Diff line change
Expand Up @@ -230,7 +230,7 @@ def msgDo(self, tymth=None, tock=0.0, **opts):
yield # enter context
if self.parser.ims:
logger.info("Client %s received:\n%s\n...\n", self.hab.name, self.parser.ims[:1024])
done = yield from self.parser.parsator() # process messages continuously
done = yield from self.parser.parsator(local=True) # process messages continuously
return done # should nover get here except forced close


Expand Down Expand Up @@ -585,7 +585,7 @@ def msgDo(self, tymth=None, tock=0.0, **opts):
if self.parser.ims:
logger.info("Server %s: received:\n%s\n...\n", self.hab.name,
self.parser.ims[:1024])
done = yield from self.parser.parsator() # process messages continuously
done = yield from self.parser.parsator(local=True) # process messages continuously
return done # should nover get here except forced close


Expand Down
2 changes: 1 addition & 1 deletion src/keri/app/forwarding.py
Original file line number Diff line number Diff line change
Expand Up @@ -143,7 +143,7 @@ def sendEvent(self, hab, fn=0):
del icp[:ser.size]

sender = hab.mhab.pre if isinstance(hab, GroupHab) else hab.pre
self.send(src=sender, dest=hab.kever.delegator, topic="delegate", serder=ser, attachment=icp)
self.send(src=sender, dest=hab.kever.delpre, topic="delegate", serder=ser, attachment=icp)
while True:
if self.cues:
cue = self.cues.popleft()
Expand Down
6 changes: 3 additions & 3 deletions src/keri/app/grouping.py
Original file line number Diff line number Diff line change
Expand Up @@ -138,9 +138,9 @@ def processPartialSignedEscrow(self):
else:
anchor = dict(i=pre, s=seqner.snh, d=saider.qb64)
if self.proxy:
self.witq.query(hab=self.proxy, pre=kever.delegator, anchor=anchor)
self.witq.query(hab=self.proxy, pre=kever.delpre, anchor=anchor)
else:
self.witq.query(src=ghab.mhab.pre, pre=kever.delegator, anchor=anchor)
self.witq.query(src=ghab.mhab.pre, pre=kever.delpre, anchor=anchor)

print("Waiting for delegation approval...")
self.hby.db.gdee.add(keys=(pre,), val=(seqner, saider))
Expand Down Expand Up @@ -175,7 +175,7 @@ def processDelegateEscrow(self):
self.hby.db.cgms.put(keys=(pre, seqner.qb64), val=saider)

else: # Not witnesser, we need to look for the anchor and then wait for receipts
if serder := self.hby.db.findAnchoringSealEvent(kever.delegator, seal=anchor):
if serder := self.hby.db.findAnchoringSealEvent(kever.delpre, seal=anchor):
aseq = coring.Seqner(sn=serder.sn)
couple = aseq.qb64b + serder.saidb
dgkey = dbing.dgKey(pre, saider.qb64b)
Expand Down
44 changes: 29 additions & 15 deletions src/keri/app/habbing.py
Original file line number Diff line number Diff line change
Expand Up @@ -129,8 +129,10 @@ class Habery:
psr (parsing.Parser): parses local messages for .kvy .rvy
habs (dict): Hab instances keyed by prefix.
To look up Hab by name get prefix from db.habs .prefix field using
.habByName
To look up Hab by name use use .habByName
To look up Hab by prefix us .habByPrefix
to get hab from db need name for key
hab prefix in db.habs record .hid field
inited (bool): True means fully initialized wrt databases.
False means not yet fully initialized
Expand Down Expand Up @@ -221,7 +223,8 @@ def __init__(self, *, name='test', base="", temp=False,
self.exc = exchanging.Exchanger(hby=self, handlers=[])
self.kvy = eventing.Kevery(db=self.db, lax=False, local=True, rvy=self.rvy)
self.kvy.registerReplyRoutes(router=self.rtr)
self.psr = parsing.Parser(framed=True, kvy=self.kvy, rvy=self.rvy, exc=self.exc)
self.psr = parsing.Parser(framed=True, kvy=self.kvy, rvy=self.rvy,
exc=self.exc, local=True)
self.habs = {} # empty .habs
self.namespaces = {} # empty .namespaces
self._signator = None
Expand All @@ -235,6 +238,7 @@ def __init__(self, *, name='test', base="", temp=False,
if self.db.opened and self.ks.opened:
self.setup(**self._inits) # finish setup later


def setup(self, *, seed=None, aeid=None, bran=None, pidx=None, algo=None,
salt=None, tier=None, free=False, temp=None, ):
"""
Expand Down Expand Up @@ -310,6 +314,7 @@ def setup(self, *, seed=None, aeid=None, bran=None, pidx=None, algo=None,
self.loadHabs()
self.inited = True


def loadHabs(self):
"""Load Habs instance from db
Expand Down Expand Up @@ -346,9 +351,9 @@ def loadHabs(self):
rtr=self.rtr, rvy=self.rvy, kvy=self.kvy, psr=self.psr,
name=name, pre=pre, temp=self.temp)

# Rules for acceptance
# if its delegated its accepted into its own local KEL even if the
# delegator has not sealed it
# Rules for acceptance:
# It is accepted into its own local KEL even if it has not been fully
# witnessed and if delegated, its delegator has not yet sealed it
if not hab.accepted and not habord.mid:
raise kering.ConfigurationError(f"Problem loading Hab pre="
f"{pre} name={name} from db.")
Expand Down Expand Up @@ -382,9 +387,9 @@ def loadHabs(self):
rtr=self.rtr, rvy=self.rvy, kvy=self.kvy, psr=self.psr,
name=name, ns=ns, pre=pre, temp=self.temp)

# Rules for acceptance
# if its delegated its accepted into its own local KEL even if the
# delegator has not sealed it
# Rules for acceptance:
# It is accepted into its own local KEL even if it has not been fully
# witnessed and if delegated, its delegator has not yet sealed it
if not hab.accepted and not habord.mid:
raise kering.ConfigurationError(f"Problem loading Hab pre="
f"{pre} name={name} from db.")
Expand All @@ -401,6 +406,7 @@ def loadHabs(self):

self.reconfigure() # post hab load reconfiguration


def makeHab(self, name, ns=None, cf=None, **kwa):
"""Make new Hab with name, pre is generated from **kwa
Expand Down Expand Up @@ -683,6 +689,8 @@ def deleteHab(self, name):

del self.habs[hab.pre]
self.db.prefixes.remove(hab.pre)
if hab.pre in self.db.groups:
self.db.groups.remove(hab.pre)

return True

Expand Down Expand Up @@ -752,7 +760,8 @@ def prefixes(self):

def habByPre(self, pre):
"""
Returns the Hab from and namespace including the default namespace.
Returns the Hab instance from .habs or .namespace
including the default namespace.
Args:
pre (str): qb64 aid of hab to find
Expand All @@ -773,7 +782,8 @@ def habByPre(self, pre):
def habByName(self, name, ns=None):
"""
Returns:
hab (Hab): instance from .habs by name if any otherwise None
hab (Hab): instance by name from .habs or .namspaces
if any otherwise None
Parameters:
name (str): alias of Hab
Expand Down Expand Up @@ -1026,7 +1036,7 @@ def __init__(self, ks, db, cf, mgr, rtr, rvy, kvy, psr, *,
self.psr = psr # injected

self.name = name
self.ns = ns
self.ns = ns # what is this?
self.pre = pre # wait to setup until after db is known to be opened
self.temp = True if temp else False

Expand Down Expand Up @@ -1239,7 +1249,7 @@ def rotate(self, *, verfers=None, digers=None, isith=None, nsith=None, toad=None
if not kever.ntholder.satisfy(indices):
raise kering.ValidationError("invalid rotation, new key set unable to satisfy prior next signing threshold")

if kever.delegator is not None: # delegator only shows up in delcept
if kever.delpre is not None: # delegator only shows up in delcept
serder = eventing.deltate(pre=kever.prefixer.qb64,
keys=keys,
dig=kever.serder.said,
Expand Down Expand Up @@ -1493,8 +1503,10 @@ def witness(self, serder):
indexed receipt signatures if key state of serder.pre shows that own pre
is a current witness of event in serder
Before calling this must check that serder being witnessed has been
accepted as valid event into controller's KEL
ToDo XXXX add parameter to force check that serder as been accepted
as valid. Otherwise must assume that before calling this that serder
being witnessed has been accepted as valid event into this hab
controller's KEL
"""
if self.kever.prefixer.transferable: # not non-transferable prefix
Expand Down Expand Up @@ -2144,6 +2156,7 @@ def processCuesIter(self, cues):
# ToDo XXXX cue for kin = "psUnescrow"
# ToDo XXXX cue for kin = "stream"
# ToDo XXXX cue for kin = "invalid"
# ToDo XXXX cue for kin=""remoteMemberedSig""


def witnesser(self):
Expand Down Expand Up @@ -2651,6 +2664,7 @@ def __init__(self, smids, mhab=None, rmids=None, **kwa):

super(GroupHab, self).__init__(**kwa)


def make(self, *, code=coring.MtrDex.Blake3_256, transferable=True, isith=None, nsith=None,
toad=None, wits=None, delpre=None, estOnly=False, DnD=False,
merfers, migers=None, data=None):
Expand Down
8 changes: 4 additions & 4 deletions src/keri/app/indirecting.py
Original file line number Diff line number Diff line change
Expand Up @@ -193,7 +193,7 @@ def msgDo(self, tymth=None, tock=0.0):

if self.parser.ims:
logger.info("Client %s received:\n%s\n...\n", self.kvy, self.parser.ims[:1024])
done = yield from self.parser.parsator() # process messages continuously
done = yield from self.parser.parsator(local=True) # process messages continuously
return done # should nover get here except forced close

def escrowDo(self, tymth=None, tock=0.0):
Expand Down Expand Up @@ -382,7 +382,7 @@ def msgDo(self, tymth=None, tock=0.0):

if self.parser.ims:
logger.info("Client %s received:\n%s\n...\n", self.hab.pre, self.parser.ims[:1024])
done = yield from self.parser.parsator() # process messages continuously
done = yield from self.parser.parsator(local=True) # process messages continuously
return done # should nover get here except forced close

def cueDo(self, tymth=None, tock=0.0):
Expand Down Expand Up @@ -673,7 +673,7 @@ def msgDo(self, tymth=None, tock=0.0):
self.tock = tock
_ = (yield self.tock)

done = yield from self.parser.parsator() # process messages continuously
done = yield from self.parser.parsator(local=True) # process messages continuously
return done # should nover get here except forced close

def escrowDo(self, tymth=None, tock=0.0):
Expand Down Expand Up @@ -1072,7 +1072,7 @@ def on_post(self, req, rep):
msg = bytearray(serder.raw)
msg.extend(cr.attachments.encode("utf-8"))

self.psr.parseOne(ims=msg)
self.psr.parseOne(ims=msg, local=True)

if pre in self.hab.kevers:
kever = self.hab.kevers[pre]
Expand Down
Loading

0 comments on commit 82a202d

Please sign in to comment.