Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Address traceability context bug #2743 #2744

22 changes: 22 additions & 0 deletions aries_cloudagent/resolver/default/web.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
from typing import Optional, Pattern, Sequence, Text

import aiohttp
import requests

from pydid import DID, DIDDocument

Expand Down Expand Up @@ -81,3 +82,24 @@ async def _resolve(
raise ResolverError(
"Could not find doc for {}: {}".format(did, await response.text())
)

def _resolve_with_request(
self,
did: str,
) -> dict:
"""Resolve did:web DIDs."""

url = self.__transform_to_url(did)
response = requests.get(url)
if response.status_code == 200:
try:
# Validate DIDDoc with pyDID
did_doc = DIDDocument.from_json(response.text)
return did_doc.serialize()
except Exception as err:
raise ResolverError("Response was incorrectly formatted") from err
if response.status == 404:
raise DIDNotFound(f"No document found for {did}")
raise ResolverError(
"Could not find doc for {}: {}".format(did, response.json())
)
2 changes: 2 additions & 0 deletions aries_cloudagent/vc/ld_proofs/constants.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,3 +19,5 @@
EXPANDED_TYPE_CREDENTIALS_CONTEXT_V1_VC_TYPE = (
"https://www.w3.org/2018/credentials#VerifiableCredential"
)

TRACEABILITY_CONTEXT_V1_URL = "https://w3id.org/traceability/v1"
26 changes: 23 additions & 3 deletions aries_cloudagent/vc/ld_proofs/purposes/controller_proof_purpose.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,9 @@
from pyld.jsonld import JsonLdProcessor
from pyld import jsonld

from ..constants import SECURITY_CONTEXT_URL
from ....resolver.default.web import WebDIDResolver

from ..constants import SECURITY_CONTEXT_URL, TRACEABILITY_CONTEXT_V1_URL
from ..document_loader import DocumentLoaderMethod
from ..error import LinkedDataProofException
from ..validation_result import PurposeResult
Expand Down Expand Up @@ -53,9 +55,26 @@ def validate(
else:
raise LinkedDataProofException('"controller" must be a string or dict')

input_to_frame = controller_id
# Get the controller
# If the controller is a web did we first resolve the document
if controller_id.startswith("did:web:"):
did_document = WebDIDResolver()._resolve_with_request(controller_id)
# We remove the traceability context if present
# to avoid a bug with the pyld library
# https://github.com/digitalbazaar/pyld/issues/188
did_document["@context"] = [
i
for i in did_document["@context"]
if i != TRACEABILITY_CONTEXT_V1_URL
]
input_to_frame = did_document

# If we have the did_document accessible locally,
# we use it as the input to frame
# Otherwise we use the controller_id
result.controller = jsonld.frame(
controller_id,
input_to_frame,
frame={
"@context": SECURITY_CONTEXT_URL,
"id": controller_id,
Expand All @@ -64,7 +83,8 @@ def validate(
options={
"documentLoader": document_loader,
"expandContext": SECURITY_CONTEXT_URL,
# if we don't set base explicitly it will remove the base in returned
# if we don't set base explicitly it
# will remove the base in returned
# document (e.g. use key:z... instead of did:key:z...)
# same as compactToRelative in jsonld.js
"base": None,
Expand Down
24 changes: 21 additions & 3 deletions aries_cloudagent/vc/ld_proofs/suites/linked_data_proof.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,10 @@
from pyld import jsonld
from typing_extensions import TypedDict

from ....resolver.default.web import WebDIDResolver

from ..check import get_properties_without_context
from ..constants import SECURITY_CONTEXT_URL
from ..constants import SECURITY_CONTEXT_URL, TRACEABILITY_CONTEXT_V1_URL
from ..document_loader import DocumentLoaderMethod
from ..error import LinkedDataProofException
from ..purposes import _ProofPurpose as ProofPurpose
Expand Down Expand Up @@ -137,13 +139,29 @@ def _get_verification_method(

if isinstance(verification_method, dict):
verification_method: str = verification_method.get("id")

if not verification_method:
raise LinkedDataProofException('No "verificationMethod" found in proof')

input_to_frame = verification_method
# If the verification_method is a web did we first resolve the document
if verification_method.startswith("did:web:"):
did_document = WebDIDResolver()._resolve_with_request(
verification_method.split("#")[0]
)
# We remove the traceability context if present
# to avoid a bug with the pyld library
# https://github.com/digitalbazaar/pyld/issues/188
did_document["@context"] = [
i for i in did_document["@context"] if i != TRACEABILITY_CONTEXT_V1_URL
]
input_to_frame = did_document

# If we have the did_document accessible locally,
# we use it as the input to frame
# Otherwise we use the verification_method
# TODO: This should optionally use the context of the document?
framed = jsonld.frame(
verification_method,
input_to_frame,
frame={
"@context": SECURITY_CONTEXT_URL,
"@embed": "@always",
Expand Down
Loading