2016-09-26 10 views
1

Я создал закрытый ключ с кривым nodejs и хочу подписать файл с помощью этого ключа. Мой код выглядит следующим образом:Невозможно подписать файл с nodejs crypto

var ecdh = crypto.createECDH('brainpoolP512t1'); 
     ecdh.generateKeys(); 
     var key = ecdh.getPrivateKey('buffer'); 

     var data= fs.readFileSync(req.file.path); 
     var sign = crypto.createSign('sha512'); 
     sign.update(data); 
     var signature = sign.sign(key, 'hex'); 

Но я получаю ошибку:

Error: error:0906D06C:PEM routines:PEM_read_bio:no start line 
    at Error (native) 
    at Sign.sign (crypto.js:283:26) 
    at /....js:32:27 
    at Immediate.<anonymous> (/.../node_modules/multer/lib/make-middleware.js:52:37) 
    at runCallback (timers.js:578:20) 
    at tryOnImmediate (timers.js:554:5) 
    at processImmediate [as _immediateCallback] (timers.js:533:5) 

Я знаю, что есть что-то делать с ключевым форматом, но я не знаю, как это исправить. Может ли кто-нибудь помочь?

UPDATE: я редактировал PrivateKey, чтобы соответствовать формату PEM:

var KEY_START = '-----BEGIN EC PRIVATE KEY-----\n'; 
var KEY_END = '\n-----END EC PRIVATE KEY-----'; 

const ecdh = crypto.createECDH('brainpoolP512t1'); 
      ecdh.generateKeys(); 
      var key =KEY_START + ecdh.getPrivateKey('base64') + KEY_END;   
      var data= fs.readFileSync(req.file.path); 
      const sign = crypto.createSign('sha512'); 
      sign.update(data); 
      var signature = sign.sign(key, 'hex'); 

А теперь я Geht другую ошибку:

Error: error:0D07207B:asn1 encoding routines:ASN1_get_object:header too long 
    at Error (native) 
    at Sign.sign (crypto.js:283:26) 
    at /...js:37:27 
    at Immediate.<anonymous> (/.../node_modules/multer/lib/make-middleware.js:52:37) 
    at runCallback (timers.js:578:20) 
    at tryOnImmediate (timers.js:554:5) 
    at processImmediate [as _immediateCallback] (timers.js:533:5) 

ответ

3

Ключ вы подписываете данные с потребностями быть действительный закрытый ключ PEM. Функция DH getPrivateKey() не возвращает ключ в этом формате, он возвращает данные открытого секретного ключа.

Ваших вариантов включают в себя:

  • Создание секретного ключа с помощью ключа утилиты генератора OpenSSL или аналогичного
  • Использования сторонних узлов модулей для правильного кодирования секретного ключа, как описано в RFC 5915. Полный пример использования asn1.js и bn.js модули:

    var crypto = require('crypto'); 
    
    var asn1 = require('asn1.js'); 
    var BN = require('bn.js'); 
    
    function toOIDArray(oid) { 
        return oid.split('.').map(function(s) { 
        return parseInt(s, 10) 
        }); 
    } 
    
    // Define ECPrivateKey from RFC 5915 
    var ECPrivateKey = asn1.define('ECPrivateKey', function() { 
        this.seq().obj(
        this.key('version').int(), 
        this.key('privateKey').octstr(), 
        this.key('parameters').explicit(0).objid().optional(), 
        this.key('publicKey').explicit(1).bitstr().optional() 
    ); 
    }); 
    
    // Generate the DH keys 
    var ecdh = crypto.createECDH('brainpoolP512t1'); 
    ecdh.generateKeys(); 
    
    // Generate the PEM-encoded private key 
    var pemKey = ECPrivateKey.encode({ 
        version: new BN(1), 
        privateKey: ecdh.getPrivateKey(), 
        // OID for brainpoolP512t1 
        parameters: toOIDArray('1.3.36.3.3.2.8.1.1.14') 
    }, 'pem', { label: 'EC PRIVATE KEY' }); 
    
    // Sign data 
    var sign = crypto.createSign('sha512'); 
    sign.update('hello world'); 
    var signature = sign.sign(pemKey, 'hex'); 
    
    console.log('signature', signature); 
    
+0

Я думал, что должен стоять файл путь к файлу, который я хочу подписать? – nolags

+0

Я ошибся, я обновил свой ответ. – mscdex

+0

Теперь я добавил пример кода, если вы хотите сгенерировать (внутри узла) действительный PEM-форматированный ключ из частного ключа DH. – mscdex