私はこの問題をどのように解決するのだろうと思っていました。WebCrypto API を使用して RSA-OAEP キーペアを生成し、ArrayBuffer としてエクスポートするキーペアから pkcs8 の秘密キーをエクスポートし、この ArrayBuffer を base64 にエンコードして、PEM として保存できるようにします。
このテスト例では、鍵を pkcs8 としてエクスポートし、この pkcs8 を CryptoKey にインポートしています。問題は、機能する場合と機能しない場合があることです。
これらはコードの結果です: 注: これらの状態の 1 つだけが一度に発生するわけではありません。注 2: この例には、-----BEGIN PRIVATE KEY----- プレフィックスとサフィックスは含まれていません。キーのみをエンコードしています。
Case1: Uncaught (in promise) URIError: 不正な URI (…)b64DecodeUnicode @ try.php:20b64toab @ try.php:70wayBack @ try.php:66(anonymous function) @ try.php:56
Case2: undefined:1 Uncaught (in promise) DOMException
ケース 3: OK - ずっと機能します。
エラーの原因はわかりませんが、base64 エンコーディングと関係があると思います。私が言ったように、秘密鍵がOKを生成する場合とそうでない場合があります。
事前にご協力いただき、誠にありがとうございました。
function b64EncodeUnicode(str) {
return btoa(encodeURIComponent(str).replace(/%([0-9A-F]{2})/g, function(match, p1) {
return String.fromCharCode('0x' + p1);
}));
}
function b64DecodeUnicode(str) {
return decodeURIComponent(Array.prototype.map.call(atob(str), function(c) {
return '%' + ('00' + c.charCodeAt(0).toString(16)).slice(-2);
}).join(''));
}
function addNewLines(str) {
var finalString = '';
for(var i=0; i < str.length; i++) {
finalString += str.substring(0, 64) + '\n';
str = str.substring(64);
}
return finalString;
}
window.crypto.subtle.generateKey(
{
name: "RSA-OAEP",
modulusLength: 2048,
publicExponent: new Uint8Array([0x01, 0x00, 0x01]),
hash: {name: "SHA-256"}
},
true,
["encrypt", "decrypt"]
).then(function(keyPair) {
window.crypto.subtle.exportKey(
"pkcs8",
keyPair.privateKey
).then(function(exportedPrivateKey) {
var byteArray = new Uint8Array(exportedPrivateKey);
console.log(byteArray);
var byteString = '';
for(var i=0; i < byteArray.byteLength; i++) {
byteString += String.fromCodePoint(byteArray[i]);
}
wayBack(addNewLines(b64EncodeUnicode(byteString)));
});
});
function wayBack(pem) {
var lines = pem.split('\n');
var encodedString = '';
for(var i=0; i < lines.length; i++) {
encodedString += lines[i].trim();
}
b64toab(encodedString);
}
function b64toab(b64) {
var byteString = b64DecodeUnicode(b64);
console.log(byteString);
var byteArray = new Uint8Array(byteString.length);
for(var i=0; i < byteString.length; i++) {
byteArray[i] = byteString.codePointAt(i);
}
console.log(byteArray);
window.crypto.subtle.importKey(
"pkcs8",
byteArray,
{
name: "RSA-OAEP",
hash: {name: "SHA-256"}
},
true,
["decrypt"]
).then(function(importedPrivateKey) {
console.log(importedPrivateKey);
});
}