0
votes

I'm trying to generate a private key and public key pair. I want to use the private key to sign my JWT and send the public key to a 3rd party to decode my JWT.

On my mac os terminal, I generated my keys like this:

ssh-keygen -m PEM -t rsa -b 2048

Do now I've pkey & pkey.pub as private and public keys respectively. Now in my rails console I tried to get the private key like this, which works fine:

rsa_private = OpenSSL::PKey::RSA.new(File.read("/path/to/private/key/pkey"))

rsa_private.to_s
"-----BEGIN RSA PRIVATE KEY-----\nCONTENTS_OF_PKEY_FILE\n-----END RSA PRIVATE KEY-----\n"

Now in rails, I can get the public key from generated private key like this :

pub_key = rsa_private.public_key

But when I try to print it's contents, it differs from what's there in pkey.pub generated when I ran ssh-keygen command.

pub_key looks something like this:

"-----BEGIN PUBLIC KEY-----\nSOME_CONTENT\n-----END PUBLIC KEY-----\n"

But my pkey.pub file looks different, something like this:

ssh-rsa SOME_OTHER_CONTENT [email protected]

So, my question, is how can I get 2 different public keys for same private key? Which one do I use to decode my JWT?

1

1 Answers

0
votes

Keys should be the same, but are encoded differently.

An RSA key pair consists of several numbers, private key is all these data, public key is the same with private part deleted.

Numbers can be written in different order, encoded in different formats. Also keys can be encrypted for storage with a password(not this case). Thus files with the same keys can look absolutely different.

PEM-format (the one with BEGIN PUBLIC KEY and Base64 data) is more common for generic keys, so better use it.

Update: PEM format is base64 encoded DER with header and footer. DER in its turn is binary representation of ASN.1. But SSH uses a dirrerent key encoding format (RFC4716)

Example:

% ssh-keygen -m PEM -t rsa -N '' -b 1024 -f ./rsa

% cat rsa.pub
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAgQDRNFYxsULk6x90T0EE8iS3skfJJ407ef3WJJClre0k2sLJUJX6/Xbc3ObxNjixXcgIXp2H4oVOnNpujqFF/XM81zlpLjGT/4igtK1FjIHIaFyRheGuwplgwCkXlxAe/oH1Bb4nFXlD/kORmGgSfSE9BpH+HQU3IzyU1i0X9K828Q== [email protected]

% ssh-keygen -e -m PEM -f ./rsa.pub
-----BEGIN RSA PUBLIC KEY-----
MIGJAoGBANE0VjGxQuTrH3RPQQTyJLeyR8knjTt5/dYkkKWt7STawslQlfr9dtzc
5vE2OLFdyAhenYfihU6c2m6OoUX9czzXOWkuMZP/iKC0rUWMgchoXJGF4a7CmWDA
KReXEB7+gfUFvicVeUP+Q5GYaBJ9IT0Gkf4dBTcjPJTWLRf0rzbxAgMBAAE=
-----END RSA PUBLIC KEY-----

% ssh-keygen -e -m PKCS8 -f ./rsa.pub
-----BEGIN PUBLIC KEY-----
MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDRNFYxsULk6x90T0EE8iS3skfJ
J407ef3WJJClre0k2sLJUJX6/Xbc3ObxNjixXcgIXp2H4oVOnNpujqFF/XM81zlp
LjGT/4igtK1FjIHIaFyRheGuwplgwCkXlxAe/oH1Bb4nFXlD/kORmGgSfSE9BpH+
HQU3IzyU1i0X9K828QIDAQAB
-----END PUBLIC KEY-----

Above is 3 different encodings of the same key, here are ASN-decoded versions of the latter two (via https://lapo.it/asn1js):

PEM, the bare minimum (modulus and exponent, no metadata):

SEQUENCE (2 elem)
  INTEGER (1024 bit) 146908353891476107599563957703741990254320034409224509383359005248419…
  INTEGER 65537

PKCS8, here we see the exact same numbers, but this time with some metadata:

SEQUENCE (2 elem)
  SEQUENCE (2 elem)
    OBJECT IDENTIFIER 1.2.840.113549.1.1.1 rsaEncryption (PKCS #1)
    NULL
  BIT STRING (1 elem)
    SEQUENCE (2 elem)
      INTEGER (1024 bit) 146908353891476107599563957703741990254320034409224509383359005248419…
      INTEGER 65537