Skip to content

Commit

Permalink
Merge branch 'main' into main
Browse files Browse the repository at this point in the history
  • Loading branch information
ianco authored Nov 10, 2021
2 parents 60f3538 + 576bcad commit 1460b2d
Show file tree
Hide file tree
Showing 17 changed files with 2,865 additions and 196 deletions.
37 changes: 33 additions & 4 deletions aries_cloudagent/config/argparse.py
Original file line number Diff line number Diff line change
Expand Up @@ -1535,15 +1535,25 @@ def add_arguments(self, parser: ArgumentParser):
"directly."
),
)
parser.add_argument(
"--endorser-invitation",
type=str,
metavar="<endorser-invitation>",
env_var="ACAPY_ENDORSER_INVITATION",
help=(
"For transaction Authors, specify the invitation used to "
"connect to the Endorser agent who will be endorsing transactions. "
"Note this is a multi-use invitation created by the Endorser agent."
),
)
parser.add_argument(
"--endorser-public-did",
type=str,
metavar="<endorser-public-did>",
env_var="ACAPY_ENDORSER_PUBLIC_DID",
help=(
"For transaction Authors, specify the the public DID of the Endorser "
"agent who will be endorsing transactions. Note this requires that "
"the connection be made using the Endorser's public DID."
"For transaction Authors, specify the public DID of the Endorser "
"agent who will be endorsing transactions."
),
)
parser.add_argument(
Expand All @@ -1552,7 +1562,7 @@ def add_arguments(self, parser: ArgumentParser):
metavar="<endorser-alias>",
env_var="ACAPY_ENDORSER_ALIAS",
help=(
"For transaction Authors, specify the the alias of the Endorser "
"For transaction Authors, specify the alias of the Endorser "
"connection that will be used to endorse transactions."
),
)
Expand Down Expand Up @@ -1623,6 +1633,25 @@ def get_settings(self, args: Namespace):
"Authors"
)

if args.endorser_invitation:
if settings["endorser.author"]:
if not settings.get("endorser.endorser_public_did"):
raise ArgsParseError(
"Parameter --endorser-public-did must be provided if "
"--endorser-invitation is set."
)
if not settings.get("endorser.endorser_alias"):
raise ArgsParseError(
"Parameter --endorser-alias must be provided if "
"--endorser-invitation is set."
)
settings["endorser.endorser_invitation"] = args.endorser_invitation
else:
raise ArgsParseError(
"Parameter --endorser-invitation should only be set for transaction "
"Authors"
)

if args.auto_request_endorsement:
if settings["endorser.author"]:
settings["endorser.auto_request"] = True
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,17 +5,15 @@
Enables having the mediation invite config be the same
for `provision` and `starting` commands.
"""
import dataclasses
import json
from typing import Optional
from typing import NamedTuple, Optional

from aries_cloudagent.storage.base import BaseStorage
from aries_cloudagent.storage.error import StorageNotFoundError
from aries_cloudagent.storage.record import StorageRecord


@dataclasses.dataclass
class MediationInviteRecord:
class MediationInviteRecord(NamedTuple):
"""A record to store mediation invites and their freshness."""

invite: str
Expand Down
91 changes: 88 additions & 3 deletions aries_cloudagent/protocols/endorse_transaction/v1_0/routes.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
"""Endorse Transaction handling admin routes."""

import json
import logging

from aiohttp import web
from aiohttp_apispec import (
Expand All @@ -22,11 +23,20 @@
from ....messaging.models.base import BaseModelError
from ....messaging.models.openapi import OpenAPISchema
from ....messaging.valid import UUIDFour
from ....protocols.connections.v1_0.manager import ConnectionManager
from ....protocols.connections.v1_0.messages.connection_invitation import (
ConnectionInvitation,
)
from ....protocols.out_of_band.v1_0.manager import OutOfBandManager
from ....protocols.out_of_band.v1_0.messages.invitation import InvitationMessage
from ....storage.error import StorageError, StorageNotFoundError

from .manager import TransactionManager, TransactionManagerError
from .models.transaction_record import TransactionRecord, TransactionRecordSchema
from .transaction_jobs import TransactionJob
from .util import is_author_role, get_endorser_connection_id

LOGGER = logging.getLogger(__name__)


class TransactionListSchema(OpenAPISchema):
Expand Down Expand Up @@ -705,13 +715,88 @@ def register_events(event_bus: EventBus):

async def on_startup_event(profile: Profile, event: Event):
"""Handle any events we need to support."""
print(">>> TODO Received STARTUP event")
pass

# auto setup is only for authors
if not is_author_role(profile):
return

# see if we have an invitation to connect to the endorser
endorser_invitation = profile.settings.get_value("endorser.endorser_invitation")
if not endorser_invitation:
# no invitation, we can't connect automatically
return

# see if we need to initiate an endorser connection
endorser_alias = profile.settings.get_value("endorser.endorser_alias")
if not endorser_alias:
# no alias is specified for the endorser connection
# note that alias is required if invitation is specified
return

connection_id = await get_endorser_connection_id(profile)
if connection_id:
# there is already a connection
return

endorser_did = profile.settings.get_value("endorser.endorser_public_did")
if not endorser_did:
# no DID, we can connect but we can't properly setup the connection metadata
# note that DID is required if invitation is specified
return

try:
# OK, we are an author, we have no endorser connection but we have enough info
# to automatically initiate the connection
invite = InvitationMessage.from_url(endorser_invitation)
if invite:
oob_mgr = OutOfBandManager(profile)
conn_record = await oob_mgr.receive_invitation(
invitation=invite,
auto_accept=True,
alias=endorser_alias,
)
else:
invite = ConnectionInvitation.from_url(endorser_invitation)
if invite:
conn_mgr = ConnectionManager(profile)
conn_record = await conn_mgr.receive_invitation(
invitation=invite,
auto_accept=True,
alias=endorser_alias,
)
else:
raise Exception(
"Failed to establish endorser connection, invalid "
"invitation format."
)

# configure the connection role and info (don't need to wait for the connection)
transaction_mgr = TransactionManager(profile)
await transaction_mgr.set_transaction_my_job(
record=conn_record,
transaction_my_job=TransactionJob.TRANSACTION_AUTHOR.name,
)

async with profile.session() as session:
value = await conn_record.metadata_get(session, "endorser_info")
if value:
value["endorser_did"] = endorser_did
value["endorser_name"] = endorser_alias
else:
value = {"endorser_did": endorser_did, "endorser_name": endorser_alias}
await conn_record.metadata_set(session, key="endorser_info", value=value)

except Exception as e:
# log the error, but continue
LOGGER.exception(
"Error accepting endorser invitation/configuring endorser connection: %s",
str(e),
)


async def on_shutdown_event(profile: Profile, event: Event):
"""Handle any events we need to support."""
print(">>> TODO Received SHUTDOWN event")
# nothing to do for now ...
pass


Expand Down
84 changes: 79 additions & 5 deletions aries_cloudagent/protocols/present_proof/dif/pres_exch.py
Original file line number Diff line number Diff line change
Expand Up @@ -146,7 +146,7 @@ class Meta:
_from = fields.Str(description="From", required=False, data_key="from")
# Self References
from_nested = fields.List(
fields.Nested(lambda: SubmissionRequirementsSchema(exclude=("from_nested",))),
fields.Nested(lambda: SubmissionRequirementsSchema()),
required=False,
)

Expand Down Expand Up @@ -180,7 +180,7 @@ def __init__(
uri: str = None,
required: bool = None,
):
"""Initialize InputDescriptors."""
"""Initialize SchemaInputDescriptor."""
self.uri = uri
self.required = required

Expand All @@ -201,6 +201,59 @@ class Meta:
required = fields.Bool(description="Required", required=False)


class SchemasInputDescriptorFilter(BaseModel):
"""SchemasInputDescriptorFilter."""

class Meta:
"""InputDescriptor Schemas filter metadata."""

schema_class = "SchemasInputDescriptorFilterSchema"

def __init__(
self,
*,
oneof_filter: bool = False,
uri_groups: Sequence[Sequence[SchemaInputDescriptor]] = None,
):
"""Initialize SchemasInputDescriptorFilter."""
self.oneof_filter = oneof_filter
self.uri_groups = uri_groups


class SchemasInputDescriptorFilterSchema(BaseModelSchema):
"""Single SchemasInputDescriptorFilterSchema Schema."""

class Meta:
"""SchemasInputDescriptorFilterSchema metadata."""

model_class = SchemasInputDescriptorFilter
unknown = EXCLUDE

uri_groups = fields.List(fields.List(fields.Nested(SchemaInputDescriptorSchema)))
oneof_filter = fields.Bool(description="oneOf")

@pre_load
def extract_info(self, data, **kwargs):
"""deserialize."""
new_data = {}
if isinstance(data, dict):
if "oneof_filter" in data:
new_data["oneof_filter"] = True
uri_group_list_of_list = []
uri_group_list = data.get("oneof_filter")
for uri_group in uri_group_list:
if isinstance(uri_group, list):
uri_group_list_of_list.append(uri_group)
else:
uri_group_list_of_list.append([uri_group])
new_data["uri_groups"] = uri_group_list_of_list
elif isinstance(data, list):
new_data["oneof_filter"] = False
new_data["uri_groups"] = [data]
data = new_data
return data


class DIFHolder(BaseModel):
"""Single Holder object for Constraints."""

Expand Down Expand Up @@ -548,7 +601,7 @@ def __init__(
purpose: str = None,
metadata: dict = None,
constraint: Constraints = None,
schemas: Sequence[SchemaInputDescriptor] = None,
schemas: SchemasInputDescriptorFilter = None,
):
"""Initialize InputDescriptors."""
self.id = id
Expand Down Expand Up @@ -584,8 +637,29 @@ class Meta:
constraint = fields.Nested(
ConstraintsSchema, required=False, data_key="constraints"
)
schemas = fields.List(
fields.Nested(SchemaInputDescriptorSchema), required=False, data_key="schema"
schemas = fields.Nested(
SchemasInputDescriptorFilterSchema,
required=False,
data_key="schema",
description=(
"Accepts a list of schema or a dict containing filters like oneof_filter."
),
example=(
{
"oneOf": [
[
{"uri": "https://www.w3.org/Test1#Test1"},
{"uri": "https://www.w3.org/Test2#Test2"},
],
{
"oneof_filter": [
[{"uri": "https://www.w3.org/Test1#Test1"}],
[{"uri": "https://www.w3.org/Test2#Test2"}],
]
},
]
}
),
)


Expand Down
Loading

0 comments on commit 1460b2d

Please sign in to comment.