diff --git a/src/js/ripple/binformat.js b/src/js/ripple/binformat.js index 35f8ce9e..cd5868c3 100644 --- a/src/js/ripple/binformat.js +++ b/src/js/ripple/binformat.js @@ -2,9 +2,6 @@ * Data type map. * * Mapping of type ids to data types. The type id is specified by the high - * - * For reference, see rippled's definition: - * https://github.com/ripple/rippled/blob/develop/src/ripple/data/protocol/SField.cpp */ var TYPES_MAP = exports.types = [ void(0), @@ -378,7 +375,7 @@ exports.ledger = { ['Balance', REQUIRED], ['LowLimit', REQUIRED], ['HighLimit', REQUIRED]]) -}; +} exports.metadata = [ [ 'TransactionIndex' , REQUIRED ], diff --git a/src/js/ripple/serializedtypes.js b/src/js/ripple/serializedtypes.js index 0aa855f1..5eab078f 100644 --- a/src/js/ripple/serializedtypes.js +++ b/src/js/ripple/serializedtypes.js @@ -24,7 +24,6 @@ var Currency = amount.Currency; // Shortcuts var hex = sjcl.codec.hex; var bytes = sjcl.codec.bytes; -var utf8 = sjcl.codec.utf8String; var BigInteger = utils.jsbn.BigInteger; @@ -53,7 +52,7 @@ function isBigInteger(val) { return val instanceof BigInteger; }; -function serializeHex(so, hexData, noLength) { +function serialize_hex(so, hexData, noLength) { var byteData = bytes.fromBits(hex.toBits(hexData)); if (!noLength) { SerializedType.serialize_varint(so, byteData.length); @@ -64,18 +63,10 @@ function serializeHex(so, hexData, noLength) { /** * parses bytes as hex */ -function convertByteArrayToHex (byte_array) { +function convert_bytes_to_hex (byte_array) { return sjcl.codec.hex.fromBits(sjcl.codec.bytes.toBits(byte_array)).toUpperCase(); }; -function convertStringToHex(string) { - return hex.fromBits(utf8.toBits(string)).toUpperCase(); -} - -function convertHexToString(hexString) { - return utf8.fromBits(hex.toBits(hexString)); -} - SerializedType.serialize_varint = function (so, val) { if (val < 0) { throw new Error('Variable integers are unsigned.'); @@ -124,7 +115,7 @@ SerializedType.prototype.parse_varint = function (so) { * * The result is appended to the serialized object ('so'). */ -function convertIntegerToByteArray(val, bytes) { +function append_byte_array(so, val, bytes) { if (!isNumber(val)) { throw new Error('Value is not a number', bytes); } @@ -139,7 +130,7 @@ function convertIntegerToByteArray(val, bytes) { newBytes.unshift(val >>> (i * 8) & 0xff); } - return newBytes; + so.append(newBytes); }; // Convert a certain number of bytes from the serialized object ('so') into an integer. @@ -161,7 +152,7 @@ function readAndSum(so, bytes) { var STInt8 = exports.Int8 = new SerializedType({ serialize: function (so, val) { - so.append(convertIntegerToByteArray(val, 1)); + append_byte_array(so, val, 1); }, parse: function (so) { return readAndSum(so, 1); @@ -172,7 +163,7 @@ STInt8.id = 16; var STInt16 = exports.Int16 = new SerializedType({ serialize: function (so, val) { - so.append(convertIntegerToByteArray(val, 2)); + append_byte_array(so, val, 2); }, parse: function (so) { return readAndSum(so, 2); @@ -183,7 +174,7 @@ STInt16.id = 1; var STInt32 = exports.Int32 = new SerializedType({ serialize: function (so, val) { - so.append(convertIntegerToByteArray(val, 4)); + append_byte_array(so, val, 4); }, parse: function (so) { return readAndSum(so, 4); @@ -226,7 +217,7 @@ var STInt64 = exports.Int64 = new SerializedType({ hex = '0' + hex; } - serializeHex(so, hex, true); //noLength = true + serialize_hex(so, hex, true); //noLength = true }, parse: function (so) { var bytes = so.read(8); @@ -246,7 +237,7 @@ var STHash128 = exports.Hash128 = new SerializedType({ if (!hash.is_valid()) { throw new Error('Invalid Hash128'); } - serializeHex(so, hash.to_hex(), true); //noLength = true + serialize_hex(so, hash.to_hex(), true); //noLength = true }, parse: function (so) { return UInt128.from_bytes(so.read(16)); @@ -261,7 +252,7 @@ var STHash256 = exports.Hash256 = new SerializedType({ if (!hash.is_valid()) { throw new Error('Invalid Hash256'); } - serializeHex(so, hash.to_hex(), true); //noLength = true + serialize_hex(so, hash.to_hex(), true); //noLength = true }, parse: function (so) { return UInt256.from_bytes(so.read(32)); @@ -276,7 +267,7 @@ var STHash160 = exports.Hash160 = new SerializedType({ if (!hash.is_valid()) { throw new Error('Invalid Hash160'); } - serializeHex(so, hash.to_hex(), true); //noLength = true + serialize_hex(so, hash.to_hex(), true); //noLength = true }, parse: function (so) { return UInt160.from_bytes(so.read(20)); @@ -303,7 +294,7 @@ var STCurrency = new SerializedType({ // UInt160 value and consider it valid. But it doesn't, so for the // deserialization to be usable, we need to allow invalid results for now. //if (!currency.is_valid()) { - // throw new Error('Invalid currency: '+convertByteArrayToHex(bytes)); + // throw new Error('Invalid currency: '+convert_bytes_to_hex(bytes)); //} return currency; } @@ -418,16 +409,15 @@ STAmount.id = 6; var STVL = exports.VariableLength = exports.VL = new SerializedType({ serialize: function (so, val) { - if (typeof val === 'string') { - serializeHex(so, val); + serialize_hex(so, val); } else { throw new Error('Unknown datatype.'); } }, parse: function (so) { var len = this.parse_varint(so); - return convertByteArrayToHex(so.read(len)); + return convert_bytes_to_hex(so.read(len)); } }); @@ -439,7 +429,7 @@ var STAccount = exports.Account = new SerializedType({ if (!account.is_valid()) { throw new Error('Invalid account!'); } - serializeHex(so, account.to_hex()); + serialize_hex(so, account.to_hex()); }, parse: function (so) { var len = this.parse_varint(so); @@ -451,6 +441,7 @@ var STAccount = exports.Account = new SerializedType({ var result = UInt160.from_bytes(so.read(len)); result.set_version(Base.VER_ACCOUNT_ID); + //console.log('PARSED 160:', result.to_json()); if (false && !result.is_valid()) { throw new Error('Invalid Account'); } @@ -602,104 +593,6 @@ var STVector256 = exports.Vector256 = new SerializedType({ STVector256.id = 19; -// Internal -var STMemo = exports.STMemo = new SerializedType({ - serialize: function(so, val, no_marker) { - - var keys = []; - - Object.keys(val).forEach(function (key) { - // Ignore lowercase field names - they're non-serializable fields by - // convention. - if (key[0] === key[0].toLowerCase()) { - return; - } - - if (typeof binformat.fieldsInverseMap[key] === 'undefined') { - throw new Error('JSON contains unknown field: "' + key + '"'); - } - - keys.push(key); - }); - - // Sort fields - keys = sort_fields(keys); - - // store that we're dealing with json - var isJson = val.MemoFormat === 'json'; - - for (var i=0; i'); + transaction.addMemo('testkey', 'testvalue'); + transaction.addMemo('testkey2', 'testvalue2'); + transaction.addMemo('testkey3'); + transaction.addMemo(void(0), 'testvalue4'); var expected = [ { Memo: { - MemoType: 'testkey', - MemoData: 'testvalue' + MemoType: new Buffer('testkey').toString('hex'), + MemoData: new Buffer('testvalue').toString('hex') }}, { Memo: { - MemoType: 'testkey2', - MemoData: 'testvalue2' + MemoType: new Buffer('testkey2').toString('hex'), + MemoData: new Buffer('testvalue2').toString('hex') }}, { Memo: { - MemoType: 'testkey3', - MemoFormat: 'text/html' + MemoType: new Buffer('testkey3').toString('hex') }}, { Memo: { - MemoData: 'testvalue4' - }}, - { Memo: { - MemoType: 'testkey4', - MemoFormat: 'text/html', - MemoData: '' - }} + MemoData: new Buffer('testvalue4').toString('hex') + } } ]; assert.deepEqual(transaction.tx_json.Memos, expected); @@ -1144,76 +1086,13 @@ describe('Transaction', function() { }, /^Error: MemoType must be a string$/); }); - it('Add Memo - invalid ASCII MemoType', function() { + it('Add Memo - invalid MemoData', function() { var transaction = new Transaction(); transaction.tx_json.TransactionType = 'Payment'; assert.throws(function() { - transaction.addMemo('한국어'); - }, /^Error: MemoType must be valid ASCII$/); - }); - - it('Add Memo - invalid MemoFormat', function() { - var transaction = new Transaction(); - transaction.tx_json.TransactionType = 'Payment'; - - assert.throws(function() { - transaction.addMemo(void(0), 1); - }, /^Error: MemoFormat must be a string$/); - }); - - it('Add Memo - invalid ASCII MemoFormat', function() { - var transaction = new Transaction(); - transaction.tx_json.TransactionType = 'Payment'; - - assert.throws(function() { - transaction.addMemo(void(0), 'России'); - }, /^Error: MemoFormat must be valid ASCII$/); - }); - - it('Add Memo - MemoData string', function() { - var transaction = new Transaction(); - transaction.tx_json.TransactionType = 'Payment'; - - transaction.addMemo({memoData:'some_string'}); - - assert.deepEqual(transaction.tx_json.Memos, [ - { - Memo: { - MemoData: 'some_string' - } - } - ]); - }); - - it('Add Memo - MemoData complex object', function() { - var transaction = new Transaction(); - transaction.tx_json.TransactionType = 'Payment'; - - var memo = { - memoData: { - string: 'string', - int: 1, - array: [ - { - string: 'string' - } - ], - object: { - string: 'string' - } - } - }; - - transaction.addMemo(memo); - - assert.deepEqual(transaction.tx_json.Memos, [ - { - Memo: { - MemoData: memo.memoData - } - } - ]); + transaction.addMemo('key', 1); + }, /^Error: MemoData must be a string$/); }); it('Construct AccountSet transaction', function() { @@ -1390,7 +1269,7 @@ describe('Transaction', function() { var bid = '1/USD/rsLEU1TPdCJPPysqhWYw9jD97xtG5WqSJm'; var ask = '1/EUR/rsLEU1TPdCJPPysqhWYw9jD97xtG5WqSJm'; assert.throws(function() { - new Transaction().offerCreate('xrsLEU1TPdCJPPysqhWYw9jD97xtG5WqSJm', bid, ask); + var transaction = new Transaction().offerCreate('xrsLEU1TPdCJPPysqhWYw9jD97xtG5WqSJm', bid, ask); }); }); @@ -1423,13 +1302,13 @@ describe('Transaction', function() { it('Construct SetRegularKey transaction - invalid account', function() { assert.throws(function() { - new Transaction().setRegularKey('xrsLEU1TPdCJPPysqhWYw9jD97xtG5WqSJm', 'r36xtKNKR43SeXnGn7kN4r4JdQzcrkqpWe'); + var transaction = new Transaction().setRegularKey('xrsLEU1TPdCJPPysqhWYw9jD97xtG5WqSJm', 'r36xtKNKR43SeXnGn7kN4r4JdQzcrkqpWe'); }); }); it('Construct SetRegularKey transaction - invalid regularKey', function() { assert.throws(function() { - new Transaction().setRegularKey('rsLEU1TPdCJPPysqhWYw9jD97xtG5WqSJm', 'xr36xtKNKR43SeXnGn7kN4r4JdQzcrkqpWe'); + var transaction = new Transaction().setRegularKey('rsLEU1TPdCJPPysqhWYw9jD97xtG5WqSJm', 'xr36xtKNKR43SeXnGn7kN4r4JdQzcrkqpWe'); }); });