Skip to content

Commit

Permalink
fix(node/crypto): support promisify on generateKeyPair (denoland#26913)
Browse files Browse the repository at this point in the history
Calling `promisify(generateKeyPair)` didn't work as expected. It
requires a custom promisify implementation.

This was easy to fix thanks to the excellent debugging investigation in
denoland#26910

Fixes denoland#26910

Co-authored-by: Bartek Iwańczuk <[email protected]>
  • Loading branch information
marvinhagemeister and bartlomieju authored Nov 19, 2024
1 parent 594a998 commit df1d363
Show file tree
Hide file tree
Showing 2 changed files with 39 additions and 4 deletions.
20 changes: 16 additions & 4 deletions ext/node/polyfills/internal/crypto/keygen.ts
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ import {
import { Buffer } from "node:buffer";
import { KeyFormat, KeyType } from "ext:deno_node/internal/crypto/types.ts";
import process from "node:process";
import { promisify } from "node:util";

import {
op_node_generate_dh_group_key,
Expand Down Expand Up @@ -570,7 +571,15 @@ export function generateKeyPair(
privateKey: any,
) => void,
) {
createJob(kAsync, type, options).then((pair) => {
_generateKeyPair(type, options)
.then(
(res) => callback(null, res.publicKey, res.privateKey),
(err) => callback(err, null, null),
);
}

function _generateKeyPair(type: string, options: unknown) {
return createJob(kAsync, type, options).then((pair) => {
const privateKeyHandle = op_node_get_private_key_from_pair(pair);
const publicKeyHandle = op_node_get_public_key_from_pair(pair);

Expand All @@ -589,12 +598,15 @@ export function generateKeyPair(
}
}

callback(null, publicKey, privateKey);
}).catch((err) => {
callback(err, null, null);
return { publicKey, privateKey };
});
}

Object.defineProperty(generateKeyPair, promisify.custom, {
enumerable: false,
value: _generateKeyPair,
});

export interface KeyPairKeyObjectResult {
publicKey: KeyObject;
privateKey: KeyObject;
Expand Down
23 changes: 23 additions & 0 deletions tests/unit_node/crypto/crypto_key_test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -677,3 +677,26 @@ Deno.test("generateKeyPair large pem", function () {
},
});
});

Deno.test("generateKeyPair promisify", async () => {
const passphrase = "mypassphrase";
const cipher = "aes-256-cbc";
const modulusLength = 4096;

const { privateKey, publicKey } = await promisify(generateKeyPair)("rsa", {
modulusLength,
publicKeyEncoding: {
type: "spki",
format: "pem",
},
privateKeyEncoding: {
type: "pkcs8",
format: "pem",
cipher,
passphrase,
},
});

assert(publicKey.startsWith("-----BEGIN PUBLIC KEY-----"));
assert(privateKey.startsWith("-----BEGIN PRIVATE KEY-----"));
});

0 comments on commit df1d363

Please sign in to comment.