Skip to content

Commit

Permalink
Merge branch 'master' into find-missing-tails-file
Browse files Browse the repository at this point in the history
  • Loading branch information
andrewwhitehead authored Aug 28, 2020
2 parents ea629b8 + 6f143f4 commit 3950758
Show file tree
Hide file tree
Showing 22 changed files with 654 additions and 177 deletions.
2 changes: 1 addition & 1 deletion aries_cloudagent/config/argparse.py
Original file line number Diff line number Diff line change
Expand Up @@ -799,7 +799,7 @@ def add_arguments(self, parser: ArgumentParser):
metavar="<storage-type>",
help="Specifies the type of Indy wallet backend to use.\
Supported internal storage types are 'basic' (memory),\
'indy', and 'postgres_storage'.",
'default' (sqlite), and 'postgres_storage'.",
)
parser.add_argument(
"--wallet-storage-config",
Expand Down
5 changes: 5 additions & 0 deletions aries_cloudagent/ledger/indy.py
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@
from ..storage.indy import IndyStorage
from ..utils import sentinel
from ..wallet.base import BaseWallet, DIDInfo
from ..wallet.did_posture import DIDPosture

from .base import BaseLedger
from .endpoint_type import EndpointType
Expand Down Expand Up @@ -877,6 +878,10 @@ async def register_nym(

await self._submit(request_json)

did_info = await self.wallet.get_local_did(did)
metadata = {**did_info.metadata, **DIDPosture.POSTED.metadata}
await self.wallet.replace_local_did_metadata(did, metadata)

async def get_nym_role(self, did: str) -> Role:
"""
Return the role of the input public DID's NYM on the ledger.
Expand Down
7 changes: 7 additions & 0 deletions aries_cloudagent/ledger/routes.py
Original file line number Diff line number Diff line change
Expand Up @@ -147,6 +147,13 @@ async def register_ledger_nym(request: web.BaseRequest):
raise web.HTTPForbidden(reason=err.roll_up)
except LedgerError as err:
raise web.HTTPBadRequest(reason=err.roll_up)
except WalletError as err:
raise web.HTTPBadRequest(
reason=(
f"Registered NYM for DID {did} on ledger but could not "
f"replace metadata in wallet: {err.roll_up}"
)
)

return web.json_response({"success": success})

Expand Down
6 changes: 3 additions & 3 deletions aries_cloudagent/ledger/tests/test_endpoint_type.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,9 @@

class TestEndpointType(AsyncTestCase):
async def test_endpoint_type(self):
assert EndpointType.ENDPOINT == EndpointType.get("endpoint")
assert EndpointType.PROFILE == EndpointType.get("PROFILE")
assert EndpointType.LINKED_DOMAINS == EndpointType.get("linked_domains")
assert EndpointType.ENDPOINT is EndpointType.get("endpoint")
assert EndpointType.PROFILE is EndpointType.get("PROFILE")
assert EndpointType.LINKED_DOMAINS is EndpointType.get("linked_domains")
assert EndpointType.get("no-such-type") is None
assert EndpointType.get(None) is None

Expand Down
7 changes: 5 additions & 2 deletions aries_cloudagent/ledger/tests/test_indy.py
Original file line number Diff line number Diff line change
Expand Up @@ -2168,8 +2168,11 @@ async def test_update_endpoint_for_did_read_only(
async def test_register_nym(
self, mock_submit, mock_build_nym_req, mock_close, mock_open
):
mock_wallet = async_mock.MagicMock()
mock_wallet.type = "indy"
mock_wallet = async_mock.MagicMock(
type="indy",
get_local_did=async_mock.CoroutineMock(),
replace_local_did_metadata=async_mock.CoroutineMock(),
)

ledger = IndyLedger("name", mock_wallet)

Expand Down
8 changes: 8 additions & 0 deletions aries_cloudagent/ledger/tests/test_routes.py
Original file line number Diff line number Diff line change
Expand Up @@ -176,6 +176,14 @@ async def test_register_nym_ledger_error(self):
with self.assertRaises(test_module.web.HTTPBadRequest):
await test_module.register_ledger_nym(request)

async def test_register_nym_wallet_error(self):
request = async_mock.MagicMock()
request.app = self.app
request.query = {"did": self.test_did, "verkey": self.test_verkey}
self.ledger.register_nym.side_effect = test_module.WalletError("Error")
with self.assertRaises(test_module.web.HTTPBadRequest):
await test_module.register_ledger_nym(request)

async def test_get_nym_role(self):
request = async_mock.MagicMock()
request.app = self.app
Expand Down
2 changes: 1 addition & 1 deletion aries_cloudagent/messaging/jsonld/create_verify_data.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ def _canonize(data):


def _sha256(data):
return hashlib.sha256(data.encode("ascii")).hexdigest()
return hashlib.sha256(data.encode("utf-8")).hexdigest()


def _cannonize_signature_options(signatureOptions):
Expand Down
62 changes: 42 additions & 20 deletions aries_cloudagent/messaging/jsonld/tests/test_routes.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,22 +4,21 @@
from aries_cloudagent.config.injection_context import InjectionContext
from aries_cloudagent.wallet.base import BaseWallet
from aries_cloudagent.wallet.basic import BasicWallet

from ....storage.base import BaseStorage

from .. import routes as test_module


# TODO: Add tests
class TestJSONLDRoutes(AsyncTestCase):
def setUp(self):
async def setUp(self):
self.context = InjectionContext(enforce_typing=False)

self.storage = async_mock.create_autospec(BaseStorage)

self.context.injector.bind_instance(BaseStorage, self.storage)

self.wallet = self.wallet = BasicWallet()
self.did_info = await self.wallet.create_local_did()
self.context.injector.bind_instance(BaseWallet, self.wallet)

self.app = {
"request_context": self.context,
}
Expand All @@ -29,18 +28,26 @@ async def test_verify_credential(self):
app=self.app,
json=async_mock.CoroutineMock(
return_value={ # posted json
"verkey": "5yKdnU7ToTjAoRNDzfuzVTfWBH38qyhE1b9xh4v8JaWF", # pulled from the did:key in example
"verkey": (
# pulled from the did:key in example
"5yKdnU7ToTjAoRNDzfuzVTfWBH38qyhE1b9xh4v8JaWF"
),
"doc": {
"@context": [
"https://www.w3.org/2018/credentials/v1",
"https://www.w3.org/2018/credentials/examples/v1",
],
"id": "http://example.gov/credentials/3732",
"type": ["VerifiableCredential", "UniversityDegreeCredential"],
"issuer": "did:key:z6MkjRagNiMu91DduvCvgEsqLZDVzrJzFrwahc4tXLt9DoHd",
"issuer": (
"did:key:z6MkjRagNiMu91DduvCvgEsqLZDVzrJzFrwahc4tXLt9DoHd"
),
"issuanceDate": "2020-03-10T04:24:12.164Z",
"credentialSubject": {
"id": "did:key:z6MkjRagNiMu91DduvCvgEsqLZDVzrJzFrwahc4tXLt9DoHd",
"id": (
"did:key:"
"z6MkjRagNiMu91DduvCvgEsqLZDVzrJzFrwahc4tXLt9DoHd"
),
"degree": {
"type": "BachelorDegree",
"name": "Bachelor of Science and Arts",
Expand All @@ -49,9 +56,19 @@ async def test_verify_credential(self):
"proof": {
"type": "Ed25519Signature2018",
"created": "2020-04-10T21:35:35Z",
"verificationMethod": "did:key:z6MkjRagNiMu91DduvCvgEsqLZDVzrJzFrwahc4tXLt9DoHd#z6MkjRagNiMu91DduvCvgEsqLZDVzrJzFrwahc4tXLt9DoHd",
"verificationMethod": (
"did:key:"
"z6MkjRagNiMu91DduvCvgEsqLZDVzrJzFrwahc"
"4tXLt9DoHd#z6MkjRagNiMu91DduvCvgEsqLZD"
"VzrJzFrwahc4tXLt9DoHd"
),
"proofPurpose": "assertionMethod",
"jws": "eyJhbGciOiJFZERTQSIsImI2NCI6ZmFsc2UsImNyaXQiOlsiYjY0Il19..l9d0YHjcFAH2H4dB9xlWFZQLUpixVCWJk0eOt4CXQe1NXKWZwmhmn9OQp6YxX0a2LffegtYESTCJEoGVXLqWAA",
"jws": (
"eyJhbGciOiJFZERTQSIsImI2NCI6ZmFsc2UsImNyaX"
"QiOlsiYjY0Il19..l9d0YHjcFAH2H4dB9xlWFZQLUp"
"ixVCWJk0eOt4CXQe1NXKWZwmhmn9OQp6YxX0a2Lffe"
"gtYESTCJEoGVXLqWAA"
),
},
},
}
Expand All @@ -64,16 +81,11 @@ async def test_verify_credential(self):
mock_response.assert_called_once_with({"valid": True}) # expected response

async def test_sign_credential(self):

wallet: BaseWallet = await self.app["request_context"].inject(BaseWallet)

did_info = await wallet.create_local_did()

mock_request = async_mock.MagicMock(
app=self.app,
json=async_mock.CoroutineMock(
return_value={ # posted json
"verkey": did_info.verkey,
"verkey": self.did_info.verkey,
"doc": {
"credential": {
"@context": [
Expand All @@ -85,20 +97,30 @@ async def test_sign_credential(self):
"VerifiableCredential",
"UniversityDegreeCredential",
],
"issuer": "did:key:z6MkjRagNiMu91DduvCvgEsqLZDVzrJzFrwahc4tXLt9DoHd",
"issuer": (
"did:key:"
"z6MkjRagNiMu91DduvCvgEsqLZDVzrJzFrwahc4tXLt9DoHd"
),
"issuanceDate": "2020-03-10T04:24:12.164Z",
"credentialSubject": {
"id": "did:key:z6MkjRagNiMu91DduvCvgEsqLZDVzrJzFrwahc4tXLt9DoHd",
"id": (
"did:key:"
"z6MkjRagNiMu91DduvCvgEsqLZDVzrJzFrwahc4tXLt9DoHd"
),
"degree": {
"type": "BachelorDegree",
"name": "Bachelor of Science and Arts",
"name": u"Bachelor of Encyclopædic Arts",
},
},
},
"options": {
"type": "Ed25519Signature2018",
"created": "2020-04-10T21:35:35Z",
"verificationMethod": "did:key:z6MkjRagNiMu91DduvCvgEsqLZDVzrJzFrwahc4tXLt9DoHd#z6MkjRagNiMu91DduvCvgEsqLZDVzrJzFrwahc4tXLt9DoHd",
"verificationMethod": (
"did:key:"
"z6MkjRagNiMu91DduvCvgEsqLZDVzrJzFrwahc4tXLt9DoHd#"
"z6MkjRagNiMu91DduvCvgEsqLZDVzrJzFrwahc4tXLt9DoHd"
),
"proofPurpose": "assertionMethod",
},
},
Expand Down
17 changes: 17 additions & 0 deletions aries_cloudagent/messaging/tests/test_valid.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
BASE64URL,
BASE64URL_NO_PAD,
DID_KEY,
DID_POSTURE,
ENDPOINT,
ENDPOINT_TYPE,
INDY_CRED_DEF_ID,
Expand Down Expand Up @@ -145,6 +146,22 @@ def test_did_key(self):

DID_KEY["validate"]("did:key:zQ4zqM7aXqm7gDQkUVLng9h")

def test_did_posture(self):
non_did_postures = [
"not-me",
None,
"PUBLIC",
"Posted",
"wallet only",
]
for non_did_posture in non_did_postures:
with self.assertRaises(ValidationError):
DID_POSTURE["validate"](non_did_posture)

DID_POSTURE["validate"]("public")
DID_POSTURE["validate"]("posted")
DID_POSTURE["validate"]("wallet_only")

def test_indy_base58_sha256_hash(self):
non_base58_sha256_hashes = [
"Q4zqM7aXqm7gDQkUVLng9JQ4zqM7aXqm7gDQkUVLng9I", # 'I' not a base58 char
Expand Down
16 changes: 16 additions & 0 deletions aries_cloudagent/messaging/valid.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
from .util import epoch_to_str

from ..ledger.endpoint_type import EndpointType as EndpointTypeEnum
from ..wallet.did_posture import DIDPosture as DIDPostureEnum

B58 = alphabet if isinstance(alphabet, str) else alphabet.decode("ascii")

Expand Down Expand Up @@ -114,6 +115,20 @@ def __init__(self):
)


class DIDPosture(OneOf):
"""Validate value against defined DID postures."""

EXAMPLE = DIDPostureEnum.WALLET_ONLY.moniker

def __init__(self):
"""Initializer."""

super().__init__(
choices=[did_posture.moniker for did_posture in DIDPostureEnum],
error="Value {input} must be one of {choices}",
)


class IndyDID(Regexp):
"""Validate value against indy DID."""

Expand Down Expand Up @@ -455,6 +470,7 @@ def __init__(self):
JWS_HEADER_KID = {"validate": JWSHeaderKid(), "example": JWSHeaderKid.EXAMPLE}
JWT = {"validate": JSONWebToken(), "example": JSONWebToken.EXAMPLE}
DID_KEY = {"validate": DIDKey(), "example": DIDKey.EXAMPLE}
DID_POSTURE = {"validate": DIDPosture(), "example": DIDPosture.EXAMPLE}
INDY_DID = {"validate": IndyDID(), "example": IndyDID.EXAMPLE}
INDY_RAW_PUBLIC_KEY = {
"validate": IndyRawPublicKey(),
Expand Down
7 changes: 4 additions & 3 deletions aries_cloudagent/protocols/present_proof/v1_0/manager.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,8 @@
from .messages.presentation import Presentation
from .message_types import ATTACH_DECO_IDS, PRESENTATION, PRESENTATION_REQUEST

LOGGER = logging.getLogger(__name__)


class PresentationManagerError(BaseError):
"""Presentation error."""
Expand All @@ -37,7 +39,6 @@ def __init__(self, context: InjectionContext):
"""

self._context = context
self._logger = logging.getLogger(__name__)

@property
def context(self) -> InjectionContext:
Expand Down Expand Up @@ -393,7 +394,7 @@ async def create_presentation(
)
)
except HolderError as e:
self._logger.error(
LOGGER.error(
f"Failed to create revocation state: {e.error_code}, {e.message}"
)
raise e
Expand Down Expand Up @@ -615,7 +616,7 @@ async def send_presentation_ack(
connection_id=presentation_exchange_record.connection_id,
)
else:
self._logger.warning(
LOGGER.warning(
"Configuration has no BaseResponder: cannot ack presentation on %s",
presentation_exchange_record.thread_id,
)
Expand Down
15 changes: 10 additions & 5 deletions aries_cloudagent/protocols/present_proof/v1_0/routes.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@

from ....connections.models.connection_record import ConnectionRecord
from ....holder.base import BaseHolder, HolderError
from ....indy.util import generate_pr_nonce
from ....ledger.error import LedgerError
from ....messaging.decorators.attach_decorator import AttachDecorator
from ....messaging.models.base import BaseModelError
Expand All @@ -33,7 +34,8 @@
WHOLE_NUM,
)
from ....storage.error import StorageError, StorageNotFoundError
from ....indy.util import generate_pr_nonce
from ....utils.tracing import trace_event, get_timer, AdminAPIMessageTracingSchema
from ....wallet.error import WalletNotFoundError

from ...problem_report.v1_0 import internal_error

Expand All @@ -51,9 +53,6 @@
)


from ....utils.tracing import trace_event, get_timer, AdminAPIMessageTracingSchema


class V10PresentationExchangeListQueryStringSchema(OpenAPISchema):
"""Parameters and validators for presentation exchange list query."""

Expand Down Expand Up @@ -931,7 +930,13 @@ async def presentation_exchange_send_presentation(request: web.BaseRequest):
comment=body.get("comment"),
)
result = pres_ex_record.serialize()
except (BaseModelError, HolderError, LedgerError, StorageError) as err:
except (
BaseModelError,
HolderError,
LedgerError,
StorageError,
WalletNotFoundError,
) as err:
await internal_error(
err,
web.HTTPBadRequest,
Expand Down
Loading

0 comments on commit 3950758

Please sign in to comment.