Skip to content

Commit

Permalink
docs: Encrypt metadata spec and types (#4176) <!-- Detail in a few bu…
Browse files Browse the repository at this point in the history
…llet points the work accomplished in this PR. Before you submit, don't forget to: CODE-OF-CONDUCT.md CONTRIBUTING.md LICENSE MAINTAINERS.md README.md cabal.project default.nix docker-compose.yml docs flake.lock flake.nix floskell.json fourmolu.yaml hie-direnv.yaml justfile lib nix prototypes reports scripts shell.nix specifications test touch.me.CI weeder.dhall Make sure the GitHub PR fields are correct: ✓ Set a good Title for your PR. ✓ Assign yourself to the PR. ✓ Assign one or more reviewer(s). ✓ Link to a Jira issue, and/or other GitHub issues or PRs. ✓ In the PR description delete any empty sections and all text commented in <!--, so that this text does not appear in merge commit messages. CODE-OF-CONDUCT.md CONTRIBUTING.md LICENSE MAINTAINERS.md README.md cabal.project default.nix docker-compose.yml docs flake.lock flake.nix floskell.json fourmolu.yaml hie-direnv.yaml justfile lib nix prototypes reports scripts shell.nix specifications test touch.me.CI weeder.dhall Don't waste reviewers' time: ✓ If it's a draft, select the Create Draft PR option. ✓ Self-review your changes to make sure nothing unexpected slipped through. CODE-OF-CONDUCT.md CONTRIBUTING.md LICENSE MAINTAINERS.md README.md cabal.project default.nix docker-compose.yml docs flake.lock flake.nix floskell.json fourmolu.yaml hie-direnv.yaml justfile lib nix prototypes reports scripts shell.nix specifications test touch.me.CI weeder.dhall Try to make your intent clear: ✓ Write a good Description that explains what this PR is meant to do. ✓ Jira will detect and link to this PR once created, but you can also link this PR in the description of the corresponding Jira ticket. ✓ Highlight what Testing you have done. ✓ Acknowledge any changes required to the Documentation. --> - [x] Adding spec and change swagger accordingly - [x] Add field `encrypt_metadata` to `ApiConstructTransactionPostData` - [x] Introduce ApiDecodeTransactionPostData` - [x] deal with all code adjustment - [x] adjust unit tests ### Issue Number ADP-322 Source commit: fd9eb91
  • Loading branch information
Cardano Wallet Documentation Bot committed Nov 16, 2023
1 parent 1d4d254 commit baa4c74
Show file tree
Hide file tree
Showing 2 changed files with 152 additions and 4 deletions.
124 changes: 124 additions & 0 deletions api/edge/metadata-encrypt.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,124 @@
# Specification: Encrypting and decrypting metadata

This document specifies those aspects of the "Transactions New > Construct" HTTP endpoint that relate to publishing of encrypted metadata.
In addition "Transactions New > Decode" HTTP endpoint is described in the context of decrypting the metadata.

## Metadata encryption

Encryption of metadata is optional and when chosen the metadata in transaction is to be encrypted
via AEAD scheme using ChaCha20 and Poly1305 (see [RFC 7539][ref]). PBKDF2 password stretching is used to get a 32-byte symmetric key
that is required for the adopted encryption algorithm. In detail, PBKDF2 encryption uses HMAC with the hash algorithm SHA512.
As a consequence the encrypted metadata, not its raw version, is going to be stored in blockchain.

[ref]: https://datatracker.ietf.org/doc/html/rfc7539

The "Transactions New > Construct" HTTP endpoint allows the encryption of metadata.
The "Transactions New > Decode" HTTP endpoint allows for decrypting of the encrypted metadata.

Specifically:

1. Creation of a transaction output that contains a metadata with encryption enabled.

In the `encrypt_metadata` field, passphrase used in encryption is established. `metadata` field to be encrypted is required.

Example `POST` data for the endpoint, ie., /wallets/{walletId}/transactions-construct`:

```
{
...
"encrypt_metadata":
{ "passphrase": "my secret encryption password"
},
"metadata": "raw metadata"
...
}
```
As a result we get transaction with metadata encrypted:
```
{
...
"metadata": "metadata encrypted"
...
}
```
The same is the case for `GET` transaction. `encrypt_metadata` is an object as we might want to introduce
optional choice of encryption method in the future. In that case the new enhancement to api will be introduced in
nonintrusive way.
Metadata encryption can be used for shared wallet style when calling `/shared-wallets/{walletId}/transactions-construct` endpoint with the same `POST` payload.
Example:
```
{
...
"encrypt_metadata":
{ "passphrase": "metadata-secret"
},
"metadata": {"1":"hello"}
...
}
```
will return
```
{
...
"metadata": {"0":"0x0aa4f9a016215f71ef007b60601708dec0d10b4ade6071b387295f95b4"}
...
}
```
Example:
```
{
...
"encrypt_metadata":
{ "passphrase": "metadata-secret"
},
"metadata":
{ "1": "Hard times create strong men."
, "2": "Strong men create good times."
, "3": "Good times create weak men."
, "4": "And, weak men create hard times."
}
...
}
```
will return
```
{
...
"metadata":
{ "0": "0x0aa4f9a016217f75f10834367493f6d7e74197417ca25c7615cae02bc345382906fb6990daf8f138b2d9192e057d0d0b555f9d5fb287abb1842928c90f26e597"
, "1": "0x559ee85f00f1588b3ee32e81dc4c84aee208a10c1eec97fffe6e0e66c69d4e0b1e3e22d7edc1618df3b20b484527d86bc3bebad4295a2ad888d034b5fec38077"
, "2": "0x8d42154f681230124c64630ea68b841aec22f0530ec830cb662d59ef423ef23d7ff3"
}
...
}
```
as metadata values have 64-byte limit. In that case the encrypted metadata is encoded in the successive bytes.
## Metadata decryption
2. Decoding transaction with encrypted metadata is possible by using the same passphrase as upon encryption in `encrypt_metadata` field. It is realized by calling `POST` on `/wallets/{walletId}/transactions-decode` endpoint with `POST` data:
```
{
"decrypt_metadata":
{ "passphrase": "my secret encryption password"
},
"transaction": ....
}
```
As a result we get decoded transaction with metadata decrypted:
```
{
...
"metadata": "raw metadata"
...
}
```
Metadata decryption can be used for shared wallet style when calling `/shared-wallets/{walletId}/transactions-decode` endpoint with the same `POST` payload.
32 changes: 28 additions & 4 deletions api/edge/swagger.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -1722,13 +1722,26 @@ x-transactionMetadata: &transactionMetadata
example:
0: "cardano"
1: 14
3: [14, 42 , "1337" ]
4: {"key1": "value" , "key2": 42 }
2: [14, 42 , "1337" ]
3: {"key1": "value" , "key2": 42 }

# Note: propertyNames pattern not supported in current OpenAPI version.
# propertyNames:
# pattern: '^[0-9]+$'

x-encryptMetadata: &encryptMetadata
description: |
If used then metadata in transaction is going to be encrypted
via AEAD scheme using ChaCha20 and Poly1305 (see RFC 7539).
PBKDF2 password stretching is used to get a 32-byte symmetric key.
PBKDF2 encryption using HMAC with the hash algorithm SHA512 is employed here.
The encrypted metadata is going to be stored in blockchain as a consequence.
type: object
required:
- passphrase
properties:
passphrase: *lenientPassphrase

x-transactionTTL: &transactionTTL
description: |
The TTL (time to live) is the time period in which the transaction
Expand Down Expand Up @@ -3506,6 +3519,16 @@ components:
<<: *walletPassphrase
description: A master passphrase to lock and protect the wallet for sensitive operation (e.g. sending funds).

ApiDecodeTransactionPostData: &ApiDecodeTransactionPostData
type: object
required:
- transaction
properties:
decrypt_metadata:
<<: *encryptMetadata
description: The metadata passphrase for decryption.
transaction: *serialisedTransactionEncoded

ApiSignTransactionPostData: &ApiSignTransactionPostData
type: object
required:
Expand Down Expand Up @@ -3671,6 +3694,7 @@ components:
payments: *ApiPaymentDestination
withdrawal: *transactionWithdrawalRequestSelf
metadata: *transactionMetadata
encrypt_metadata: *encryptMetadata
mint_burn:
type: array
items: *ApiMintBurnData
Expand Down Expand Up @@ -6651,7 +6675,7 @@ paths:
required: true
content:
application/json:
schema: *ApiSerialisedTransactionEncoded
schema: *ApiDecodeTransactionPostData
responses: *responsesDecodedTransaction

/wallets/{walletId}/transactions-submit:
Expand Down Expand Up @@ -7811,7 +7835,7 @@ paths:
required: true
content:
application/json:
schema: *ApiSerialisedTransactionEncoded
schema: *ApiDecodeTransactionPostData
responses: *responsesDecodedTransaction

/shared-wallets/{walletId}/transactions-sign:
Expand Down

0 comments on commit baa4c74

Please sign in to comment.