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

Generate a JWT with a RSA signature #166

Open
stephane-ein opened this issue Sep 3, 2020 · 2 comments
Open

Generate a JWT with a RSA signature #166

stephane-ein opened this issue Sep 3, 2020 · 2 comments

Comments

@stephane-ein
Copy link

stephane-ein commented Sep 3, 2020

Hello,

I would like to generate a JWT with a RSA signature and I try to do the following :

let private_key = "-----BEGIN PRIVATE KEY-----\nMIIjioNDS78DsqqpCnWsI@9122 ... WA==-----END PRIVATE KEY-----"
let signing_secret = Secret::bytes_from_str(private_key.as_str());

let expected_claims = ClaimsSet::<CreateSessionClaims> {
    registered: RegisteredClaims {
        ..Default::default()
    }
};

let expected_jwt = JWT::new_decoded(From::from(
    RegisteredHeader {
        algorithm: SignatureAlgorithm::RS256,
        ..Default::default()
    }),expected_claims.clone());

let token = expected_jwt.into_encoded(&signing_secret).unwrap();
let token = token.unwrap_encoded().to_string();

But I got the following error :

GenericError("Invalid secret type. A RsaKeyPair is required")

I looked through the documentation and the code and it seems we cannot generate a secret from a RSA string value but only from a file (with rsa_keypair_from_file) or from jwk::RSAKeyParameters.

Is there a way to generate an encoding key with RSA like this library https://github.com/Keats/jsonwebtoken ?

let private_key = "-----BEGIN PRIVATE KEY-----\nMIIjioNDS78DsqqpCnWsI@9122 ... WA==-----END PRIVATE KEY-----"
let token = encode(&Header::new(Algorithm::RS256), &my_claims, &EncodingKey::from_rsa_pem(private_key.to_string()))?)?;

Regards

@JadedEvan
Copy link

JadedEvan commented Jan 9, 2021

@stephane-ein I was looking at the issue that you opened in the firestore-db-and-auth repository. Is this still an issue with recent changes to this crate? Digging into the code it as thought it now supports reading from a string value.

Scratch my earlier comment. I think I've figured out that there is something wrong in the example that you've shared above. It would appear that the RSA private key that you're using in the example is not a DER encoded private key. The jsonwebtoken crate requires that you use DER format. Any JWT that uses the RS256 signature is going to require a key pair, not an individual file.

I'm able to get around the error you've received above by using the Secret::rsa_keypair_from_file method. A few changes are required to the dummy code to get this working:

#[derive(Debug, PartialEq, Clone, Serialize, Deserialize)]
struct PrivateClaims {
    company: String,
    department: String,
}

let signing_secret = biscuit::jws::Secret::rsa_keypair_from_file(path).unwrap();

let expected_claims = ClaimsSet::<PrivateClaims> {
    registered: biscuit::RegisteredClaims {
        ..Default::default()
    },
    private: PrivateClaims {
        company: "company".to_string(),
        department: "department".to_string()
    }
};

let expected_jwt = JWT::new_decoded(From::from(
    biscuit::jws::RegisteredHeader {
        algorithm: biscuit::jwa::SignatureAlgorithm::RS256,
        ..Default::default()
    }),expected_claims.clone());


let token = expected_jwt.into_encoded(&signing_secret).unwrap();
let token = token.unwrap_encoded().to_string();

@jbg
Copy link

jbg commented Jun 30, 2022

Note that if you have a PEM string as in @stephane-ein's code, you can strip the first and last lines (-----BEGIN PRIVATE KEY----- and -----END PRIVATE KEY-----) and base64-decode to get DER.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants