scala-js/scala-js-dom

generateKey API not flexible enough

bblfish opened this issue · 3 comments

The crypto api mapping is not general enough. The definition I see is:

def generateKey(algorithm: String, extractable: Boolean,
      keyUsages: js.Array[String]): Promise[js.Any] = js.native

the algorithm seems to also potentially be an object according to this blog post where the example code is

window.crypto.subtle.generateKey(
            {
                name: "RSASSA-PKCS1-v1_5",
                modulusLength: 2048,
                publicExponent: new Uint8Array([1, 0, 1]),
                hash: {name: "SHA-256"}
            },
            true,   // Must extract private key to create PEM files later
            ["sign", "verify"]).

It's actually not that easy to read these JS specs, and WebCrypto API is not exceptions. Still the definition there is

Promise<any> generateKey(AlgorithmIdentifier algorithm,
                          boolean extractable,
                          sequence<KeyUsage> keyUsages );

One thing that one could do is make algorithms typesafe, as for example I have been trying with the Fetch API.

Here things may be a bit different. I was thinking in this case algorithms for example could not be sealed traits, but it seems according to this stackoverflow article that it is not actually possible to discover supported algorithms in the browser. Still I suppose developers could integrate libraries that support them and ship those with the code....

When I initially PR'd the web crypto api, @sjrd suggested that we could use path dependent types to actually provide accurate types for all the promises, so I think it might be worth mapping out the various routes through the api. I believe we can produce accurate typing for the known algorithms, with a fallback to Promise[Any] when the user uses something we've not seen before. (And actually it's kind of a neat demo of what's possible with the Scala type system). I didn't do it at the time and have regretted it ever since :)

That sounds like a good idea. The above changes get me far enough to continue programming my implementation of http-signatures