Skip to content

These Open SSL examples can be used for key generation and signature in non-production environments.

OpenSSL is not suitable for production environments. You always need to generate and store production keys using a cryptographically secure method (a key management system).

Key generation examples

The following examples show how to generate a key pair using the common OpenSSL toolbox.

Key generation using secp256r1 elliptic curve

To generate a key pair using the secp256r1 elliptic curve, enter the following commands:

secp256r1 private key
openssl ecparam -genkey -name secp256r1 -noout -out privateKey.pem
secp256r1 public key
openssl ec -in privateKey.pem -pubout -outform DER | openssl base64 -A -out publicKey.pem

Key generation using secp256k1 elliptic curve

To generate a key pair using the secp256k1 elliptic curve, enter the following commands:

secp256k1 private key
openssl ecparam -genkey -name secp256k1 -noout -out privateKey.pem
secp256k1 public key
openssl ec -in privateKey.pem -pubout -outform DER | openssl base64 -A -out publicKey.pem

Key generation using ED25519 elliptic curve

To generate a key pair using the ED25519 elliptic curve, enter the following commands:

ED25519 private key
openssl genpkey -algorithm Ed25519 -out privateKey.pem
ED25519 public key
openssl ec -in privateKey.pem -pubout -outform DER | openssl base64 -A -out publicKey.pem

View the output

In the previous examples, the public key is exported without the header and footer, which is the format that Ripple Custody expects.

To view the contents of the key files:

  1. To view the contents of the private key files, for each file, enter the following command:

    View private key
    cat privateKey.pem

    The output is similar to the following example:

    Private key output
    -----BEGIN EC PRIVATE KEY-----
    MHcCAQEEIEfoycax3w8+JvkNv+L0CHmNUAHUcgCxlnOIpw/CoXzxoAoGCCqGSM49
    AwEHoUQDQgAEg36xU2KQ6xLPCvZ3JXZYf5pFCagAb7WGMlYCN92zzgi737EOkDOC
    MlZB0TY8CbzRHhG4RUdKuLkdRtD+OVIu2w==
    -----END EC PRIVATE KEY-----
  2. To view the contents of the public key files, for each file, enter the following command:

    View public key
    cat publicKey.pem

    The output is similar to the following example:

    Public key output
    MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEg36xU2KQ6xLPCvZ3JXZYf5pFCagAb7WGMlYCN92zzgi737EOkDOCMlZB0TY8CbzRHhG4RUdKuLkdRtD+OVIu2w==

Signature examples

The following examples show how to:

  • Sign a challenge to obtain a JSON web token (JWT)
  • Submit an intent

Sign a challenge to obtain a JWT

This example shows how to sign a challenge. These steps generate the output that you need to obtain a JWT for authentication in Ripple Custody.

For more information about JWT generation, see Obtain a JSON web token (JWT) in the API guide.

To generate the signature:

  1. Prepare a random string to use as a challenge, for example a UUID, in a text file called challenge.txt:

    Prepare the challenge string
    user@HOSTNAME:~/test$ cat challenge.txt
    22ff6b83-784c-46ab-8514-096c3c2b93ff
  2. Sign the challenge with the secp256r1, secp256k1, or ED25519 elliptic curve.

    • To sign the challenge with secp256r1 or secp256k1, enter the following command:

      Signature with secp256r1 or secp256k1
      openssl dgst -sha256 -sign privateKey.pem challenge.txt | base64

      The output of the signature operation is in raw format, which we converted to Base64, to give an output similar to the following example:

      Output of secp256r1 or secp256k1
      MEQCIGtDBRAdRgUn9kT3olUGBmQbzEwQ2wQr8Ucevu6uwDmXAiB+OISmprOU7TwI0XUnyNuNQpBpyze9fnaLTp5LxZuJ/Q==
    • To sign the challenge with ED25519:

      1. Enter the following command:

        Signature with ED25519
        openssl pkeyutl -sign -inkey privateKey.pem  -rawin -in challenge.txt -out sig.dat

        Because the signature output of ED25519 is in compact format, we must first convert it to DER format.

      2. Convert the compact signature to DER format, and then encode it in Base64, with the one of the following commands:

        Signature conversion to DER and Base64
        cat sig.dat | hexdump -v -e '/1 "%02x"' | sed 's/\(.\{64\}\)\(.\{64\}\)/30440220\10220\2/g' | xxd -r -p | base64 -w0

        The output is similar to the following example:

        Output of ED25519 after conversion
        MEQCICVs3TeU6DsaKc/DC3Y4VerQjiy/Sm4Prfyoh4yFKj1TAiBPu6/c5rxNxCU5Gl2NZH+orCUHKGFTAxcrDxRQqTYSBA==

        You can submit this output to Ripple Custody to obtain a JWT. For more information, see Obtain a token.

Sign a payload for intent submission

This example shows how to sign a payload before you submit an intent to create or update system data. For more information, see Sign intents.

To sign a payload for intent submission:

  1. Save the following example in a JSON file named v0_CreateAccount.json:

    Example account creation intent in JSON format
    {
        "author":{  
            "id":"e02f08ce-e515-46fa-9ed3-326179a1de89",
            "domainId":"789265d6-aea6-4c7b-9d68-1a532ea3060b"
        },
        "expiryAt":"2024-08-24T14:15:22Z",
        "targetDomainId":"789265d6-aea6-4c7b-9d68-1a532ea3060b",
        "id":"1b96fd0f-4e50-4782-9fae-ff0fce7f982c",
        "payload":{
            "id":"9dbc612f-b98a-4c83-8143-9d33e1865127",
            "alias":"OpenSSL Test Account 1",
            "providerDetails":{
                "vaultId":"00000000-0000-0000-0000-000000000000",
                "keyStrategy":"VaultHard",
                "type":"Vault"
            },
            "ledgerIds":["bitcoin-cash-testnet"],
            "lock":"Unlocked",
            "customProperties":{},
            "type":"v0_CreateAccount"
        },
        "description":"OpenSSL Creation of Test Account 1",
        "customProperties":{},
        "type":"Propose"
    }
  2. Sort the JSON payload, with the following command:

    Sort the payload file
    cat v0_CreateAccount.json | jq -j -S -c > v0_CreateAccount_Sorted.json

    The following example shows the output of the sorted JSON file:

    Sorted payload output
    {"author":{"domainId":"777265d6-aea6-4c7b-9d68-1a532ea3060b","id":"e02f08ce-e515-46fa-9ed3-326179a1de77"},"customProperties":{},"description":"OpenSSL Creation of Test Account 1","expiryAt":"2024-08-24T14:15:22Z","id":"1b95fd0f-4e50-4782-9fae-ff0fce7f982c","payload":{"alias":"OpenSSL Test Account 2","customProperties":{},"id":"9cbc612f-b98a-4c83-8143-9d33e1865127","ledgerIds":["bitcoin-cash-testnet"],"lock":"Unlocked","providerDetails":{"keyStrategy":"VaultHard","type":"Vault","vaultId":"00000000-0000-0000-0000-000000000000"},"type":"v0_CreateAccount"},"targetDomainId":"777265d6-aea6-4c7b-9d68-1a532ea3060b","type":"Propose"}
  3. Sign the payload using secp256r1, secp256k1, or ED25519.

    • To sign using secp256r1 or secp256k1, enter one of the following commands:
    Payload signature using secp256r1 or secp256k1
    openssl dgst -sha256 -sign privateKey.pem v0_CreateAccount_Sorted.json | base64 -w0
    • To sign using ED25519, enter one of the following commands:
    Payload signature using ED25519
    tmp=$(mktemp)
    cat v0_CreateAccount_Sorted.json | sha256sum | xxd -r -p > ${tmp}
    openssl pkeyutl -sign -inkey privateKey.pem -rawin -in ${tmp} | hexdump -v -e '/1 "%02x"' | sed 's/\(.\{64\}\)\(.\{64\}\)/30440220\10220\2/g' | xxd -r -p | base64 -w0
    rm -f ${tmp}

Check the signature returned by Ripple Custody

All data payloads that you retrieve from Ripple Custody that are part of the secure data include a signature. To verify the authenticity of this signature, we highly recommend that you run a verification step.

To check the signature:

  1. Retrieve the public key of Ripple Custody, with the List system properties API operation.

    The API operation returns the public key as part of the response:

    Custody public key
    {
        "id": "CUSTODY_API_KEY",
        "value": {
            "publicKey": {
                "value": "MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAE1WXjDbBcWEVmqObzEndfnug+nd4EOEqcXMY5a5I0XvfRq1+K6Z9K1DdZ2YgFIbuzdX2Z2kOfE/fcDj/QzF5IAw==",
                "type": "PublicKey"
            }
        }
    }
  2. Save the public key value into a text file, together with a header and footer, in the following format:

    Formatted public key file
    CustodypublicKey.pem
    -----BEGIN PUBLIC KEY-----
    MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAE1WXjDbBcWEVmqObzEndfnug+nd4EOEqcXMY5a5I0XvfRq1+K6Z9K1DdZ2YgFIbuzdX2Z2kOfE/fcDj/zF5IAw==
    -----END PUBLIC KEY-----
  3. Prepare the signature string. OpenSSL expects the signature in raw format, so the signature string received needs to be converted using the following command:

    Signature conversion to raw format
    openssl enc -d -A -base64 -in signatureByHarmonize.txt -out signatureByHarmonize.bin
  4. Sort the result, using a command similar to step 2 of Sign a payload for intent submission.

  5. Once you have the sorted object, the Ripple Custody public key, and the signature in binary format, to verify the data, run the following command:

    Data verification
    openssl pkeyutl -verify -pubin -inkey CustodypublicKey.pem -rawin -in Sorted_Object.json -sigfile signatureByHarmonize.bin

If the signature is valid, Ripple Custody returns the following message: Signature Verified Successfully