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

Align "usage" with "verificationMethod purpose" #362

Closed
OR13 opened this issue Dec 24, 2019 · 24 comments
Closed

Align "usage" with "verificationMethod purpose" #362

OR13 opened this issue Dec 24, 2019 · 24 comments
Assignees
Labels
protocol Sidetree protocol change proposal Spec v1

Comments

@OR13
Copy link
Contributor

OR13 commented Dec 24, 2019

Consider:

{
  "@context": "https://w3id.org/did/v1",
  "id": "did:key:z6Mkozt95WhH9chvYaPTTsd1FzMbXc1cuvo1hfiZodGNd9Gs",
  "publicKey": [
    {
      "id": "did:key:z6Mkozt95WhH9chvYaPTTsd1FzMbXc1cuvo1hfiZodGNd9Gs",
      "type": "Ed25519VerificationKey2018",
      "controller": "did:key:z6Mkozt95WhH9chvYaPTTsd1FzMbXc1cuvo1hfiZodGNd9Gs",
      "publicKeyBase58": "AYd6VGSqp5DTS5YknJfAQtobi2jmW3Yf1eodyMJMhvVV"
    }
  ],
  "authentication": [
    "did:key:z6Mkozt95WhH9chvYaPTTsd1FzMbXc1cuvo1hfiZodGNd9Gs"
  ],
  "assertionMethod": [
    "did:key:z6Mkozt95WhH9chvYaPTTsd1FzMbXc1cuvo1hfiZodGNd9Gs"
  ],
  "capabilityDelegation": [
    "did:key:z6Mkozt95WhH9chvYaPTTsd1FzMbXc1cuvo1hfiZodGNd9Gs"
  ],
  "capabilityInvocation": [
    "did:key:z6Mkozt95WhH9chvYaPTTsd1FzMbXc1cuvo1hfiZodGNd9Gs"
  ],
  "keyAgreement": [
    {
      "id": "did:key:z6Mkozt95WhH9chvYaPTTsd1FzMbXc1cuvo1hfiZodGNd9Gs#zC3tSpPuJfsqkaBy9PR2sYLVRR7P8EpRUChi8oDoWQMsZ4",
      "type": "X25519KeyAgreementKey2019",
      "controller": "did:key:z6Mkozt95WhH9chvYaPTTsd1FzMbXc1cuvo1hfiZodGNd9Gs",
      "publicKeyBase58": "4Pj72iVUW6U95vAw1YJaBKk7s7KHFirhopqmNii1FdSr"
    }
  ]
}

capabilityInvocation, assertionMethod, etc... these are "usage".

This topic was discussed in did core: w3c/did-core#2

IMO the correct way to handle this concept under the current world view of JSON-LD, is to define a sidetree context, and provide a new top level verificationMethod purpose called "recovery" or similar.

and then link the keys that are recovery keys as they are for authentication in the example above.

"usage = signing" is equivalent to assertionMethod.

Also note that since "usage" is not defined in the did core context, it must be defined in a method specific context to avoid errors, see also:

w3c/did-core#128

@OR13 OR13 added the protocol Sidetree protocol change proposal label Dec 24, 2019
@gjgd
Copy link
Member

gjgd commented Jan 7, 2020

Yes, I agree with what @OR13 said above ^ The publicKey property in a did document is meant for specifying public keys as verification methods, and is not meant to specify how these verification methods should be used. That is the job of the authentication, authorization, etc... properties

I would also add that:

@OR13
Copy link
Contributor Author

OR13 commented Jan 7, 2020

The reason it is ignored is that its not present in the did-core JSON-LD context.

When we add our extension to the context for element, it will be returned by the universal resolver properly (and the did document will be valid JSON-LD again)

https://docs.element-did.com/contexts/sidetree/sidetree-v0.0.jsonld

@OR13
Copy link
Contributor Author

OR13 commented Jan 7, 2020

@peacekeeper I wonder if we are hurting people by removing properties that are not in context from the universal resolver....

It makes it sorta hard to use the universal resolver to health check spec compliance.

I was thinking of writing a script to resolve the example dids, and sign them with JSON-LD, and see which just fail, but some might pass because of things the universal resolver is doing that would otherwise fail...

This is one such example.

@OR13
Copy link
Contributor Author

OR13 commented Jan 7, 2020

Another alternative would be to provide the raw json unprocessed, and some kind of indication of whether it is valid JSON-LD...

@gjgd
Copy link
Member

gjgd commented Jan 8, 2020

Yes agreed, right now it is not clear that the content of the "Did Document" tab is processed and that properties may be filtered out

@OR13
Copy link
Contributor Author

OR13 commented Jan 26, 2020

Proof that sidetree did methods are not W3 compliant: https://travis-ci.org/decentralized-identity/context/jobs/641886720#L290

@csuwildcat
Copy link
Member

Hopefully after the F2F in Amsterdam we'll have some conclusions around the requirements and options related to the DID Document's composition and format that we can use to close this out. I would like to wait until after that to take any action, because they may made some decisions that impact what we can/must do.

@OR13
Copy link
Contributor Author

OR13 commented Jan 26, 2020

Sidetree did methods will still not be valid json-ld if they contain a context which does not define usage... which belongs as root level property in the did document, and not as an annotation on public keys...

the correct way to handle this is:

{
  "id": "did:elem:EiChaglAoJaBq7bGWp6bA5PAQKaOTzVHVXIlJqyQbljfmg",
  "@context": [
    "https://www.w3.org/ns/did/v1",
    "https://docs.element-did.com/contexts/sidetree/sidetree-v0.1.jsonld"
  ],
  "publicKey": [
    {
      "publicKeyJwk": {
        "crv": "secp256k1",
        "y": "EiZOvo9JWPz1yGlNNW66IV8uA44EQP_Yv_E7OZl1NG0",
        "kid": "qfknmVDhMi3Uc190IHBRfBRqMgbEEBRzWOj1E9EmzwM",
        "x": "NbASvplLIO_XTzP9R69a3MuqOO0DQw2LGnhJjirpd4w",
        "kty": "EC"
      },
      "type": "EcdsaSecp256k1VerificationKey2019",
      "id": "#qfknmVDhMi3Uc190IHBRfBRqMgbEEBRzWOj1E9EmzwM",
      "controller": "did:elem:EiChaglAoJaBq7bGWp6bA5PAQKaOTzVHVXIlJqyQbljfmg"
    },
    {
      "id": "#primary",
      "publicKeyHex": "0335b012be994b20efd74f33fd47af5adccbaa38ed03430d8b1a78498e2ae9778c",
      "type": "EcdsaSecp256k1VerificationKey2019",
      "controller": "did:elem:EiChaglAoJaBq7bGWp6bA5PAQKaOTzVHVXIlJqyQbljfmg"
    },
    {
      "publicKeyHex": "03f4c82cee043eeb8dbed2bf02a6b9b066c742557816a738f74a6e4dfd2bbc6469",
      "type": "EcdsaSecp256k1VerificationKey2019",
      "id": "#recovery",
      "controller": "did:elem:EiChaglAoJaBq7bGWp6bA5PAQKaOTzVHVXIlJqyQbljfmg"
    },
    {
      "type": "Ed25519VerificationKey2018",
      "publicKeyBase58": "5gjvqgVsgJYsTaxmVdZ4jtPfgafe7FkvAKF2xRLtkW3H",
      "id": "#PiF0Sf3wDqec9_LYGO5T5-i4ihm7byhbUpoMq2nhZBg",
      "controller": "did:elem:EiChaglAoJaBq7bGWp6bA5PAQKaOTzVHVXIlJqyQbljfmg"
    }
  ],
  "recoveryKeys": ["#recovery"],
  "keyAgreement": [
    {
      "type": "X25519KeyAgreementKey2019",
      "publicKeyBase58": "25aM2gBrRcZyK5GcGamw9QNH36D1mLxMn2GQ68twTSQr",
      "id": "#keyAgreement",
      "controller": "did:elem:EiChaglAoJaBq7bGWp6bA5PAQKaOTzVHVXIlJqyQbljfmg"
    }
  ],
  "assertionMethod": [
    "#qfknmVDhMi3Uc190IHBRfBRqMgbEEBRzWOj1E9EmzwM",
    "#primary",
    "#recovery",
    "#PiF0Sf3wDqec9_LYGO5T5-i4ihm7byhbUpoMq2nhZBg"
  ],

  "capabilityInvocation": [
    "#qfknmVDhMi3Uc190IHBRfBRqMgbEEBRzWOj1E9EmzwM",
    "#primary",
    "#recovery",
    "#PiF0Sf3wDqec9_LYGO5T5-i4ihm7byhbUpoMq2nhZBg"
  ],
  "authentication": [
    "#qfknmVDhMi3Uc190IHBRfBRqMgbEEBRzWOj1E9EmzwM",
    "#primary",
    "#recovery",
    "#PiF0Sf3wDqec9_LYGO5T5-i4ihm7byhbUpoMq2nhZBg"
  ],
  "capabilityDelegation": [
    "#qfknmVDhMi3Uc190IHBRfBRqMgbEEBRzWOj1E9EmzwM",
    "#primary",
    "#recovery",
    "#PiF0Sf3wDqec9_LYGO5T5-i4ihm7byhbUpoMq2nhZBg"
  ]
}

recoveryKeys must be defined in the sidetree json-ld context.

ION may decide to not be linked data compliant, but element will be linked data compliant, so the protocol needs to reflect best practices for linked data, or sidetree won't be usable to create linked data did methods... all you need to do is know how to document properties in json and markdown... if you can't figure out how to do that properly you have no business touching cryptography.

We need to agree on how we will document "protocol specific terms" like usage... which currently breaks document signing with linked data... making your did document not linked data is like fixing your car problem, by switching to a tricycle... not a solution for element.

@dlongley
Copy link

"usage = signing" is equivalent to assertionMethod.

I'm not sure how usage is being defined here, but if it is like Web Crypto API "KeyUsage", then the above statement is not true.

"KeyUsage" from that spec refers to the cryptographic operations that a particular key can perform, which is not the same thing as a user authorizing a verification method to be used to verify a proof that was made for a particular purpose.

For example:

Key A, with "KeyUsage" "sign", can be used to sign proofs for the purpose of authentication. A proof of this sort could be sent to a service to "log you in"/"establish a session", i.e., generally used to prove to another party that they are talking with whomever is in control of a particular key.

Key B, also with "KeyUsage" "sign", can be used to sign proofs for the purpose of assertionMethod. A proof of this sort is merely a method of making an assertion, like a set of claims about some subject, aka a Verifiable Credential, and presenting such a proof should NOT be used to "log you in"/"establish a session". It would be a problem if Alice were to give Bob a VC that says Bob is her friend and Bob could turn around and use that to log into a service as Alice -- because it is her proof on the VC.

Both keys use the "sign" cryptographic method here, but for very different purposes. Also note that both keys can mathematically (or according only to the cryptographic protocol) be used to sign proofs for either purpose. The math will work. This can be dangerous if Alice is running software that isn't sufficiently protecting her from accidentally signing the hash of a message that could be used for authentication -- when she thought it was only for making an assertion she intended to share with another party.

BUT, a DID Document allows Alice to specify which verification methods are permitted to verify proofs based on the purpose of those proofs. Alice can use her DID Document to say that the verification method associated with key A (i.e., its public key) can only be used to verify proofs for the purpose of authentication and the verification for key B can only be used to verify proofs for the purpose of assertionMethod. That way verification libraries can be written just once that will check the proofPurpose and verificationMethod Alice puts on her proofs against the authorization relations she has put in her DID Document.

If a proof says "proofPurpose": "authentication", "verificationMethod": ["did:foo:123#key"] then the verification library will only follow in the authentication relation (aka property/attribute/JSON key) in her DID Document to look for "did:foo:123#key" when verifying. If it's not there, it's not authorized to be used to verify a proof for that purpose. The same applies if the proof were to say "proofPurpose": "assertionMethod" instead; the verification library would only look under the assertionMethod relation for the verificationMethod "did:foo:123#key". This ensures that this authorization is coming from Alice (it is a relation between her and the verification method). So, note that this is not the same thing as what cryptographic operations the key can technically perform (which is a relation between the key and its cryptographic functions).

@OR13
Copy link
Contributor Author

OR13 commented Jan 27, 2020

KeyUsage

A type of operation that may be performed using a key. The recognized key usage values are "encrypt", "decrypt", "sign", "verify", "deriveKey", "deriveBits", "wrapKey" and "unwrapKey".

https://self-issued.info/docs/draft-ietf-jose-json-web-key.html#rfc.section.4.3

IMO, we should close the loop on this stuff in did-core, asap.

@OR13
Copy link
Contributor Author

OR13 commented Jan 29, 2020

See w3c/did-core#158 , we should just standardize what we are doing here in the did core spec, if possible

@OR13
Copy link
Contributor Author

OR13 commented Mar 12, 2020

Prefer:

"recoveryKey": [{
      "publicKeyJwk": {
        "crv": "secp256k1",
        "y": "EiZOvo9JWPz1yGlNNW66IV8uA44EQP_Yv_E7OZl1NG0",
        "kid": "qfknmVDhMi3Uc190IHBRfBRqMgbEEBRzWOj1E9EmzwM",
        "x": "NbASvplLIO_XTzP9R69a3MuqOO0DQw2LGnhJjirpd4w",
        "kty": "EC"
      },
      "type": "EcdsaSecp256k1VerificationKey2019",
      "id": "did:elem:EiChaglAoJaBq7bGWp6bA5PAQKaOTzVHVXIlJqyQbljfmg#qfknmVDhMi3Uc190IHBRfBRqMgbEEBRzWOj1E9EmzwM",
      "controller": "did:elem:EiChaglAoJaBq7bGWp6bA5PAQKaOTzVHVXIlJqyQbljfmg"
}]

@OR13
Copy link
Contributor Author

OR13 commented Mar 12, 2020

Related #437

@OR13
Copy link
Contributor Author

OR13 commented Mar 19, 2020

@thehenrytsai what is the format of this: https://github.com/decentralized-identity/sidetree/blob/master/lib/core/versions/latest/DocumentComposer.ts#L27

I assume its publicKeyHex DID Core Spec compliant public key?

@OR13
Copy link
Contributor Author

OR13 commented Mar 19, 2020

Like above?

@csuwildcat
Copy link
Member

csuwildcat commented Mar 25, 2020

I'd like to close this, as I don't feel it has (or ever had?) any bearing on Sidetree's internal representations. I have updated one of the possible schema options to include a mechanism of ensuring keys are output correctly, to the right places in the resolved DID Document, regardless of what the endlessly churning DID WG renames/moves the properties and values to: https://identity.foundation/sidetree/docs/spec/#add-public-keys

@csuwildcat
Copy link
Member

Sorry, had two tabs open, one local, one from the site - this is the right link: https://identity.foundation/sidetree/docs/spec/#add-public-keys

@OR13
Copy link
Contributor Author

OR13 commented Mar 26, 2020

I think we can close this... the property was removed... I just closed the did core issue that was related to this.

@OR13 OR13 closed this as completed Mar 26, 2020
@csuwildcat
Copy link
Member

To be clear: I have readded the property/mechanism to our own internal, non-DID Document key schema representation, which provides an abstraction layer that can be used to output keys anywhere in the DID Document they are needed/wanted: https://identity.foundation/sidetree/docs/spec/#add-public-keys

Thankfully implementers can now choose a path where they'll never need to quibble at a protocol-level about this class of ramifications, which stem from seemingly endless changes to a spec that churns like the sea during a hurricane. I, for one, feel at peace knowing folks who follow the optional schema-based abstraction framework defined in the Sidetree spec can shrug and say "Whatever lil' buddies, we'll always output the right doc, no matter how frequently you attempt to pull the rug out".

@OR13
Copy link
Contributor Author

OR13 commented Mar 26, 2020

Its also the case, that Microsoft will no longer introduce breaking changes into the did document, that are not documented in did core, or a custom context, as was required previously... I call this a win win.

@csuwildcat
Copy link
Member

We didn't introduce a breaking change with this prop, the devs simply tried to do something that seemed OK given the unsure state of play. Thankfully, there is no need to ever care about such nonsense again, given we can project keys and other values into publicKeys, authentication, or, if the sea-churners desire to, a renamed property called whateverIDGAF. Freedom from this class of nonsense makes me feel so much better as an implementer, but others are free to feel differently, if they choose,

@OR13
Copy link
Contributor Author

OR13 commented Mar 26, 2020

You did. we have tests that prove that you did. You need to read the did core spec.... just to be super clear... you cannot add properties to a did document that are not defined in did core, and if you do, you need to extend the context, as we did to fix the breaking change for did:elem ... "usage: signing", was a breaking change... we had multiple bug reports from interop partners from it, here are the tests to show that we had to fix it:

Screen Shot 2020-03-26 at 12 12 13 PM

https://identity.foundation/context/test-report.html

@csuwildcat
Copy link
Member

Yep, I realize that was the unintended outcome, but they were just trying to get something done that they didn't perceive the spec disallowed or provided for. My point in celebrating the closure of this issue is that we can now separate tracking of usage classifications from the nuances and shifting outputs of the DID Document, which should have always been abstracted away (at least in our opinion/approach)

@OR13
Copy link
Contributor Author

OR13 commented Mar 26, 2020

I agree, and I think its wise that sidetree core has this separation, but we must remain aware of anything in the outward representation that violates the did core spec... I am looking forward to adding support for did:ion to the did core registries, which will prove that it is compliant, and give us greater confidence, and warning about changes, that might be breaking.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
protocol Sidetree protocol change proposal Spec v1
Projects
None yet
Development

No branches or pull requests

4 participants