pull out common signature code

This commit is contained in:
Sanjana Rajan 2018-02-14 18:23:50 +01:00
parent 38a11d7aaf
commit b5d19b6f8d
3 changed files with 28 additions and 53 deletions

View File

@ -29,7 +29,7 @@ import armor from './encoding/armor';
import enums from './enums';
import packet from './packet';
import { Signature } from './signature';
import { createVerificationObjects } from './message';
import { createVerificationObjects, createSignaturePackets } from './message';
import { getPreferredHashAlgo } from './key';
/**
@ -80,34 +80,10 @@ CleartextMessage.prototype.sign = async function(privateKeys) {
* @return {module:signature~Signature} new detached signature of message content
*/
CleartextMessage.prototype.signDetached = async function(privateKeys) {
const packetlist = new packet.List();
const literalDataPacket = new packet.Literal();
literalDataPacket.setText(this.text);
await Promise.all(privateKeys.map(async function(privateKey) {
if (privateKey.isPublic()) {
throw new Error('Need private key for signing');
}
await privateKey.verifyPrimaryUser();
const signingKeyPacket = privateKey.getSigningKeyPacket();
if (!signingKeyPacket) {
throw new Error('Could not find valid key packet for signing in key ' +
privateKey.primaryKey.getKeyId().toHex());
}
const signaturePacket = new packet.Signature();
signaturePacket.signatureType = enums.signature.text;
signaturePacket.publicKeyAlgorithm = signingKeyPacket.algorithm;
signaturePacket.hashAlgorithm = getPreferredHashAlgo(privateKey);
if (!signingKeyPacket.isDecrypted) {
throw new Error('Private key is not decrypted.');
}
await signaturePacket.sign(signingKeyPacket, literalDataPacket);
return signaturePacket;
})).then(signatureList => {
signatureList.forEach(signaturePacket => packetlist.push(signaturePacket));
});
return new Signature(packetlist);
return new Signature(await createSignaturePackets(literalDataPacket, privateKeys));
};
/**

View File

@ -416,25 +416,7 @@ Message.prototype.sign = async function(privateKeys=[], signature=null) {
});
packetlist.push(literalDataPacket);
await Promise.all(privateKeys.map(async function(privateKey) {
const signaturePacket = new packet.Signature();
const signingKeyPacket = privateKey.getSigningKeyPacket();
if (!signingKeyPacket.isDecrypted) {
throw new Error('Private key is not decrypted.');
}
signaturePacket.signatureType = signatureType;
signaturePacket.hashAlgorithm = getPreferredHashAlgo(privateKey);
signaturePacket.publicKeyAlgorithm = signingKeyPacket.algorithm;
await signaturePacket.sign(signingKeyPacket, literalDataPacket);
return signaturePacket;
})).then(signatureList => {
signatureList.forEach(signaturePacket => packetlist.push(signaturePacket));
});
if (signature) {
packetlist.concat(existingSigPacketlist);
}
packetlist.concat(await createSignaturePackets(literalDataPacket, privateKeys, signature));
return new Message(packetlist);
};
@ -466,24 +448,40 @@ Message.prototype.compress = function(compression) {
* @return {module:signature~Signature} new detached signature of message content
*/
Message.prototype.signDetached = async function(privateKeys=[], signature=null) {
const packetlist = new packet.List();
const literalDataPacket = this.packets.findPacket(enums.packet.literal);
if (!literalDataPacket) {
throw new Error('No literal data packet to sign.');
}
return new Signature(await createSignaturePackets(literalDataPacket, privateKeys, signature));
};
/**
* Create signature packets for the message
* @param {module:packet/literal} the literal data packet to sign
* @param {Array<module:key~Key>} privateKey private keys with decrypted secret key data for signing
* @param {Signature} signature (optional) any existing detached signature to append
* @return {module:packet/packetlist} list of signature packets
*/
export async function createSignaturePackets(literalDataPacket, privateKeys, signature=null) {
const packetlist = new packet.List();
const literalFormat = enums.write(enums.literal, literalDataPacket.format);
const signatureType = literalFormat === enums.literal.binary ?
enums.signature.binary : enums.signature.text;
await Promise.all(privateKeys.map(async function(privateKey) {
const signaturePacket = new packet.Signature();
if (privateKey.isPublic()) {
throw new Error('Need private key for signing');
}
await privateKey.verifyPrimaryUser();
const signingKeyPacket = privateKey.getSigningKeyPacket();
if (!signingKeyPacket) {
throw new Error('Could not find valid key packet for signing in key ' + privateKey.primaryKey.getKeyId().toHex());
}
if (!signingKeyPacket.isDecrypted) {
throw new Error('Private key is not decrypted.');
}
const signaturePacket = new packet.Signature();
signaturePacket.signatureType = signatureType;
signaturePacket.publicKeyAlgorithm = signingKeyPacket.algorithm;
signaturePacket.hashAlgorithm = getPreferredHashAlgo(privateKey);
@ -497,10 +495,8 @@ Message.prototype.signDetached = async function(privateKeys=[], signature=null)
const existingSigPacketlist = signature.packets.filterByTag(enums.packet.signature);
packetlist.concat(existingSigPacketlist);
}
return new Signature(packetlist);
};
return packetlist;
}
/**
* Verify message signatures

View File

@ -1279,7 +1279,7 @@ describe('OpenPGP.js public api tests', function() {
privateKeys: [privateKey.keys[0], privKeyDE]
};
const verifyOpt = {
publicKeys: publicKey.keys
publicKeys: [publicKey.keys[0], privKeyDE.toPublic()]
};
return openpgp.sign(signOpt).then(function (signed) {
expect(signed.data).to.match(/-----BEGIN PGP SIGNED MESSAGE-----/);
@ -1290,6 +1290,9 @@ describe('OpenPGP.js public api tests', function() {
expect(verified.signatures[0].valid).to.be.true;
expect(verified.signatures[0].keyid.toHex()).to.equal(privateKey.keys[0].getSigningKeyPacket().getKeyId().toHex());
expect(verified.signatures[0].signature.packets.length).to.equal(1);
expect(verified.signatures[1].valid).to.be.true;
expect(verified.signatures[1].keyid.toHex()).to.equal(privKeyDE.getSigningKeyPacket().getKeyId().toHex());
expect(verified.signatures[1].signature.packets.length).to.equal(1);
});
});