Zaubrik / djwt

Create and verify JSON Web Tokens (JWT) with Deno or the browser.
MIT License
228 stars 23 forks source link

There's no permanent key available. #60

Closed Scionax closed 3 years ago

Scionax commented 3 years ago

Every tutorial on djwt uses the secret_key as a string that was on your older versions. Now you use the crypto.subtle.generateKey() instead. But Deno doesn't have an export for that key (i.e. crypto.subtle.export() is not available), so there's no way that I'm aware of to actually persist the key.

Can you make a permanent key option available again, or clarify in the example how this is done? As the example stands, this would invalidate all cookies if the server reset.

matthewp commented 3 years ago

You can use exportKey to export your key to a file and then import it with importKey: https://developer.mozilla.org/en-US/docs/Web/API/SubtleCrypto/exportKey

Only raw is supported right now (but jwk just landed in a PR).


const key = await crypto.subtle.generateKey(
  { name: "HMAC", hash: "SHA-512" },
  true,
  ["sign", "verify"],
);

let result = await crypto.subtle.exportKey('raw', key);
let data = new Uint8Array(result);
Deno.writeFile('mysite.key', data);
Scionax commented 3 years ago

I'll check more into this later when I'm back on that set of code, but just pasting it quickly into VSCode appears to show no issues. It seems like this will probably work. Thank you :)

Scionax commented 3 years ago

Actually, after going back and running the full test, it was the original issue I'd mentioned.

Yes, that works fine in JS. Deno does not have the ability. The crypto.subtle.exportKey('raw', key) line gives me an error under the exportKey: Property 'exportKey' does not exist on type 'SubtleCrypto'.deno-ts(2339)

authcompanion commented 3 years ago

@Scionax Did you find a solution to persist a key once it's generated? I'm in the same boat.

Scionax commented 3 years ago

Nope. The code posted was basically identical to what I'd originally tried on my own, but straight up just doesn't work in Deno.

timonson commented 3 years ago

I added an example for generating, exporting and importing a key in pkcs8 format here.

littledivy commented 3 years ago

@Scionax Deno ~1.13~ 1.14 added support for exporting HMAC/RSA keys. This code snippet works now.

timonson commented 3 years ago

@littledivy meant Deno 1.14 :)

authcompanion commented 3 years ago

Thanks @littledivy for the web crypto api implementations and updates in 1.14. This is a game changer for Deno. Thanks too @timonson for the provided examples!!

Scionax commented 3 years ago

Awesome! Thank you littledivy. I have mostly good news. The code snippet works, although it was briefly wonky with the "window." for some reason. I changed it toawait crypto.subtle.generateKey and it worked fine, but then changing it back to window.crypto.subtle worked fine as well... no idea what voodoo happened there.

The snippet does give me two typing errors with crypto.subtle.exportKey(), since the first parameter is set to format: "raw", and therefore anything but "raw" (e.g. "pkcs8") shows a TypeScript error. However, Deno itself processes it fine.

Looks like this issue can be closed. Thanks again.

tomekrozalski commented 3 years ago

@Scionax I still do not understand why we cannot use string as secret key. I assume that it is something with security. Alright, but what if I want to install the library just for testing purposes? This generateKey, exportKey etc. flow is much more complex, isn't it? I real life I believe most of developers will choose just older version with secret token as a string.

ralyodio commented 3 years ago

How do I import the key to be used from this example to export it?

const key = await crypto.subtle.generateKey(
  { name: "HMAC", hash: "SHA-512" },
  true,
  ["sign", "verify"],
);

let result = await crypto.subtle.exportKey('raw', key);
let data = new Uint8Array(result);
Deno.writeFile('mysite.key', data);

That writes it out, but now how to do I import it for use with djwt?

timonson commented 3 years ago

Did you take a look at the example I posted in this issue? The best way would be to use the importKey method: https://developer.mozilla.org/en-US/docs/Web/API/SubtleCrypto/importKey