Move methods of Key and Message class to prototype. Clean up openpgp.js file.
This commit is contained in:
parent
89eb5dff2a
commit
be96de5188
File diff suppressed because one or more lines are too long
128
src/key.js
128
src/key.js
|
@ -22,21 +22,23 @@ var config = require('./config');
|
|||
|
||||
/**
|
||||
* @class
|
||||
* @classdesc Class that represents an OpenPGP key. Must contain a master key.
|
||||
* @param {packetlist} packetlist [description]
|
||||
* Can contain additional subkeys, signatures,
|
||||
* user ids, user attributes.
|
||||
* @classdesc Class that represents an OpenPGP key. Must contain a primary key.
|
||||
* Can contain additional subkeys, signatures, user ids, user attributes.
|
||||
* @param {packetlist} packetlist The packets that form this key
|
||||
*/
|
||||
|
||||
function key(packetlist) {
|
||||
|
||||
function Key(packetlist) {
|
||||
if (!(this instanceof Key)) {
|
||||
return new Key(packetlist);
|
||||
}
|
||||
this.packets = packetlist || new packet.list();
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Returns the primary key packet (secret or public)
|
||||
* @returns {packet_secret_key|packet_public_key|null}
|
||||
*/
|
||||
this.getKeyPacket = function() {
|
||||
Key.prototype.getKeyPacket = function() {
|
||||
for (var i = 0; i < this.packets.length; i++) {
|
||||
if (this.packets[i].tag == enums.packet.public_key ||
|
||||
this.packets[i].tag == enums.packet.secret_key) {
|
||||
|
@ -44,13 +46,13 @@ var config = require('./config');
|
|||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Returns all the private and public subkey packets
|
||||
* @returns {[public_subkey|secret_subkey]}
|
||||
*/
|
||||
this.getSubkeyPackets = function() {
|
||||
Key.prototype.getSubkeyPackets = function() {
|
||||
|
||||
var subkeys = [];
|
||||
|
||||
|
@ -62,30 +64,30 @@ var config = require('./config');
|
|||
}
|
||||
|
||||
return subkeys;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Returns all the private and public key and subkey packets
|
||||
* @returns {[public_subkey|secret_subkey|packet_secret_key|packet_public_key]}
|
||||
*/
|
||||
this.getAllKeyPackets = function() {
|
||||
Key.prototype.getAllKeyPackets = function() {
|
||||
return [this.getKeyPacket()].concat(this.getSubkeyPackets());
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Returns key IDs of all key packets
|
||||
* @returns {[keyid]}
|
||||
*/
|
||||
this.getKeyIds = function() {
|
||||
Key.prototype.getKeyIds = function() {
|
||||
var keyIds = [];
|
||||
var keys = this.getAllKeyPackets();
|
||||
for (var i = 0; i < keys.length; i++) {
|
||||
keyIds.push(keys[i].getKeyId());
|
||||
}
|
||||
return keyIds;
|
||||
}
|
||||
};
|
||||
|
||||
function findKey(keys, keyIds) {
|
||||
function findKey(keys, keyIds) {
|
||||
for (var i = 0; i < keys.length; i++) {
|
||||
var keyId = keys[i].getKeyId();
|
||||
for (var j = 0; j < keyIds.length; j++) {
|
||||
|
@ -95,51 +97,51 @@ var config = require('./config');
|
|||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Returns first public key packet for given array of key IDs
|
||||
* @param {[keyid]} keyIds
|
||||
* @return {public_subkey|packet_public_key|null}
|
||||
*/
|
||||
this.getPublicKeyPacket = function(keyIds) {
|
||||
Key.prototype.getPublicKeyPacket = function(keyIds) {
|
||||
var keys = this.packets.filterByTag(enums.packet.public_key, enums.packet.public_subkey);
|
||||
return findKey(keys, keyIds);
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Returns first private key packet for given array of key IDs
|
||||
* @param {[keyid]} keyIds
|
||||
* @return {secret_subkey|packet_secret_key|null}
|
||||
*/
|
||||
this.getPrivateKeyPacket = function(keyIds) {
|
||||
Key.prototype.getPrivateKeyPacket = function(keyIds) {
|
||||
var keys = this.packets.filterByTag(enums.packet.secret_key, enums.packet.secret_subkey);
|
||||
return findKey(keys, keyIds);
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Returns true if this is a public key
|
||||
* @return {Boolean}
|
||||
*/
|
||||
this.isPublic = function() {
|
||||
Key.prototype.isPublic = function() {
|
||||
var publicKeyPackets = this.packets.filterByTag(enums.packet.public_key);
|
||||
return publicKeyPackets.length ? true : false;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Returns true if this is a private key
|
||||
* @return {Boolean}
|
||||
*/
|
||||
this.isPrivate = function() {
|
||||
Key.prototype.isPrivate = function() {
|
||||
var privateKeyPackets = this.packets.filterByTag(enums.packet.private_key);
|
||||
return privateKeyPackets.length ? true : false;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Returns key as public key
|
||||
* @return {key} public key
|
||||
*/
|
||||
this.toPublic = function() {
|
||||
Key.prototype.toPublic = function() {
|
||||
for (var i = 0; i < this.packets.length; i++) {
|
||||
if (this.packets[i].tag == enums.packet.secret_key) {
|
||||
var bytes = this.packets[i].writePublicKey();
|
||||
|
@ -155,22 +157,22 @@ var config = require('./config');
|
|||
}
|
||||
}
|
||||
return this;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Returns ASCII armored text of key
|
||||
* @return {String} ASCII armor
|
||||
*/
|
||||
this.armor = function() {
|
||||
Key.prototype.armor = function() {
|
||||
var type = this.isPublic() ? enums.armor.public_key : enums.armor.private_key;
|
||||
return armor.encode(type, this.packets.write());
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Returns first key packet that is available for signing
|
||||
* @return {public_subkey|secret_subkey|packet_secret_key|packet_public_key|null}
|
||||
*/
|
||||
this.getSigningKeyPacket = function() {
|
||||
Key.prototype.getSigningKeyPacket = function() {
|
||||
|
||||
var signing = [ enums.publicKey.rsa_encrypt_sign, enums.publicKey.rsa_sign, enums.publicKey.dsa];
|
||||
|
||||
|
@ -187,23 +189,23 @@ var config = require('./config');
|
|||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Returns preferred signature hash algorithm of this key
|
||||
* @return {String}
|
||||
*/
|
||||
function getPreferredSignatureHashAlgorithm() {
|
||||
Key.prototype.getPreferredSignatureHashAlgorithm = function() {
|
||||
//TODO implement: https://tools.ietf.org/html/rfc4880#section-5.2.3.8
|
||||
//separate private key preference from digest preferences
|
||||
return config.prefer_hash_algorithm;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Returns the first valid encryption key packet for this key
|
||||
* @returns {public_subkey|secret_subkey|packet_secret_key|packet_public_key|null} key packet or null if no encryption key has been found
|
||||
*/
|
||||
this.getEncryptionKeyPacket = function() {
|
||||
Key.prototype.getEncryptionKeyPacket = function() {
|
||||
// V4: by convention subkeys are prefered for encryption service
|
||||
// V3: keys MUST NOT have subkeys
|
||||
var isValidEncryptionKey = function(key) {
|
||||
|
@ -227,29 +229,29 @@ var config = require('./config');
|
|||
return primaryKey;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Decrypts all secret key and subkey packets
|
||||
* @param {String} passphrase
|
||||
* @return {Boolean} true if all key and subkey packets decrypted successfully
|
||||
*/
|
||||
this.decrypt = function(passphrase) {
|
||||
Key.prototype.decrypt = function(passphrase) {
|
||||
var keys = this.packets.filterByTag(enums.packet.secret_key, enums.packet.secret_subkey);
|
||||
for (var i = 0; i < keys.length; i++) {
|
||||
var success = keys[i].decrypt(passphrase);
|
||||
if (!success) return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Decrypts specific key packets by key ID
|
||||
* @param {[keyid]} keyIds
|
||||
* @param {String} passphrase
|
||||
* @return {Boolean} true if all key packets decrypted successfully
|
||||
*/
|
||||
this.decryptKeyPacket = function(keyIds, passphrase) {
|
||||
Key.prototype.decryptKeyPacket = function(keyIds, passphrase) {
|
||||
//TODO return value
|
||||
var keys = this.packets.filterByTag(enums.packet.secret_key, enums.packet.secret_subkey);
|
||||
for (var i = 0; i < keys.length; i++) {
|
||||
|
@ -262,32 +264,32 @@ var config = require('./config');
|
|||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
// TODO
|
||||
this.verify = function() {
|
||||
// TODO
|
||||
Key.prototype.verify = function() {
|
||||
|
||||
}
|
||||
// TODO
|
||||
this.revoke = function() {
|
||||
};
|
||||
// TODO
|
||||
Key.prototype.revoke = function() {
|
||||
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* reads an OpenPGP armored text and returns a key object
|
||||
* @param {String} armoredText text to be parsed
|
||||
* @return {key} new key object
|
||||
*/
|
||||
key.readArmored = function(armoredText) {
|
||||
function readArmored(armoredText) {
|
||||
//TODO how do we want to handle bad text? Exception throwing
|
||||
//TODO don't accept non-key armored texts
|
||||
var input = armor.decode(armoredText).data;
|
||||
var packetlist = new packet.list();
|
||||
packetlist.read(input);
|
||||
var newKey = new key(packetlist);
|
||||
var newKey = new Key(packetlist);
|
||||
return newKey;
|
||||
}
|
||||
|
||||
module.exports = key;
|
||||
exports.Key = Key;
|
||||
exports.readArmored = readArmored;
|
||||
|
|
169
src/message.js
169
src/message.js
|
@ -24,31 +24,36 @@ var util = require('./util');
|
|||
|
||||
/**
|
||||
* @class
|
||||
* @classdesc A generic message containing one or more literal packets.
|
||||
* @classdesc Class that represents an OpenPGP message.
|
||||
* Can be an encrypted message, signed message, compressed message or literal message
|
||||
* See http://tools.ietf.org/html/rfc4880#section-11.3
|
||||
*/
|
||||
|
||||
function message(packetlist) {
|
||||
|
||||
function Message(packetlist) {
|
||||
if (!(this instanceof Message)) {
|
||||
return new Message(packetlist);
|
||||
}
|
||||
this.packets = packetlist || new packet.list();
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Returns the key IDs of the keys to which the session key is encrypted
|
||||
* @return {[keyId]} array of keyid objects
|
||||
*/
|
||||
this.getEncryptionKeyIds = function() {
|
||||
Message.prototype.getEncryptionKeyIds = function() {
|
||||
var keyIds = [];
|
||||
var pkESKeyPacketlist = this.packets.filterByTag(enums.packet.public_key_encrypted_session_key);
|
||||
pkESKeyPacketlist.forEach(function(packet) {
|
||||
keyIds.push(packet.publicKeyId);
|
||||
});
|
||||
return keyIds;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Returns the key IDs of the keys that signed the message
|
||||
* @return {[keyId]} array of keyid objects
|
||||
*/
|
||||
this.getSigningKeyIds = function() {
|
||||
Message.prototype.getSigningKeyIds = function() {
|
||||
var keyIds = [];
|
||||
var msg = this.unwrapCompressed();
|
||||
// search for one pass signatures
|
||||
|
@ -64,14 +69,14 @@ function message(packetlist) {
|
|||
});
|
||||
}
|
||||
return keyIds;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Decrypt the message
|
||||
* @param {key} privateKey private key with decrypted secret data
|
||||
* @return {[message]} new message with decrypted content
|
||||
*/
|
||||
this.decrypt = function(privateKey) {
|
||||
Message.prototype.decrypt = function(privateKey) {
|
||||
var encryptionKeyIds = this.getEncryptionKeyIds();
|
||||
if (!encryptionKeyIds.length) {
|
||||
// nothing to decrypt return unmodified message
|
||||
|
@ -93,25 +98,25 @@ function message(packetlist) {
|
|||
if (symEncryptedPacketlist.length !== 0) {
|
||||
var symEncryptedPacket = symEncryptedPacketlist[0];
|
||||
symEncryptedPacket.decrypt(pkESKeyPacket.sessionKeyAlgorithm, pkESKeyPacket.sessionKey);
|
||||
return new message(symEncryptedPacket.packets);
|
||||
}
|
||||
return new Message(symEncryptedPacket.packets);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Get literal data that is the body of the message
|
||||
* @return {String|null} literal body of the message as string
|
||||
*/
|
||||
this.getLiteralData = function() {
|
||||
Message.prototype.getLiteralData = function() {
|
||||
var literal = this.packets.findPacket(enums.packet.literal);
|
||||
return literal && literal.data || null;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Get literal data as text
|
||||
* @return {String|null} literal body of the message interpreted as text
|
||||
*/
|
||||
this.getText = function() {
|
||||
Message.prototype.getText = function() {
|
||||
var literal = this.packets.findPacket(enums.packet.literal);
|
||||
if (literal) {
|
||||
var data = literal.data;
|
||||
|
@ -124,14 +129,14 @@ function message(packetlist) {
|
|||
} else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Encrypt the message
|
||||
* @param {[key]} keys array of keys, used to encrypt the message
|
||||
* @return {[message]} new message with encrypted content
|
||||
*/
|
||||
this.encrypt = function(keys) {
|
||||
Message.prototype.encrypt = function(keys) {
|
||||
var packetlist = new packet.list();
|
||||
//TODO get preferred algo from signature
|
||||
var sessionKey = crypto.generateSessionKey(enums.read(enums.symmetric, config.encryption_cipher));
|
||||
|
@ -158,15 +163,15 @@ function message(packetlist) {
|
|||
//TODO get preferred algo from signature
|
||||
symEncryptedPacket.encrypt(enums.read(enums.symmetric, config.encryption_cipher), sessionKey);
|
||||
packetlist.push(symEncryptedPacket);
|
||||
return new message(packetlist);
|
||||
}
|
||||
return new Message(packetlist);
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Sign the message (the literal data packet of the message)
|
||||
* @param {[key]} privateKey private keys with decrypted secret key data for signing
|
||||
* @return {message} new message with signed content
|
||||
*/
|
||||
this.sign = function(privateKeys) {
|
||||
Message.prototype.sign = function(privateKeys) {
|
||||
|
||||
var packetlist = new packet.list();
|
||||
|
||||
|
@ -200,15 +205,15 @@ function message(packetlist) {
|
|||
packetlist.push(signaturePacket);
|
||||
}
|
||||
|
||||
return new message(packetlist);
|
||||
}
|
||||
return new Message(packetlist);
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Verify message signatures
|
||||
* @param {[key]} publicKeys public keys to verify signatures
|
||||
* @return {[{'keyid': keyid, 'valid': Boolean}]} list of signer's keyid and validity of signature
|
||||
*/
|
||||
this.verify = function(publicKeys) {
|
||||
Message.prototype.verify = function(publicKeys) {
|
||||
var result = [];
|
||||
var msg = this.unwrapCompressed();
|
||||
var literalDataList = msg.packets.filterByTag(enums.packet.literal);
|
||||
|
@ -227,119 +232,41 @@ function message(packetlist) {
|
|||
}
|
||||
});
|
||||
return result;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Unwrap compressed message
|
||||
* @return {message} message Content of compressed message
|
||||
*/
|
||||
this.unwrapCompressed = function() {
|
||||
Message.prototype.unwrapCompressed = function() {
|
||||
var compressed = this.packets.filterByTag(enums.packet.compressed);
|
||||
if (compressed.length) {
|
||||
return new message(compressed[0].packets);
|
||||
return new Message(compressed[0].packets);
|
||||
} else {
|
||||
return this;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
/**
|
||||
* Returns ASCII armored text of message
|
||||
* @return {String} ASCII armor
|
||||
*/
|
||||
this.armor = function() {
|
||||
Message.prototype.armor = function() {
|
||||
return armor.encode(enums.armor.message, this.packets.write());
|
||||
}
|
||||
|
||||
/**
|
||||
* Decrypts a message and generates user interface message out of the found.
|
||||
* MDC will be verified as well as message signatures
|
||||
* @param {openpgp_msg_privatekey} private_key the private the message is encrypted with (corresponding to the session key)
|
||||
* @param {openpgp_packet_encryptedsessionkey} sessionkey the session key to be used to decrypt the message
|
||||
* @param {openpgp_msg_publickey} pubkey Array of public keys to check signature against. If not provided, checks local keystore.
|
||||
* @return {String} plaintext of the message or null on error
|
||||
*/
|
||||
function decryptAndVerifySignature(private_key, sessionkey, pubkey) {
|
||||
if (private_key == null || sessionkey == null || sessionkey == "")
|
||||
return null;
|
||||
var decrypted = sessionkey.decrypt(this, private_key.keymaterial);
|
||||
if (decrypted == null)
|
||||
return null;
|
||||
var packet;
|
||||
var position = 0;
|
||||
var len = decrypted.length;
|
||||
var validSignatures = new Array();
|
||||
util.print_debug_hexstr_dump("openpgp.msg.messge decrypt:\n", decrypted);
|
||||
|
||||
var messages = openpgp.read_messages_dearmored({
|
||||
text: decrypted,
|
||||
openpgp: decrypted
|
||||
});
|
||||
for (var m in messages) {
|
||||
if (messages[m].data) {
|
||||
this.text = messages[m].data;
|
||||
}
|
||||
if (messages[m].signature) {
|
||||
validSignatures.push(messages[m].verifySignature(pubkey));
|
||||
}
|
||||
}
|
||||
return {
|
||||
text: this.text,
|
||||
validSignatures: validSignatures
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Verifies a message signature. This function can be called after read_message if the message was signed only.
|
||||
* @param {openpgp_msg_publickey} pubkey Array of public keys to check signature against. If not provided, checks local keystore.
|
||||
* @return {boolean} true if the signature was correct; otherwise false
|
||||
*/
|
||||
function verifySignature(pubkey) {
|
||||
var result = false;
|
||||
if (this.signature.tagType == 2) {
|
||||
if (!pubkey || pubkey.length == 0) {
|
||||
var pubkey;
|
||||
if (this.signature.version == 4) {
|
||||
pubkey = openpgp.keyring.getPublicKeysForKeyId(this.signature.issuerKeyId);
|
||||
} else if (this.signature.version == 3) {
|
||||
pubkey = openpgp.keyring.getPublicKeysForKeyId(this.signature.keyId);
|
||||
} else {
|
||||
util.print_error("unknown signature type on message!");
|
||||
return false;
|
||||
}
|
||||
}
|
||||
if (pubkey.length == 0)
|
||||
util.print_warning("Unable to verify signature of issuer: " + util.hexstrdump(this.signature.issuerKeyId) +
|
||||
". Public key not found in keyring.");
|
||||
else {
|
||||
for (var i = 0; i < pubkey.length; i++) {
|
||||
var tohash = this.text.replace(/\r\n/g, "\n").replace(/\n/g, "\r\n");
|
||||
if (this.signature.verify(tohash, pubkey[i])) {
|
||||
util.print_info("Found Good Signature from " + pubkey[i].obj.userIds[0].text + " (0x" + util.hexstrdump(
|
||||
pubkey[i].obj.getKeyId()).substring(8) + ")");
|
||||
result = true;
|
||||
} else {
|
||||
util.print_error("Signature verification failed: Bad Signature from " + pubkey[i].obj.userIds[0].text +
|
||||
" (0x" + util.hexstrdump(pubkey[0].obj.getKeyId()).substring(8) + ")");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* reads an OpenPGP armored message and returns a message object
|
||||
* @param {String} armoredText text to be parsed
|
||||
* @return {message} new message object
|
||||
*/
|
||||
message.readArmored = function(armoredText) {
|
||||
function readArmored(armoredText) {
|
||||
//TODO how do we want to handle bad text? Exception throwing
|
||||
//TODO don't accept non-message armored texts
|
||||
var input = armor.decode(armoredText).data;
|
||||
var packetlist = new packet.list();
|
||||
packetlist.read(input);
|
||||
var newMessage = new message(packetlist);
|
||||
var newMessage = new Message(packetlist);
|
||||
return newMessage;
|
||||
}
|
||||
|
||||
|
@ -348,14 +275,16 @@ message.readArmored = function(armoredText) {
|
|||
* @param {String} text
|
||||
* @return {message} new message object
|
||||
*/
|
||||
message.fromText = function(text) {
|
||||
function fromText(text) {
|
||||
var literalDataPacket = new packet.literal();
|
||||
// text will be converted to UTF8
|
||||
literalDataPacket.set(text);
|
||||
var literalDataPacketlist = new packet.list();
|
||||
literalDataPacketlist.push(literalDataPacket);
|
||||
var newMessage = new message(literalDataPacketlist);
|
||||
var newMessage = new Message(literalDataPacketlist);
|
||||
return newMessage;
|
||||
}
|
||||
|
||||
module.exports = message;
|
||||
exports.Message = Message;
|
||||
exports.readArmored = readArmored;
|
||||
exports.fromText = fromText;
|
184
src/openpgp.js
184
src/openpgp.js
|
@ -16,68 +16,59 @@
|
|||
// Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
|
||||
/**
|
||||
* @fileoverview The openpgp base class should provide all of the functionality
|
||||
* @fileoverview The openpgp base module should provide all of the functionality
|
||||
* to consume the openpgp.js library. All additional classes are documented
|
||||
* for extending and developing on top of the base library.
|
||||
*/
|
||||
|
||||
var armor = require('./encoding/armor.js');
|
||||
var packet = require('./packet');
|
||||
var util = require('./util');
|
||||
var enums = require('./enums.js');
|
||||
var config = require('./config');
|
||||
var message = require('./message.js');
|
||||
|
||||
/**
|
||||
* GPG4Browsers Core interface. A single instance is hold
|
||||
* from the beginning. To use this library call "openpgp.init()"
|
||||
* @alias openpgp
|
||||
* @class
|
||||
* @classdesc Main Openpgp.js class. Use this to initiate and make all calls to this library.
|
||||
*/
|
||||
function _openpgp() {
|
||||
|
||||
/**
|
||||
/**
|
||||
* Encrypts message text with keys
|
||||
* @param {[key]} keys array of keys, used to encrypt the message
|
||||
* @param {String} text message as native JavaScript string
|
||||
* @return {String} encrypted ASCII armored message
|
||||
*/
|
||||
function encryptMessage(keys, text) {
|
||||
function encryptMessage(keys, text) {
|
||||
var msg = message.fromText(text);
|
||||
msg = msg.encrypt(keys);
|
||||
var armored = armor.encode(enums.armor.message, msg.packets.write());
|
||||
return armored;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Signs message text and encrypts it
|
||||
* @param {[key]} publicKeys array of keys, used to encrypt the message
|
||||
* @param {key} privateKey private key with decrypted secret key data for signing
|
||||
* @param {String} text message as native JavaScript string
|
||||
* @return {String} encrypted ASCII armored message
|
||||
*/
|
||||
function signAndEncryptMessage(publicKeys, privateKey, text) {
|
||||
function signAndEncryptMessage(publicKeys, privateKey, text) {
|
||||
var msg = message.fromText(text);
|
||||
msg = msg.sign([privateKey]);
|
||||
msg = msg.encrypt(publicKeys);
|
||||
var armored = armor.encode(enums.armor.message, msg.packets.write());
|
||||
return armored;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Decrypts message
|
||||
* @param {key} privateKey private key with decrypted secret key data
|
||||
* @param {message} message the message object with the encrypted data
|
||||
* @return {String|null} decrypted message as as native JavaScript string
|
||||
* or null if no literal data found
|
||||
*/
|
||||
function decryptMessage(privateKey, message) {
|
||||
function decryptMessage(privateKey, message) {
|
||||
message = message.decrypt(privateKey);
|
||||
return message.getText();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Decrypts message and verifies signatures
|
||||
* @param {key} privateKey private key with decrypted secret key data
|
||||
* @param {[key]} publicKeys public keys to verify signatures
|
||||
|
@ -86,7 +77,7 @@ function _openpgp() {
|
|||
* decrypted message as as native JavaScript string
|
||||
* with verified signatures or null if no literal data found
|
||||
*/
|
||||
function decryptAndVerifyMessage(privateKey, publicKeys, message) {
|
||||
function decryptAndVerifyMessage(privateKey, publicKeys, message) {
|
||||
var result = {};
|
||||
message = message.decrypt(privateKey);
|
||||
result.text = message.getText();
|
||||
|
@ -95,17 +86,19 @@ function _openpgp() {
|
|||
return result;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
function verifyMessage(publicKeys, messagePacketlist) {
|
||||
function signClearMessage(privateKeys, text) {
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
function signMessage(privateKey, messagePacketlist) {
|
||||
function verifyClearSignedMessage(publicKeys, message) {
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
|
||||
/**
|
||||
* TODO: update this doc
|
||||
* generates a new key pair for openpgp. Beta stage. Currently only
|
||||
* supports RSA keys, and no subkeys.
|
||||
|
@ -119,7 +112,7 @@ function _openpgp() {
|
|||
* @return {Object} {privateKey: [openpgp_msg_privatekey],
|
||||
* privateKeyArmored: [string], publicKeyArmored: [string]}
|
||||
*/
|
||||
function generateKeyPair(keyType, numBits, userId, passphrase) {
|
||||
function generateKeyPair(keyType, numBits, userId, passphrase) {
|
||||
var packetlist = new packet.list();
|
||||
|
||||
var secretKeyPacket = new packet.secret_key();
|
||||
|
@ -165,119 +158,9 @@ function _openpgp() {
|
|||
|
||||
var armored = armor.encode(enums.armor.private_key, packetlist.write());
|
||||
return armored;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* creates a binary string representation of an encrypted and signed message.
|
||||
* The message will be encrypted with the public keys specified and signed
|
||||
* with the specified private key.
|
||||
* @param {Object} privatekey {obj: [openpgp_msg_privatekey]} Private key
|
||||
* to be used to sign the message
|
||||
* @param {Object[]} publickeys An arraf of {obj: [openpgp_msg_publickey]}
|
||||
* - public keys to be used to encrypt the message
|
||||
* @param {String} messagetext message text to encrypt and sign
|
||||
* @return {String} a binary string representation of the message which
|
||||
* can be OpenPGP armored
|
||||
*/
|
||||
function write_signed_and_encrypted_message(privatekey, publickeys, messagetext) {
|
||||
var result = "";
|
||||
var i;
|
||||
var literal = new openpgp_packet_literaldata().write_packet(messagetext.replace(/\r\n/g, "\n").replace(/\n/g,
|
||||
"\r\n"));
|
||||
util.print_debug_hexstr_dump("literal_packet: |" + literal + "|\n", literal);
|
||||
for (i = 0; i < publickeys.length; i++) {
|
||||
var onepasssignature = new openpgp_packet_onepasssignature();
|
||||
var onepasssigstr = "";
|
||||
if (i === 0)
|
||||
onepasssigstr = onepasssignature.write_packet(1, openpgp.config.config.prefer_hash_algorithm, privatekey, false);
|
||||
else
|
||||
onepasssigstr = onepasssignature.write_packet(1, openpgp.config.config.prefer_hash_algorithm, privatekey, false);
|
||||
util.print_debug_hexstr_dump("onepasssigstr: |" + onepasssigstr + "|\n", onepasssigstr);
|
||||
var datasignature = new openpgp_packet_signature().write_message_signature(1, messagetext.replace(/\r\n/g, "\n").replace(
|
||||
/\n/g, "\r\n"), privatekey);
|
||||
util.print_debug_hexstr_dump("datasignature: |" + datasignature.openpgp + "|\n", datasignature.openpgp);
|
||||
if (i === 0) {
|
||||
result = onepasssigstr + literal + datasignature.openpgp;
|
||||
} else {
|
||||
result = onepasssigstr + result + datasignature.openpgp;
|
||||
}
|
||||
}
|
||||
|
||||
util.print_debug_hexstr_dump("signed packet: |" + result + "|\n", result);
|
||||
// signatures done.. now encryption
|
||||
var sessionkey = openpgp_crypto_generateSessionKey(openpgp.config.config.encryption_cipher);
|
||||
var result2 = "";
|
||||
|
||||
// creating session keys for each recipient
|
||||
for (i = 0; i < publickeys.length; i++) {
|
||||
var pkey = publickeys[i].getEncryptionKey();
|
||||
if (pkey === null) {
|
||||
util.print_error("no encryption key found! Key is for signing only.");
|
||||
return null;
|
||||
}
|
||||
result2 += new openpgp_packet_encryptedsessionkey().
|
||||
write_pub_key_packet(
|
||||
pkey.getKeyId(),
|
||||
pkey.MPIs,
|
||||
pkey.publicKeyAlgorithm,
|
||||
openpgp.config.config.encryption_cipher,
|
||||
sessionkey);
|
||||
}
|
||||
if (openpgp.config.config.integrity_protect) {
|
||||
result2 += new openpgp_packet_encryptedintegrityprotecteddata().write_packet(openpgp.config.config.encryption_cipher,
|
||||
sessionkey, result);
|
||||
} else {
|
||||
result2 += new openpgp_packet_encrypteddata().write_packet(openpgp.config.config.encryption_cipher, sessionkey,
|
||||
result);
|
||||
}
|
||||
return armor.encode(3, result2, null, null);
|
||||
}
|
||||
/**
|
||||
* creates a binary string representation of an encrypted message.
|
||||
* The message will be encrypted with the public keys specified
|
||||
* @param {Object[]} publickeys An array of {obj: [openpgp_msg_publickey]}
|
||||
* -public keys to be used to encrypt the message
|
||||
* @param {String} messagetext message text to encrypt
|
||||
* @return {String} a binary string representation of the message
|
||||
* which can be OpenPGP armored
|
||||
*/
|
||||
function write_encrypted_message(publickeys, messagetext) {
|
||||
var result = "";
|
||||
var literal = new openpgp_packet_literaldata().write_packet(messagetext.replace(/\r\n/g, "\n").replace(/\n/g,
|
||||
"\r\n"));
|
||||
util.print_debug_hexstr_dump("literal_packet: |" + literal + "|\n", literal);
|
||||
result = literal;
|
||||
|
||||
// signatures done.. now encryption
|
||||
var sessionkey = openpgp_crypto_generateSessionKey(openpgp.config.config.encryption_cipher);
|
||||
var result2 = "";
|
||||
|
||||
// creating session keys for each recipient
|
||||
for (var i = 0; i < publickeys.length; i++) {
|
||||
var pkey = publickeys[i].getEncryptionKey();
|
||||
if (pkey === null) {
|
||||
util.print_error("no encryption key found! Key is for signing only.");
|
||||
return null;
|
||||
}
|
||||
result2 += new openpgp_packet_encryptedsessionkey().
|
||||
write_pub_key_packet(
|
||||
pkey.getKeyId(),
|
||||
pkey.MPIs,
|
||||
pkey.publicKeyAlgorithm,
|
||||
openpgp.config.config.encryption_cipher,
|
||||
sessionkey);
|
||||
}
|
||||
if (openpgp.config.config.integrity_protect) {
|
||||
result2 += new openpgp_packet_encryptedintegrityprotecteddata().write_packet(openpgp.config.config.encryption_cipher,
|
||||
sessionkey, result);
|
||||
} else {
|
||||
result2 += new openpgp_packet_encrypteddata().write_packet(openpgp.config.config.encryption_cipher, sessionkey,
|
||||
result);
|
||||
}
|
||||
return armor.encode(3, result2, null, null);
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* creates a binary string representation a signed message.
|
||||
* The message will be signed with the specified private key.
|
||||
* @param {Object} privatekey {obj: [openpgp_msg_privatekey]}
|
||||
|
@ -288,7 +171,8 @@ function _openpgp() {
|
|||
* armored(openpgp) and a text representation of the message (text).
|
||||
* This can be directly used to OpenPGP armor the message
|
||||
*/
|
||||
function write_signed_message(privatekey, messagetext) {
|
||||
/*
|
||||
function write_signed_message(privatekey, messagetext) {
|
||||
var sig = new openpgp_packet_signature().write_message_signature(1, messagetext.replace(/\r\n/g, "\n").replace(/\n/,
|
||||
"\r\n"), privatekey);
|
||||
var result = {
|
||||
|
@ -297,15 +181,13 @@ function _openpgp() {
|
|||
hash: sig.hash
|
||||
};
|
||||
return armor.encode(2, result, null, null);
|
||||
}
|
||||
|
||||
this.generateKeyPair = generateKeyPair;
|
||||
this.write_signed_message = write_signed_message;
|
||||
this.signAndEncryptMessage = signAndEncryptMessage;
|
||||
this.decryptAndVerifyMessage = decryptAndVerifyMessage
|
||||
this.encryptMessage = encryptMessage;
|
||||
this.decryptMessage = decryptMessage;
|
||||
|
||||
}
|
||||
*/
|
||||
|
||||
module.exports = new _openpgp();
|
||||
exports.encryptMessage = encryptMessage;
|
||||
exports.signAndEncryptMessage = signAndEncryptMessage;
|
||||
exports.decryptMessage = decryptMessage;
|
||||
exports.decryptAndVerifyMessage = decryptAndVerifyMessage
|
||||
exports.signClearMessage = signClearMessage;
|
||||
exports.verifyClearSignedMessage = verifyClearSignedMessage;
|
||||
exports.generateKeyPair = generateKeyPair;
|
||||
|
|
File diff suppressed because one or more lines are too long
Loading…
Reference in New Issue
Block a user