v1.3.0: integrate node v6 support (rsa-compat backport)
This commit is contained in:
		
							parent
							
								
									adc8eaec85
								
							
						
					
					
						commit
						1c67c47131
					
				
							
								
								
									
										2
									
								
								index.js
									
									
									
									
									
								
							
							
						
						
									
										2
									
								
								index.js
									
									
									
									
									
								
							@ -1,2 +1,2 @@
 | 
			
		||||
'use strict';
 | 
			
		||||
module.exports = require('./lib/rasha.js');
 | 
			
		||||
module.exports = require('./lib/rsa.js');
 | 
			
		||||
 | 
			
		||||
							
								
								
									
										51
									
								
								lib/crypto.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										51
									
								
								lib/crypto.js
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,51 @@
 | 
			
		||||
'use strict';
 | 
			
		||||
/*global Promise*/
 | 
			
		||||
 | 
			
		||||
var PEM = require('./pem.js');
 | 
			
		||||
var x509 = require('./x509.js');
 | 
			
		||||
var ASN1 = require('./asn1.js');
 | 
			
		||||
 | 
			
		||||
// Hacky-do, wrappy-do
 | 
			
		||||
module.exports.generate = function (opts) {
 | 
			
		||||
  if (!opts) { opts = {}; }
 | 
			
		||||
  return new Promise(function (resolve, reject) {
 | 
			
		||||
    try {
 | 
			
		||||
      var modlen = opts.modulusLength || 2048;
 | 
			
		||||
      var exp = opts.publicExponent || 0x10001;
 | 
			
		||||
      var pair = require('./generate-privkey.js')(modlen,exp);
 | 
			
		||||
      if (pair.private) { resolve(pair); return; }
 | 
			
		||||
      pair = toJwks(pair);
 | 
			
		||||
      resolve({ private: pair.private , public: pair.public });
 | 
			
		||||
    } catch(e) {
 | 
			
		||||
      reject(e);
 | 
			
		||||
    }
 | 
			
		||||
  });
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
// PKCS1 to JWK only
 | 
			
		||||
function toJwks(oldpair) {
 | 
			
		||||
  var block = PEM.parseBlock(oldpair.privateKeyPem);
 | 
			
		||||
  var asn1 = ASN1.parse(block.bytes);
 | 
			
		||||
  var jwk = { kty: 'RSA', n: null, e: null };
 | 
			
		||||
  jwk = x509.parsePkcs1(block.bytes, asn1, jwk);
 | 
			
		||||
  return { private: jwk, public: neuter(jwk) };
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Copied from rsa.js to prevent circular dep
 | 
			
		||||
var privates = [ 'p', 'q', 'd', 'dp', 'dq', 'qi' ];
 | 
			
		||||
function neuter(priv) {
 | 
			
		||||
  var pub = {};
 | 
			
		||||
  Object.keys(priv).forEach(function (key) {
 | 
			
		||||
    if (!privates.includes(key)) {
 | 
			
		||||
      pub[key] = priv[key];
 | 
			
		||||
    }
 | 
			
		||||
  });
 | 
			
		||||
  return pub;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
if (require.main === module) {
 | 
			
		||||
  module.exports.generate().then(function (pair) {
 | 
			
		||||
    console.info(JSON.stringify(pair.private, null, 2));
 | 
			
		||||
    console.info(JSON.stringify(pair.public, null, 2));
 | 
			
		||||
  });
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										53
									
								
								lib/generate-privkey-forge.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										53
									
								
								lib/generate-privkey-forge.js
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,53 @@
 | 
			
		||||
// Copyright 2016-2018 AJ ONeal. All rights reserved
 | 
			
		||||
/* This Source Code Form is subject to the terms of the Mozilla Public
 | 
			
		||||
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 | 
			
		||||
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 | 
			
		||||
'use strict';
 | 
			
		||||
 | 
			
		||||
module.exports = function (bitlen, exp) {
 | 
			
		||||
  var k = require('node-forge').pki.rsa
 | 
			
		||||
    .generateKeyPair({ bits: bitlen || 2048, e: exp || 0x10001 }).privateKey;
 | 
			
		||||
  var jwk = {
 | 
			
		||||
    kty: "RSA"
 | 
			
		||||
  , n: _toUrlBase64(k.n)
 | 
			
		||||
  , e: _toUrlBase64(k.e)
 | 
			
		||||
  , d: _toUrlBase64(k.d)
 | 
			
		||||
  , p: _toUrlBase64(k.p)
 | 
			
		||||
  , q: _toUrlBase64(k.q)
 | 
			
		||||
  , dp: _toUrlBase64(k.dP)
 | 
			
		||||
  , dq: _toUrlBase64(k.dQ)
 | 
			
		||||
  , qi: _toUrlBase64(k.qInv)
 | 
			
		||||
  };
 | 
			
		||||
  return {
 | 
			
		||||
    private: jwk
 | 
			
		||||
  , public: {
 | 
			
		||||
      kty: jwk.kty
 | 
			
		||||
    , n: jwk.n
 | 
			
		||||
    , e: jwk.e
 | 
			
		||||
    }
 | 
			
		||||
  };
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
function _toUrlBase64(fbn) {
 | 
			
		||||
  var hex = fbn.toRadix(16);
 | 
			
		||||
  if (hex.length % 2) {
 | 
			
		||||
    // Invalid hex string
 | 
			
		||||
    hex = '0' + hex;
 | 
			
		||||
  }
 | 
			
		||||
  while ('00' === hex.slice(0, 2)) {
 | 
			
		||||
    hex = hex.slice(2);
 | 
			
		||||
  }
 | 
			
		||||
  return Buffer.from(hex, 'hex').toString('base64')
 | 
			
		||||
    .replace(/\+/g, "-")
 | 
			
		||||
    .replace(/\//g, "_")
 | 
			
		||||
    .replace(/=/g,"")
 | 
			
		||||
  ;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
if (require.main === module) {
 | 
			
		||||
  var keypair = module.exports(2048, 0x10001);
 | 
			
		||||
  console.info(keypair.private);
 | 
			
		||||
  console.warn(keypair.public);
 | 
			
		||||
  //console.info(keypair.privateKeyJwk);
 | 
			
		||||
  //console.warn(keypair.publicKeyJwk);
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										26
									
								
								lib/generate-privkey-node.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										26
									
								
								lib/generate-privkey-node.js
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,26 @@
 | 
			
		||||
// Copyright 2016-2018 AJ ONeal. All rights reserved
 | 
			
		||||
/* This Source Code Form is subject to the terms of the Mozilla Public
 | 
			
		||||
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 | 
			
		||||
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 | 
			
		||||
'use strict';
 | 
			
		||||
 | 
			
		||||
module.exports = function (bitlen, exp) {
 | 
			
		||||
  var keypair = require('crypto').generateKeyPairSync(
 | 
			
		||||
    'rsa'
 | 
			
		||||
  , { modulusLength: bitlen
 | 
			
		||||
    , publicExponent: exp
 | 
			
		||||
    , privateKeyEncoding: { type: 'pkcs1', format: 'pem' }
 | 
			
		||||
    , publicKeyEncoding: { type: 'pkcs1', format: 'pem' }
 | 
			
		||||
    }
 | 
			
		||||
  );
 | 
			
		||||
  var result = { privateKeyPem: keypair.privateKey.trim() };
 | 
			
		||||
  return result;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
if (require.main === module) {
 | 
			
		||||
  var keypair = module.exports(2048, 0x10001);
 | 
			
		||||
  console.info(keypair.privateKeyPem);
 | 
			
		||||
  console.warn(keypair.publicKeyPem);
 | 
			
		||||
  //console.info(keypair.privateKeyJwk);
 | 
			
		||||
  //console.warn(keypair.publicKeyJwk);
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										25
									
								
								lib/generate-privkey-ursa.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										25
									
								
								lib/generate-privkey-ursa.js
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,25 @@
 | 
			
		||||
// Copyright 2016-2018 AJ ONeal. All rights reserved
 | 
			
		||||
/* This Source Code Form is subject to the terms of the Mozilla Public
 | 
			
		||||
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 | 
			
		||||
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 | 
			
		||||
'use strict';
 | 
			
		||||
 | 
			
		||||
module.exports = function (bitlen, exp) {
 | 
			
		||||
  var ursa;
 | 
			
		||||
  try {
 | 
			
		||||
    ursa = require('ursa');
 | 
			
		||||
  } catch(e) {
 | 
			
		||||
    ursa = require('ursa-optional');
 | 
			
		||||
  }
 | 
			
		||||
  var keypair = ursa.generatePrivateKey(bitlen, exp);
 | 
			
		||||
  var result = { privateKeyPem: keypair.toPrivatePem().toString('ascii').trim() };
 | 
			
		||||
  return result;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
if (require.main === module) {
 | 
			
		||||
  var keypair = module.exports(2048, 0x10001);
 | 
			
		||||
  console.info(keypair.privateKeyPem);
 | 
			
		||||
  console.warn(keypair.publicKeyPem);
 | 
			
		||||
  //console.info(keypair.privateKeyJwk);
 | 
			
		||||
  //console.warn(keypair.publicKeyJwk);
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										67
									
								
								lib/generate-privkey.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										67
									
								
								lib/generate-privkey.js
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,67 @@
 | 
			
		||||
// Copyright 2016-2018 AJ ONeal. All rights reserved
 | 
			
		||||
/* This Source Code Form is subject to the terms of the Mozilla Public
 | 
			
		||||
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 | 
			
		||||
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 | 
			
		||||
'use strict';
 | 
			
		||||
 | 
			
		||||
var oldver = false;
 | 
			
		||||
 | 
			
		||||
module.exports = function (bitlen, exp) {
 | 
			
		||||
  bitlen = parseInt(bitlen, 10) || 2048;
 | 
			
		||||
  exp = parseInt(exp, 10) || 65537;
 | 
			
		||||
 | 
			
		||||
  try {
 | 
			
		||||
    return require('./generate-privkey-node.js')(bitlen, exp);
 | 
			
		||||
  } catch(e) {
 | 
			
		||||
    if (!/generateKeyPairSync is not a function/.test(e.message)) {
 | 
			
		||||
      throw e;
 | 
			
		||||
    }
 | 
			
		||||
    try {
 | 
			
		||||
      return require('./generate-privkey-ursa.js')(bitlen, exp);
 | 
			
		||||
    } catch(e) {
 | 
			
		||||
      if (e.code !== 'MODULE_NOT_FOUND') {
 | 
			
		||||
        console.error("[rsa-compat] Unexpected error when using 'ursa':");
 | 
			
		||||
        console.error(e);
 | 
			
		||||
      }
 | 
			
		||||
      if (!oldver) {
 | 
			
		||||
        oldver = true;
 | 
			
		||||
        console.warn("[WARN] rsa-compat: Your version of node does not have crypto.generateKeyPair()");
 | 
			
		||||
        console.warn("[WARN] rsa-compat: Please update to node >= v10.12 or 'npm install --save ursa node-forge'");
 | 
			
		||||
        console.warn("[WARN] rsa-compat: Using node-forge as a fallback may be unacceptably slow.");
 | 
			
		||||
        if (/arm|mips/i.test(require('os').arch)) {
 | 
			
		||||
          console.warn("================================================================");
 | 
			
		||||
          console.warn("                         WARNING");
 | 
			
		||||
          console.warn("================================================================");
 | 
			
		||||
          console.warn("");
 | 
			
		||||
          console.warn("WARNING: You are generating an RSA key using pure JavaScript on");
 | 
			
		||||
          console.warn("         a VERY SLOW cpu. This could take DOZENS of minutes!");
 | 
			
		||||
          console.warn("");
 | 
			
		||||
          console.warn("         We recommend installing node >= v10.12, or 'gcc' and 'ursa'");
 | 
			
		||||
          console.warn("");
 | 
			
		||||
          console.warn("EXAMPLE:");
 | 
			
		||||
          console.warn("");
 | 
			
		||||
          console.warn("        sudo apt-get install build-essential && npm install ursa");
 | 
			
		||||
          console.warn("");
 | 
			
		||||
          console.warn("================================================================");
 | 
			
		||||
        }
 | 
			
		||||
      }
 | 
			
		||||
      try {
 | 
			
		||||
        return require('./generate-privkey-forge.js')(bitlen, exp);
 | 
			
		||||
      } catch(e) {
 | 
			
		||||
        if (e.code !== 'MODULE_NOT_FOUND') {
 | 
			
		||||
          throw e;
 | 
			
		||||
        }
 | 
			
		||||
        console.error("[ERROR] rsa-compat: could not generate a private key.");
 | 
			
		||||
        console.error("None of crypto.generateKeyPair, ursa, nor node-forge are present");
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
if (require.main === module) {
 | 
			
		||||
  var keypair = module.exports(2048, 0x10001);
 | 
			
		||||
  console.info(keypair.privateKeyPem);
 | 
			
		||||
  console.warn(keypair.publicKeyPem);
 | 
			
		||||
  //console.info(keypair.privateKeyJwk);
 | 
			
		||||
  //console.warn(keypair.publicKeyJwk);
 | 
			
		||||
}
 | 
			
		||||
@ -6,19 +6,30 @@ var PEM = require('./pem.js');
 | 
			
		||||
var x509 = require('./x509.js');
 | 
			
		||||
var ASN1 = require('./asn1.js');
 | 
			
		||||
var Enc = require('./encoding.js');
 | 
			
		||||
var Crypto = require('./crypto.js');
 | 
			
		||||
 | 
			
		||||
/*global Promise*/
 | 
			
		||||
RSA.generate = function (opts) {
 | 
			
		||||
  return Promise.resolve().then(function () {
 | 
			
		||||
    var typ = 'rsa';
 | 
			
		||||
  opts.kty = "RSA";
 | 
			
		||||
  return Crypto.generate(opts).then(function (pair) {
 | 
			
		||||
    var format = opts.format;
 | 
			
		||||
    var encoding = opts.encoding;
 | 
			
		||||
 | 
			
		||||
    // The easy way
 | 
			
		||||
    if ('json' === format && !encoding) {
 | 
			
		||||
      format = 'jwk';
 | 
			
		||||
      encoding = 'json';
 | 
			
		||||
    }
 | 
			
		||||
    if (('jwk' === format || !format) && ('json' === encoding || !encoding)) { return pair; }
 | 
			
		||||
    if ('jwk' === format || 'json' === encoding) {
 | 
			
		||||
      throw new Error("format '" + format + "' is incompatible with encoding '" + encoding + "'");
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // The... less easy way
 | 
			
		||||
    /*
 | 
			
		||||
    var priv;
 | 
			
		||||
    var pub;
 | 
			
		||||
 | 
			
		||||
    if (!format) {
 | 
			
		||||
      format = 'jwk';
 | 
			
		||||
    }
 | 
			
		||||
    if ('spki' === format || 'pkcs8' === format) {
 | 
			
		||||
      format = 'pkcs8';
 | 
			
		||||
      pub = 'spki';
 | 
			
		||||
@ -32,13 +43,8 @@ RSA.generate = function (opts) {
 | 
			
		||||
      encoding = 'der';
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    if ('jwk' === format || 'json' === format) {
 | 
			
		||||
      format = 'jwk';
 | 
			
		||||
      encoding = 'json';
 | 
			
		||||
    } else {
 | 
			
		||||
      priv = format;
 | 
			
		||||
      pub = pub || format;
 | 
			
		||||
    }
 | 
			
		||||
    priv = format;
 | 
			
		||||
    pub = pub || format;
 | 
			
		||||
 | 
			
		||||
    if (!encoding) {
 | 
			
		||||
      encoding = 'pem';
 | 
			
		||||
@ -52,29 +58,19 @@ RSA.generate = function (opts) {
 | 
			
		||||
      priv = { type: 'pkcs1', format: 'pem' };
 | 
			
		||||
      pub = { type: 'pkcs1', format: 'pem' };
 | 
			
		||||
    }
 | 
			
		||||
    */
 | 
			
		||||
    if (('pem' === format || 'der' === format) && !encoding) {
 | 
			
		||||
      encoding = format;
 | 
			
		||||
      format = 'pkcs1';
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return new Promise(function (resolve, reject) {
 | 
			
		||||
      return require('crypto').generateKeyPair(typ, {
 | 
			
		||||
        modulusLength: opts.modulusLength || 2048
 | 
			
		||||
      , publicExponent: opts.publicExponent || 0x10001
 | 
			
		||||
      , privateKeyEncoding: priv
 | 
			
		||||
      , publicKeyEncoding: pub
 | 
			
		||||
      }, function (err, pubkey, privkey) {
 | 
			
		||||
        if (err) { reject(err); }
 | 
			
		||||
        resolve({
 | 
			
		||||
          private: privkey
 | 
			
		||||
        , public: pubkey
 | 
			
		||||
        });
 | 
			
		||||
    var exOpts = { jwk: pair.private, format: format, encoding: encoding };
 | 
			
		||||
    return RSA.export(exOpts).then(function (priv) {
 | 
			
		||||
      exOpts.public = true;
 | 
			
		||||
      if ('pkcs8' === exOpts.format) { exOpts.format = 'spki'; }
 | 
			
		||||
      return RSA.export(exOpts).then(function (pub) {
 | 
			
		||||
        return { private: priv, public: pub };
 | 
			
		||||
      });
 | 
			
		||||
    }).then(function (keypair) {
 | 
			
		||||
      if ('jwk' !== format) {
 | 
			
		||||
        return keypair;
 | 
			
		||||
      }
 | 
			
		||||
 | 
			
		||||
      return {
 | 
			
		||||
        private: RSA.importSync({ pem: keypair.private, format: priv.type })
 | 
			
		||||
      , public: RSA.importSync({ pem: keypair.public, format: pub.type, public: true })
 | 
			
		||||
      };
 | 
			
		||||
    });
 | 
			
		||||
  });
 | 
			
		||||
};
 | 
			
		||||
@ -102,7 +98,7 @@ RSA.importSync = function (opts) {
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  if (opts.public) {
 | 
			
		||||
    jwk = RSA.nueter(jwk);
 | 
			
		||||
    jwk = RSA.neuter(jwk);
 | 
			
		||||
  }
 | 
			
		||||
  return jwk;
 | 
			
		||||
};
 | 
			
		||||
@ -139,7 +135,7 @@ RSA.exportSync = function (opts) {
 | 
			
		||||
  var format = opts.format;
 | 
			
		||||
  var pub = opts.public;
 | 
			
		||||
  if (pub || -1 !== [ 'spki', 'pkix', 'ssh', 'rfc4716' ].indexOf(format)) {
 | 
			
		||||
    jwk = RSA.nueter(jwk);
 | 
			
		||||
    jwk = RSA.neuter(jwk);
 | 
			
		||||
  }
 | 
			
		||||
  if ('RSA' !== jwk.kty) {
 | 
			
		||||
    throw new Error("options.jwk.kty must be 'RSA' for RSA keys");
 | 
			
		||||
@ -193,15 +189,16 @@ RSA.pack = function (opts) {
 | 
			
		||||
RSA.toPem = RSA.export = RSA.pack;
 | 
			
		||||
 | 
			
		||||
// snip the _private_ parts... hAHAHAHA!
 | 
			
		||||
RSA.nueter = function (jwk) {
 | 
			
		||||
  // (snip rather than new object to keep potential extra data)
 | 
			
		||||
  // otherwise we could just do this:
 | 
			
		||||
  // return { kty: jwk.kty, n: jwk.n, e: jwk.e };
 | 
			
		||||
  [ 'p', 'q', 'd', 'dp', 'dq', 'qi' ].forEach(function (key) {
 | 
			
		||||
    if (key in jwk) { jwk[key] = undefined; }
 | 
			
		||||
    return jwk;
 | 
			
		||||
var privates = [ 'p', 'q', 'd', 'dp', 'dq', 'qi' ];
 | 
			
		||||
// fix misspelling without breaking the API
 | 
			
		||||
RSA.neuter = RSA.nueter = function (priv) {
 | 
			
		||||
  var pub = {};
 | 
			
		||||
  Object.keys(priv).forEach(function (key) {
 | 
			
		||||
    if (!privates.includes(key)) {
 | 
			
		||||
      pub[key] = priv[key];
 | 
			
		||||
    }
 | 
			
		||||
  });
 | 
			
		||||
  return jwk;
 | 
			
		||||
  return pub;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
RSA.__thumbprint = function (jwk) {
 | 
			
		||||
@ -1,6 +1,6 @@
 | 
			
		||||
{
 | 
			
		||||
  "name": "rasha",
 | 
			
		||||
  "version": "1.2.5",
 | 
			
		||||
  "version": "1.3.0",
 | 
			
		||||
  "description": "💯 PEM-to-JWK and JWK-to-PEM for RSA keys in a lightweight, zero-dependency library focused on perfect universal compatibility.",
 | 
			
		||||
  "homepage": "https://git.coolaj86.com/coolaj86/rasha.js",
 | 
			
		||||
  "main": "index.js",
 | 
			
		||||
@ -35,5 +35,8 @@
 | 
			
		||||
    "PEM-to-SSH"
 | 
			
		||||
  ],
 | 
			
		||||
  "author": "AJ ONeal <coolaj86@gmail.com> (https://coolaj86.com/)",
 | 
			
		||||
  "license": "MPL-2.0"
 | 
			
		||||
  "license": "MPL-2.0",
 | 
			
		||||
  "trulyOptionalDependencies": {
 | 
			
		||||
    "node-forge": "^0.8.2"
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
							
								
								
									
										8
									
								
								test.sh
									
									
									
									
									
								
							
							
						
						
									
										8
									
								
								test.sh
									
									
									
									
									
								
							@ -123,13 +123,21 @@ jwktopem ""
 | 
			
		||||
 | 
			
		||||
echo ""
 | 
			
		||||
echo "testing node key generation"
 | 
			
		||||
echo "defaults"
 | 
			
		||||
node bin/rasha.js > /dev/null
 | 
			
		||||
echo "jwk"
 | 
			
		||||
node bin/rasha.js jwk > /dev/null
 | 
			
		||||
echo "json 2048"
 | 
			
		||||
node bin/rasha.js json 2048 > /dev/null
 | 
			
		||||
echo "der"
 | 
			
		||||
node bin/rasha.js der > /dev/null
 | 
			
		||||
echo "pkcs8 der"
 | 
			
		||||
node bin/rasha.js pkcs8 der > /dev/null
 | 
			
		||||
echo "pem"
 | 
			
		||||
node bin/rasha.js pem > /dev/null
 | 
			
		||||
echo "pkcs1"
 | 
			
		||||
node bin/rasha.js pkcs1 pem > /dev/null
 | 
			
		||||
echo "spki"
 | 
			
		||||
node bin/rasha.js spki > /dev/null
 | 
			
		||||
echo "PASS"
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user