Commit cc3fa2ec authored by Adam Cozzette's avatar Adam Cozzette Committed by GitHub

Merge pull request #2676 from acozzette/js-compatibility-tests

JS compatibility tests
parents 4a0dd03e 10ea2513
......@@ -148,8 +148,15 @@ vendor/
# JavaScript artifacts
js/commonjs_out/
js/compatibility_tests/v3.0.0/commonjs_out*
js/compatibility_tests/v3.0.0/protoc
js/compatibility_tests/v3.0.0/testproto_libs1.js
js/compatibility_tests/v3.0.0/testproto_libs1_new.js
js/compatibility_tests/v3.0.0/testproto_libs2.js
js/compatibility_tests/v3.0.0/testproto_libs2_new.js
js/deps.js
js/google-protobuf.js
js/google/
js/node_modules/
js/testproto_libs.js
js/testproto_libs1.js
js/testproto_libs2.js
......@@ -855,6 +855,35 @@ js_EXTRA_DIST= \
js/commonjs/rewrite_tests_for_commonjs.js \
js/commonjs/test6/test6.proto \
js/commonjs/test7/test7.proto \
js/compatibility_tests/v3.0.0/binary/arith_test.js \
js/compatibility_tests/v3.0.0/binary/decoder_test.js \
js/compatibility_tests/v3.0.0/binary/proto_test.js \
js/compatibility_tests/v3.0.0/binary/reader_test.js \
js/compatibility_tests/v3.0.0/binary/utils_test.js \
js/compatibility_tests/v3.0.0/binary/writer_test.js \
js/compatibility_tests/v3.0.0/commonjs/export_asserts.js \
js/compatibility_tests/v3.0.0/commonjs/export_testdeps.js \
js/compatibility_tests/v3.0.0/commonjs/import_test.js \
js/compatibility_tests/v3.0.0/commonjs/jasmine.json \
js/compatibility_tests/v3.0.0/commonjs/rewrite_tests_for_commonjs.js \
js/compatibility_tests/v3.0.0/commonjs/test6/test6.proto \
js/compatibility_tests/v3.0.0/commonjs/test7/test7.proto \
js/compatibility_tests/v3.0.0/data.proto \
js/compatibility_tests/v3.0.0/debug_test.js \
js/compatibility_tests/v3.0.0/jasmine1.json \
js/compatibility_tests/v3.0.0/jasmine2.json \
js/compatibility_tests/v3.0.0/jasmine3.json \
js/compatibility_tests/v3.0.0/message_test.js \
js/compatibility_tests/v3.0.0/proto3_test.js \
js/compatibility_tests/v3.0.0/proto3_test.proto \
js/compatibility_tests/v3.0.0/test2.proto \
js/compatibility_tests/v3.0.0/test3.proto \
js/compatibility_tests/v3.0.0/test4.proto \
js/compatibility_tests/v3.0.0/test5.proto \
js/compatibility_tests/v3.0.0/testbinary.proto \
js/compatibility_tests/v3.0.0/testempty.proto \
js/compatibility_tests/v3.0.0/test.proto \
js/compatibility_tests/v3.0.0/test.sh \
js/data.proto \
js/debug.js \
js/debug_test.js \
......
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
/**
* @fileoverview Test cases for Int64-manipulation functions.
*
* Test suite is written using Jasmine -- see http://jasmine.github.io/
*
* @author cfallin@google.com (Chris Fallin)
*/
goog.require('goog.testing.asserts');
goog.require('jspb.arith.Int64');
goog.require('jspb.arith.UInt64');
describe('binaryArithTest', function() {
/**
* Tests comparison operations.
*/
it('testCompare', function() {
var a = new jspb.arith.UInt64(1234, 5678);
var b = new jspb.arith.UInt64(1234, 5678);
assertEquals(a.cmp(b), 0);
assertEquals(b.cmp(a), 0);
b.lo -= 1;
assertEquals(a.cmp(b), 1);
assertEquals(b.cmp(a), -1);
b.lo += 2;
assertEquals(a.cmp(b), -1);
assertEquals(b.cmp(a), 1);
b.lo = a.lo;
b.hi = a.hi - 1;
assertEquals(a.cmp(b), 1);
assertEquals(b.cmp(a), -1);
assertEquals(a.zero(), false);
assertEquals(a.msb(), false);
assertEquals(a.lsb(), false);
a.hi = 0;
a.lo = 0;
assertEquals(a.zero(), true);
a.hi = 0x80000000;
assertEquals(a.zero(), false);
assertEquals(a.msb(), true);
a.lo = 0x00000001;
assertEquals(a.lsb(), true);
});
/**
* Tests shifts.
*/
it('testShifts', function() {
var a = new jspb.arith.UInt64(1, 0);
assertEquals(a.lo, 1);
assertEquals(a.hi, 0);
var orig = a;
a = a.leftShift();
assertEquals(orig.lo, 1); // original unmodified.
assertEquals(orig.hi, 0);
assertEquals(a.lo, 2);
assertEquals(a.hi, 0);
a = a.leftShift();
assertEquals(a.lo, 4);
assertEquals(a.hi, 0);
for (var i = 0; i < 29; i++) {
a = a.leftShift();
}
assertEquals(a.lo, 0x80000000);
assertEquals(a.hi, 0);
a = a.leftShift();
assertEquals(a.lo, 0);
assertEquals(a.hi, 1);
a = a.leftShift();
assertEquals(a.lo, 0);
assertEquals(a.hi, 2);
a = a.rightShift();
a = a.rightShift();
assertEquals(a.lo, 0x80000000);
assertEquals(a.hi, 0);
a = a.rightShift();
assertEquals(a.lo, 0x40000000);
assertEquals(a.hi, 0);
});
/**
* Tests additions.
*/
it('testAdd', function() {
var a = new jspb.arith.UInt64(/* lo = */ 0x89abcdef,
/* hi = */ 0x01234567);
var b = new jspb.arith.UInt64(/* lo = */ 0xff52ab91,
/* hi = */ 0x92fa2123);
// Addition with carry.
var c = a.add(b);
assertEquals(a.lo, 0x89abcdef); // originals unmodified.
assertEquals(a.hi, 0x01234567);
assertEquals(b.lo, 0xff52ab91);
assertEquals(b.hi, 0x92fa2123);
assertEquals(c.lo, 0x88fe7980);
assertEquals(c.hi, 0x941d668b);
// Simple addition without carry.
a.lo = 2;
a.hi = 0;
b.lo = 3;
b.hi = 0;
c = a.add(b);
assertEquals(c.lo, 5);
assertEquals(c.hi, 0);
});
/**
* Test subtractions.
*/
it('testSub', function() {
var kLength = 10;
var hiValues = [0x1682ef32,
0x583902f7,
0xb62f5955,
0x6ea99bbf,
0x25a39c20,
0x0700a08b,
0x00f7304d,
0x91a5b5af,
0x89077fd2,
0xe09e347c];
var loValues = [0xe1538b18,
0xbeacd556,
0x74100758,
0x96e3cb26,
0x56c37c3f,
0xe00b3f7d,
0x859f25d7,
0xc2ee614a,
0xe1d21cd7,
0x30aae6a4];
for (var i = 0; i < kLength; i++) {
for (var j = 0; j < kLength; j++) {
var a = new jspb.arith.UInt64(loValues[i], hiValues[j]);
var b = new jspb.arith.UInt64(loValues[j], hiValues[i]);
var c = a.add(b).sub(b);
assertEquals(c.hi, a.hi);
assertEquals(c.lo, a.lo);
}
}
});
/**
* Tests 32-by-32 multiplication.
*/
it('testMul32x32', function() {
var testData = [
// a b low(a*b) high(a*b)
[0xc0abe2f8, 0x1607898a, 0x5de711b0, 0x109471b8],
[0x915eb3cb, 0x4fb66d0e, 0xbd0d441a, 0x2d43d0bc],
[0xfe4efe70, 0x80b48c37, 0xbcddea10, 0x7fdada0c],
[0xe222fd4a, 0xe43d524a, 0xd5e0eb64, 0xc99d549c],
[0xd171f469, 0xb94ebd01, 0x4be17969, 0x979bc4fa],
[0x829cc1df, 0xe2598b38, 0xf4157dc8, 0x737c12ad],
[0xf10c3767, 0x8382881e, 0x942b3612, 0x7bd428b8],
[0xb0f6dd24, 0x232597e1, 0x079c98a4, 0x184bbce7],
[0xfcdb05a7, 0x902f55bc, 0x636199a4, 0x8e69f412],
[0x0dd0bfa9, 0x916e27b1, 0x6e2542d9, 0x07d92e65]
];
for (var i = 0; i < testData.length; i++) {
var a = testData[i][0] >>> 0;
var b = testData[i][1] >>> 0;
var cLow = testData[i][2] >>> 0;
var cHigh = testData[i][3] >>> 0;
var c = jspb.arith.UInt64.mul32x32(a, b);
assertEquals(c.lo, cLow);
assertEquals(c.hi, cHigh);
}
});
/**
* Tests 64-by-32 multiplication.
*/
it('testMul', function() {
// 64x32 bits produces 96 bits of product. The multiplication function under
// test truncates the top 32 bits, so we compare against a 64-bit expected
// product.
var testData = [
// low(a) high(a) low(a*b) high(a*b)
[0xec10955b, 0x360eb168, 0x4b7f3f5b, 0xbfcb7c59, 0x9517da5f],
[0x42b000fc, 0x9d101642, 0x6fa1ab72, 0x2584c438, 0x6a9e6d2b],
[0xf42d4fb4, 0xae366403, 0xa65a1000, 0x92434000, 0x1ff978df],
[0x17e2f56b, 0x25487693, 0xf13f98c7, 0x73794e2d, 0xa96b0c6a],
[0x492f241f, 0x76c0eb67, 0x7377ac44, 0xd4336c3c, 0xfc4b1ebe],
[0xd6b92321, 0xe184fa48, 0xd6e76904, 0x93141584, 0xcbf44da1],
[0x4bf007ea, 0x968c0a9e, 0xf5e4026a, 0x4fdb1ae4, 0x61b9fb7d],
[0x10a83be7, 0x2d685ba6, 0xc9e5fb7f, 0x2ad43499, 0x3742473d],
[0x2f261829, 0x1aca681a, 0x3d3494e3, 0x8213205b, 0x283719f8],
[0xe4f2ce21, 0x2e74b7bd, 0xd801b38b, 0xbc17feeb, 0xc6c44e0f]
];
for (var i = 0; i < testData.length; i++) {
var a = new jspb.arith.UInt64(testData[i][0], testData[i][1]);
var prod = a.mul(testData[i][2]);
assertEquals(prod.lo, testData[i][3]);
assertEquals(prod.hi, testData[i][4]);
}
});
/**
* Tests 64-div-by-32 division.
*/
it('testDiv', function() {
// Compute a/b, yielding quot = a/b and rem = a%b.
var testData = [
// --- divisors in (0, 2^32-1) to test full divisor range
// low(a) high(a) b low(quot) high(quot) rem
[0x712443f1, 0xe85cefcc, 0xc1a7050b, 0x332c79ad, 0x00000001, 0x92ffa882],
[0x11912915, 0xb2699eb5, 0x30467cbe, 0xb21b4be4, 0x00000003, 0x283465dd],
[0x0d917982, 0x201f2a6e, 0x3f35bf03, 0x8217c8e4, 0x00000000, 0x153402d6],
[0xa072c108, 0x74020c96, 0xc60568fd, 0x95f9613e, 0x00000000, 0x3f4676c2],
[0xd845d5d8, 0xcdd235c4, 0x20426475, 0x6154e78b, 0x00000006, 0x202fb751],
[0xa4dbf71f, 0x9e90465e, 0xf08e022f, 0xa8be947f, 0x00000000, 0xbe43b5ce],
[0x3dbe627f, 0xa791f4b9, 0x28a5bd89, 0x1f5dfe93, 0x00000004, 0x02bf9ed4],
[0x5c1c53ee, 0xccf5102e, 0x198576e7, 0x07e3ae31, 0x00000008, 0x02ea8fb7],
[0xfef1e581, 0x04714067, 0xca6540c1, 0x059e73ec, 0x00000000, 0x31658095],
[0x1e2dd90c, 0x13dd6667, 0x8b2184c3, 0x248d1a42, 0x00000000, 0x4ca6d0c6],
// --- divisors in (0, 2^16-1) to test larger quotient high-words
// low(a) high(a) b low(quot) high(quot) rem
[0x86722b47, 0x2cd57c9a, 0x00003123, 0x2ae41b7a, 0x0000e995, 0x00000f99],
[0x1dd7884c, 0xf5e839bc, 0x00009eeb, 0x5c886242, 0x00018c21, 0x000099b6],
[0x5c53d625, 0x899fc7e5, 0x000087d7, 0xd625007a, 0x0001035c, 0x000019af],
[0x6932d932, 0x9d0a5488, 0x000051fb, 0x9d976143, 0x0001ea63, 0x00004981],
[0x4d18bb85, 0x0c92fb31, 0x00001d9f, 0x03265ab4, 0x00006cac, 0x000001b9],
[0xbe756768, 0xdea67ccb, 0x00008a03, 0x58add442, 0x00019cff, 0x000056a2],
[0xe2466f9a, 0x2521f114, 0x0000c350, 0xa0c0860d, 0x000030ab, 0x0000a48a],
[0xf00ddad1, 0xe2f5446a, 0x00002cfc, 0x762697a6, 0x00050b96, 0x00000b69],
[0xa879152a, 0x0a70e0a5, 0x00007cdf, 0xb44151b3, 0x00001567, 0x0000363d],
[0x7179a74c, 0x46083fff, 0x0000253c, 0x4d39ba6e, 0x0001e17f, 0x00000f84]
];
for (var i = 0; i < testData.length; i++) {
var a = new jspb.arith.UInt64(testData[i][0], testData[i][1]);
var result = a.div(testData[i][2]);
var quotient = result[0];
var remainder = result[1];
assertEquals(quotient.lo, testData[i][3]);
assertEquals(quotient.hi, testData[i][4]);
assertEquals(remainder.lo, testData[i][5]);
}
});
/**
* Tests .toString() and .fromString().
*/
it('testStrings', function() {
var testData = [
[0x5e84c935, 0xcae33d0e, '14619595947299359029'],
[0x62b3b8b8, 0x93480544, '10612738313170434232'],
[0x319bfb13, 0xc01c4172, '13843011313344445203'],
[0x5b8a65fb, 0xa5885b31, '11927883880638080507'],
[0x6bdb80f1, 0xb0d1b16b, '12741159895737008369'],
[0x4b82b442, 0x2e0d8c97, '3318463081876730946'],
[0x780d5208, 0x7d76752c, '9040542135845999112'],
[0x2e46800f, 0x0993778d, '690026616168284175'],
[0xf00a7e32, 0xcd8e3931, '14811839111111540274'],
[0x1baeccd6, 0x923048c4, '10533999535534820566'],
[0x03669d29, 0xbff3ab72, '13831587386756603177'],
[0x2526073e, 0x01affc81, '121593346566522686'],
[0xc24244e0, 0xd7f40d0e, '15561076969511732448'],
[0xc56a341e, 0xa68b66a7, '12000798502816461854'],
[0x8738d64d, 0xbfe78604, '13828168534871037517'],
[0x5baff03b, 0xd7572aea, '15516918227177304123'],
[0x4a843d8a, 0x864e132b, '9677693725920476554'],
[0x25b4e94d, 0x22b54dc6, '2500990681505655117'],
[0x6bbe664b, 0x55a5cc0e, '6171563226690381387'],
[0xee916c81, 0xb00aabb3, '12685140089732426881']
];
for (var i = 0; i < testData.length; i++) {
var a = new jspb.arith.UInt64(testData[i][0], testData[i][1]);
var roundtrip = jspb.arith.UInt64.fromString(a.toString());
assertEquals(roundtrip.lo, a.lo);
assertEquals(roundtrip.hi, a.hi);
assertEquals(a.toString(), testData[i][2]);
}
});
/**
* Tests signed Int64s. These are built on UInt64s, so we only need to test
* the explicit overrides: .toString() and .fromString().
*/
it('testSignedInt64', function() {
var testStrings = [
'-7847499644178593666',
'3771946501229139523',
'2872856549054995060',
'-5780049594274350904',
'3383785956695105201',
'2973055184857072610',
'-3879428459215627206',
'4589812431064156631',
'8484075557333689940',
'1075325817098092407',
'-4346697501012292314',
'2488620459718316637',
'6112655187423520672',
'-3655278273928612104',
'3439154019435803196',
'1004112478843763757',
'-6587790776614368413',
'664320065099714586',
'4760412909973292912',
'-7911903989602274672'
];
for (var i = 0; i < testStrings.length; i++) {
var roundtrip =
jspb.arith.Int64.fromString(testStrings[i]).toString();
assertEquals(roundtrip, testStrings[i]);
}
});
});
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
/**
* @fileoverview Test cases for jspb's binary protocol buffer decoder.
*
* There are two particular magic numbers that need to be pointed out -
* 2^64-1025 is the largest number representable as both a double and an
* unsigned 64-bit integer, and 2^63-513 is the largest number representable as
* both a double and a signed 64-bit integer.
*
* Test suite is written using Jasmine -- see http://jasmine.github.io/
*
* @author aappleby@google.com (Austin Appleby)
*/
goog.require('goog.testing.asserts');
goog.require('jspb.BinaryConstants');
goog.require('jspb.BinaryDecoder');
goog.require('jspb.BinaryEncoder');
/**
* Tests encoding and decoding of unsigned types.
* @param {Function} readValue
* @param {Function} writeValue
* @param {number} epsilon
* @param {number} upperLimit
* @param {Function} filter
* @suppress {missingProperties|visibility}
*/
function doTestUnsignedValue(readValue,
writeValue, epsilon, upperLimit, filter) {
var encoder = new jspb.BinaryEncoder();
// Encode zero and limits.
writeValue.call(encoder, filter(0));
writeValue.call(encoder, filter(epsilon));
writeValue.call(encoder, filter(upperLimit));
// Encode positive values.
for (var cursor = epsilon; cursor < upperLimit; cursor *= 1.1) {
writeValue.call(encoder, filter(cursor));
}
var decoder = jspb.BinaryDecoder.alloc(encoder.end());
// Check zero and limits.
assertEquals(filter(0), readValue.call(decoder));
assertEquals(filter(epsilon), readValue.call(decoder));
assertEquals(filter(upperLimit), readValue.call(decoder));
// Check positive values.
for (var cursor = epsilon; cursor < upperLimit; cursor *= 1.1) {
if (filter(cursor) != readValue.call(decoder)) throw 'fail!';
}
// Encoding values outside the valid range should assert.
assertThrows(function() {writeValue.call(encoder, -1);});
assertThrows(function() {writeValue.call(encoder, upperLimit * 1.1);});
}
/**
* Tests encoding and decoding of signed types.
* @param {Function} readValue
* @param {Function} writeValue
* @param {number} epsilon
* @param {number} lowerLimit
* @param {number} upperLimit
* @param {Function} filter
* @suppress {missingProperties}
*/
function doTestSignedValue(readValue,
writeValue, epsilon, lowerLimit, upperLimit, filter) {
var encoder = new jspb.BinaryEncoder();
// Encode zero and limits.
writeValue.call(encoder, filter(lowerLimit));
writeValue.call(encoder, filter(-epsilon));
writeValue.call(encoder, filter(0));
writeValue.call(encoder, filter(epsilon));
writeValue.call(encoder, filter(upperLimit));
var inputValues = [];
// Encode negative values.
for (var cursor = lowerLimit; cursor < -epsilon; cursor /= 1.1) {
var val = filter(cursor);
writeValue.call(encoder, val);
inputValues.push(val);
}
// Encode positive values.
for (var cursor = epsilon; cursor < upperLimit; cursor *= 1.1) {
var val = filter(cursor);
writeValue.call(encoder, val);
inputValues.push(val);
}
var decoder = jspb.BinaryDecoder.alloc(encoder.end());
// Check zero and limits.
assertEquals(filter(lowerLimit), readValue.call(decoder));
assertEquals(filter(-epsilon), readValue.call(decoder));
assertEquals(filter(0), readValue.call(decoder));
assertEquals(filter(epsilon), readValue.call(decoder));
assertEquals(filter(upperLimit), readValue.call(decoder));
// Verify decoded values.
for (var i = 0; i < inputValues.length; i++) {
assertEquals(inputValues[i], readValue.call(decoder));
}
// Encoding values outside the valid range should assert.
assertThrows(function() {writeValue.call(encoder, lowerLimit * 1.1);});
assertThrows(function() {writeValue.call(encoder, upperLimit * 1.1);});
}
describe('binaryDecoderTest', function() {
/**
* Tests the decoder instance cache.
*/
it('testInstanceCache', /** @suppress {visibility} */ function() {
// Empty the instance caches.
jspb.BinaryDecoder.instanceCache_ = [];
// Allocating and then freeing a decoder should put it in the instance
// cache.
jspb.BinaryDecoder.alloc().free();
assertEquals(1, jspb.BinaryDecoder.instanceCache_.length);
// Allocating and then freeing three decoders should leave us with three in
// the cache.
var decoder1 = jspb.BinaryDecoder.alloc();
var decoder2 = jspb.BinaryDecoder.alloc();
var decoder3 = jspb.BinaryDecoder.alloc();
decoder1.free();
decoder2.free();
decoder3.free();
assertEquals(3, jspb.BinaryDecoder.instanceCache_.length);
});
/**
* Tests reading 64-bit integers as hash strings.
*/
it('testHashStrings', function() {
var encoder = new jspb.BinaryEncoder();
var hashA = String.fromCharCode(0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00);
var hashB = String.fromCharCode(0x12, 0x34, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00);
var hashC = String.fromCharCode(0x12, 0x34, 0x56, 0x78,
0x87, 0x65, 0x43, 0x21);
var hashD = String.fromCharCode(0xFF, 0xFF, 0xFF, 0xFF,
0xFF, 0xFF, 0xFF, 0xFF);
encoder.writeVarintHash64(hashA);
encoder.writeVarintHash64(hashB);
encoder.writeVarintHash64(hashC);
encoder.writeVarintHash64(hashD);
encoder.writeFixedHash64(hashA);
encoder.writeFixedHash64(hashB);
encoder.writeFixedHash64(hashC);
encoder.writeFixedHash64(hashD);
var decoder = jspb.BinaryDecoder.alloc(encoder.end());
assertEquals(hashA, decoder.readVarintHash64());
assertEquals(hashB, decoder.readVarintHash64());
assertEquals(hashC, decoder.readVarintHash64());
assertEquals(hashD, decoder.readVarintHash64());
assertEquals(hashA, decoder.readFixedHash64());
assertEquals(hashB, decoder.readFixedHash64());
assertEquals(hashC, decoder.readFixedHash64());
assertEquals(hashD, decoder.readFixedHash64());
});
/**
* Verifies that misuse of the decoder class triggers assertions.
* @suppress {checkTypes|visibility}
*/
it('testDecodeErrors', function() {
// Reading a value past the end of the stream should trigger an assertion.
var decoder = jspb.BinaryDecoder.alloc([0, 1, 2]);
assertThrows(function() {decoder.readUint64()});
// Overlong varints should trigger assertions.
decoder.setBlock([255, 255, 255, 255, 255, 255,
255, 255, 255, 255, 255, 0]);
assertThrows(function() {decoder.readUnsignedVarint64()});
decoder.reset();
assertThrows(function() {decoder.readSignedVarint64()});
decoder.reset();
assertThrows(function() {decoder.readZigzagVarint64()});
// Positive 32-bit varints encoded with 1 bits in positions 33 through 35
// should trigger assertions.
decoder.setBlock([255, 255, 255, 255, 0x1F]);
assertThrows(function() {decoder.readUnsignedVarint32()});
decoder.setBlock([255, 255, 255, 255, 0x2F]);
assertThrows(function() {decoder.readUnsignedVarint32()});
decoder.setBlock([255, 255, 255, 255, 0x4F]);
assertThrows(function() {decoder.readUnsignedVarint32()});
// Negative 32-bit varints encoded with non-1 bits in the high dword should
// trigger assertions.
decoder.setBlock([255, 255, 255, 255, 255, 255, 0, 255, 255, 1]);
assertThrows(function() {decoder.readUnsignedVarint32()});
decoder.setBlock([255, 255, 255, 255, 255, 255, 255, 255, 255, 0]);
assertThrows(function() {decoder.readUnsignedVarint32()});
});
/**
* Tests encoding and decoding of unsigned integers.
*/
it('testUnsignedIntegers', function() {
doTestUnsignedValue(
jspb.BinaryDecoder.prototype.readUint8,
jspb.BinaryEncoder.prototype.writeUint8,
1, 0xFF, Math.round);
doTestUnsignedValue(
jspb.BinaryDecoder.prototype.readUint16,
jspb.BinaryEncoder.prototype.writeUint16,
1, 0xFFFF, Math.round);
doTestUnsignedValue(
jspb.BinaryDecoder.prototype.readUint32,
jspb.BinaryEncoder.prototype.writeUint32,
1, 0xFFFFFFFF, Math.round);
doTestUnsignedValue(
jspb.BinaryDecoder.prototype.readUint64,
jspb.BinaryEncoder.prototype.writeUint64,
1, Math.pow(2, 64) - 1025, Math.round);
});
/**
* Tests encoding and decoding of signed integers.
*/
it('testSignedIntegers', function() {
doTestSignedValue(
jspb.BinaryDecoder.prototype.readInt8,
jspb.BinaryEncoder.prototype.writeInt8,
1, -0x80, 0x7F, Math.round);
doTestSignedValue(
jspb.BinaryDecoder.prototype.readInt16,
jspb.BinaryEncoder.prototype.writeInt16,
1, -0x8000, 0x7FFF, Math.round);
doTestSignedValue(
jspb.BinaryDecoder.prototype.readInt32,
jspb.BinaryEncoder.prototype.writeInt32,
1, -0x80000000, 0x7FFFFFFF, Math.round);
doTestSignedValue(
jspb.BinaryDecoder.prototype.readInt64,
jspb.BinaryEncoder.prototype.writeInt64,
1, -Math.pow(2, 63), Math.pow(2, 63) - 513, Math.round);
});
/**
* Tests encoding and decoding of floats.
*/
it('testFloats', function() {
/**
* @param {number} x
* @return {number}
*/
function truncate(x) {
var temp = new Float32Array(1);
temp[0] = x;
return temp[0];
}
doTestSignedValue(
jspb.BinaryDecoder.prototype.readFloat,
jspb.BinaryEncoder.prototype.writeFloat,
jspb.BinaryConstants.FLOAT32_EPS,
-jspb.BinaryConstants.FLOAT32_MAX,
jspb.BinaryConstants.FLOAT32_MAX,
truncate);
doTestSignedValue(
jspb.BinaryDecoder.prototype.readDouble,
jspb.BinaryEncoder.prototype.writeDouble,
jspb.BinaryConstants.FLOAT64_EPS * 10,
-jspb.BinaryConstants.FLOAT64_MAX,
jspb.BinaryConstants.FLOAT64_MAX,
function(x) { return x; });
});
});
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Test suite is written using Jasmine -- see http://jasmine.github.io/
goog.require('goog.crypt.base64');
goog.require('goog.testing.asserts');
goog.require('jspb.Message');
// CommonJS-LoadFromFile: ../testbinary_pb proto.jspb.test
goog.require('proto.jspb.test.ExtendsWithMessage');
goog.require('proto.jspb.test.ForeignEnum');
goog.require('proto.jspb.test.ForeignMessage');
goog.require('proto.jspb.test.TestAllTypes');
goog.require('proto.jspb.test.TestExtendable');
goog.require('proto.jspb.test.extendOptionalBool');
goog.require('proto.jspb.test.extendOptionalBytes');
goog.require('proto.jspb.test.extendOptionalDouble');
goog.require('proto.jspb.test.extendOptionalFixed32');
goog.require('proto.jspb.test.extendOptionalFixed64');
goog.require('proto.jspb.test.extendOptionalFloat');
goog.require('proto.jspb.test.extendOptionalForeignEnum');
goog.require('proto.jspb.test.extendOptionalInt32');
goog.require('proto.jspb.test.extendOptionalInt64');
goog.require('proto.jspb.test.extendOptionalSfixed32');
goog.require('proto.jspb.test.extendOptionalSfixed64');
goog.require('proto.jspb.test.extendOptionalSint32');
goog.require('proto.jspb.test.extendOptionalSint64');
goog.require('proto.jspb.test.extendOptionalString');
goog.require('proto.jspb.test.extendOptionalUint32');
goog.require('proto.jspb.test.extendOptionalUint64');
goog.require('proto.jspb.test.extendPackedRepeatedBoolList');
goog.require('proto.jspb.test.extendPackedRepeatedDoubleList');
goog.require('proto.jspb.test.extendPackedRepeatedFixed32List');
goog.require('proto.jspb.test.extendPackedRepeatedFixed64List');
goog.require('proto.jspb.test.extendPackedRepeatedFloatList');
goog.require('proto.jspb.test.extendPackedRepeatedForeignEnumList');
goog.require('proto.jspb.test.extendPackedRepeatedInt32List');
goog.require('proto.jspb.test.extendPackedRepeatedInt64List');
goog.require('proto.jspb.test.extendPackedRepeatedSfixed32List');
goog.require('proto.jspb.test.extendPackedRepeatedSfixed64List');
goog.require('proto.jspb.test.extendPackedRepeatedSint32List');
goog.require('proto.jspb.test.extendPackedRepeatedSint64List');
goog.require('proto.jspb.test.extendPackedRepeatedUint32List');
goog.require('proto.jspb.test.extendPackedRepeatedUint64List');
goog.require('proto.jspb.test.extendRepeatedBoolList');
goog.require('proto.jspb.test.extendRepeatedBytesList');
goog.require('proto.jspb.test.extendRepeatedDoubleList');
goog.require('proto.jspb.test.extendRepeatedFixed32List');
goog.require('proto.jspb.test.extendRepeatedFixed64List');
goog.require('proto.jspb.test.extendRepeatedFloatList');
goog.require('proto.jspb.test.extendRepeatedForeignEnumList');
goog.require('proto.jspb.test.extendRepeatedInt32List');
goog.require('proto.jspb.test.extendRepeatedInt64List');
goog.require('proto.jspb.test.extendRepeatedSfixed32List');
goog.require('proto.jspb.test.extendRepeatedSfixed64List');
goog.require('proto.jspb.test.extendRepeatedSint32List');
goog.require('proto.jspb.test.extendRepeatedSint64List');
goog.require('proto.jspb.test.extendRepeatedStringList');
goog.require('proto.jspb.test.extendRepeatedUint32List');
goog.require('proto.jspb.test.extendRepeatedUint64List');
var suite = {};
var BYTES = new Uint8Array([1, 2, 8, 9]);
var BYTES_B64 = goog.crypt.base64.encodeByteArray(BYTES);
/**
* Helper: fill all fields on a TestAllTypes message.
* @param {proto.jspb.test.TestAllTypes} msg
*/
function fillAllFields(msg) {
msg.setOptionalInt32(-42);
// can be exactly represented by JS number (64-bit double, i.e., 52-bit
// mantissa).
msg.setOptionalInt64(-0x7fffffff00000000);
msg.setOptionalUint32(0x80000000);
msg.setOptionalUint64(0xf000000000000000);
msg.setOptionalSint32(-100);
msg.setOptionalSint64(-0x8000000000000000);
msg.setOptionalFixed32(1234);
msg.setOptionalFixed64(0x1234567800000000);
msg.setOptionalSfixed32(-1234);
msg.setOptionalSfixed64(-0x1234567800000000);
msg.setOptionalFloat(1.5);
msg.setOptionalDouble(-1.5);
msg.setOptionalBool(true);
msg.setOptionalString('hello world');
msg.setOptionalBytes(BYTES);
msg.setOptionalGroup(new proto.jspb.test.TestAllTypes.OptionalGroup());
msg.getOptionalGroup().setA(100);
var submsg = new proto.jspb.test.ForeignMessage();
submsg.setC(16);
msg.setOptionalForeignMessage(submsg);
msg.setOptionalForeignEnum(proto.jspb.test.ForeignEnum.FOREIGN_FOO);
msg.setOneofString('oneof');
msg.setRepeatedInt32List([-42]);
msg.setRepeatedInt64List([-0x7fffffff00000000]);
msg.setRepeatedUint32List([0x80000000]);
msg.setRepeatedUint64List([0xf000000000000000]);
msg.setRepeatedSint32List([-100]);
msg.setRepeatedSint64List([-0x8000000000000000]);
msg.setRepeatedFixed32List([1234]);
msg.setRepeatedFixed64List([0x1234567800000000]);
msg.setRepeatedSfixed32List([-1234]);
msg.setRepeatedSfixed64List([-0x1234567800000000]);
msg.setRepeatedFloatList([1.5]);
msg.setRepeatedDoubleList([-1.5]);
msg.setRepeatedBoolList([true]);
msg.setRepeatedStringList(['hello world']);
msg.setRepeatedBytesList([BYTES, BYTES]);
msg.setRepeatedGroupList([new proto.jspb.test.TestAllTypes.RepeatedGroup()]);
msg.getRepeatedGroupList()[0].setA(100);
submsg = new proto.jspb.test.ForeignMessage();
submsg.setC(1000);
msg.setRepeatedForeignMessageList([submsg]);
msg.setRepeatedForeignEnumList([proto.jspb.test.ForeignEnum.FOREIGN_FOO]);
msg.setPackedRepeatedInt32List([-42]);
msg.setPackedRepeatedInt64List([-0x7fffffff00000000]);
msg.setPackedRepeatedUint32List([0x80000000]);
msg.setPackedRepeatedUint64List([0xf000000000000000]);
msg.setPackedRepeatedSint32List([-100]);
msg.setPackedRepeatedSint64List([-0x8000000000000000]);
msg.setPackedRepeatedFixed32List([1234]);
msg.setPackedRepeatedFixed64List([0x1234567800000000]);
msg.setPackedRepeatedSfixed32List([-1234]);
msg.setPackedRepeatedSfixed64List([-0x1234567800000000]);
msg.setPackedRepeatedFloatList([1.5]);
msg.setPackedRepeatedDoubleList([-1.5]);
msg.setPackedRepeatedBoolList([true]);
}
/**
* Helper: compare a bytes field to an expected value
* @param {Uint8Array|string} arr
* @param {Uint8Array} expected
* @return {boolean}
*/
function bytesCompare(arr, expected) {
if (goog.isString(arr)) {
arr = goog.crypt.base64.decodeStringToUint8Array(arr);
}
if (arr.length != expected.length) {
return false;
}
for (var i = 0; i < arr.length; i++) {
if (arr[i] != expected[i]) {
return false;
}
}
return true;
}
/**
* Helper: verify contents of given TestAllTypes message as set by
* fillAllFields().
* @param {proto.jspb.test.TestAllTypes} original
* @param {proto.jspb.test.TestAllTypes} copy
*/
function checkAllFields(original, copy) {
assertTrue(jspb.Message.equals(original, copy));
assertEquals(copy.getOptionalInt32(), -42);
assertEquals(copy.getOptionalInt64(), -0x7fffffff00000000);
assertEquals(copy.getOptionalUint32(), 0x80000000);
assertEquals(copy.getOptionalUint64(), 0xf000000000000000);
assertEquals(copy.getOptionalSint32(), -100);
assertEquals(copy.getOptionalSint64(), -0x8000000000000000);
assertEquals(copy.getOptionalFixed32(), 1234);
assertEquals(copy.getOptionalFixed64(), 0x1234567800000000);
assertEquals(copy.getOptionalSfixed32(), -1234);
assertEquals(copy.getOptionalSfixed64(), -0x1234567800000000);
assertEquals(copy.getOptionalFloat(), 1.5);
assertEquals(copy.getOptionalDouble(), -1.5);
assertEquals(copy.getOptionalBool(), true);
assertEquals(copy.getOptionalString(), 'hello world');
assertEquals(true, bytesCompare(copy.getOptionalBytes(), BYTES));
assertEquals(true, bytesCompare(copy.getOptionalBytes_asU8(), BYTES));
assertEquals(
copy.getOptionalBytes_asB64(), goog.crypt.base64.encodeByteArray(BYTES));
assertEquals(copy.getOptionalGroup().getA(), 100);
assertEquals(copy.getOptionalForeignMessage().getC(), 16);
assertEquals(copy.getOptionalForeignEnum(),
proto.jspb.test.ForeignEnum.FOREIGN_FOO);
assertEquals(copy.getOneofString(), 'oneof');
assertEquals(copy.getOneofFieldCase(),
proto.jspb.test.TestAllTypes.OneofFieldCase.ONEOF_STRING);
assertElementsEquals(copy.getRepeatedInt32List(), [-42]);
assertElementsEquals(copy.getRepeatedInt64List(), [-0x7fffffff00000000]);
assertElementsEquals(copy.getRepeatedUint32List(), [0x80000000]);
assertElementsEquals(copy.getRepeatedUint64List(), [0xf000000000000000]);
assertElementsEquals(copy.getRepeatedSint32List(), [-100]);
assertElementsEquals(copy.getRepeatedSint64List(), [-0x8000000000000000]);
assertElementsEquals(copy.getRepeatedFixed32List(), [1234]);
assertElementsEquals(copy.getRepeatedFixed64List(), [0x1234567800000000]);
assertElementsEquals(copy.getRepeatedSfixed32List(), [-1234]);
assertElementsEquals(copy.getRepeatedSfixed64List(), [-0x1234567800000000]);
assertElementsEquals(copy.getRepeatedFloatList(), [1.5]);
assertElementsEquals(copy.getRepeatedDoubleList(), [-1.5]);
assertElementsEquals(copy.getRepeatedBoolList(), [true]);
assertElementsEquals(copy.getRepeatedStringList(), ['hello world']);
assertEquals(copy.getRepeatedBytesList().length, 2);
assertEquals(true, bytesCompare(copy.getRepeatedBytesList_asU8()[0], BYTES));
assertEquals(true, bytesCompare(copy.getRepeatedBytesList()[0], BYTES));
assertEquals(true, bytesCompare(copy.getRepeatedBytesList_asU8()[1], BYTES));
assertEquals(copy.getRepeatedBytesList_asB64()[0], BYTES_B64);
assertEquals(copy.getRepeatedBytesList_asB64()[1], BYTES_B64);
assertEquals(copy.getRepeatedGroupList().length, 1);
assertEquals(copy.getRepeatedGroupList()[0].getA(), 100);
assertEquals(copy.getRepeatedForeignMessageList().length, 1);
assertEquals(copy.getRepeatedForeignMessageList()[0].getC(), 1000);
assertElementsEquals(copy.getRepeatedForeignEnumList(),
[proto.jspb.test.ForeignEnum.FOREIGN_FOO]);
assertElementsEquals(copy.getPackedRepeatedInt32List(), [-42]);
assertElementsEquals(copy.getPackedRepeatedInt64List(),
[-0x7fffffff00000000]);
assertElementsEquals(copy.getPackedRepeatedUint32List(), [0x80000000]);
assertElementsEquals(copy.getPackedRepeatedUint64List(),
[0xf000000000000000]);
assertElementsEquals(copy.getPackedRepeatedSint32List(), [-100]);
assertElementsEquals(copy.getPackedRepeatedSint64List(),
[-0x8000000000000000]);
assertElementsEquals(copy.getPackedRepeatedFixed32List(), [1234]);
assertElementsEquals(copy.getPackedRepeatedFixed64List(),
[0x1234567800000000]);
assertElementsEquals(copy.getPackedRepeatedSfixed32List(), [-1234]);
assertElementsEquals(copy.getPackedRepeatedSfixed64List(),
[-0x1234567800000000]);
assertElementsEquals(copy.getPackedRepeatedFloatList(), [1.5]);
assertElementsEquals(copy.getPackedRepeatedDoubleList(), [-1.5]);
}
/**
* Helper: verify that all expected extensions are present.
* @param {!proto.jspb.test.TestExtendable} msg
*/
function checkExtensions(msg) {
assertEquals(-42,
msg.getExtension(proto.jspb.test.extendOptionalInt32));
assertEquals(-0x7fffffff00000000,
msg.getExtension(proto.jspb.test.extendOptionalInt64));
assertEquals(0x80000000,
msg.getExtension(proto.jspb.test.extendOptionalUint32));
assertEquals(0xf000000000000000,
msg.getExtension(proto.jspb.test.extendOptionalUint64));
assertEquals(-100,
msg.getExtension(proto.jspb.test.extendOptionalSint32));
assertEquals(-0x8000000000000000,
msg.getExtension(proto.jspb.test.extendOptionalSint64));
assertEquals(1234,
msg.getExtension(proto.jspb.test.extendOptionalFixed32));
assertEquals(0x1234567800000000,
msg.getExtension(proto.jspb.test.extendOptionalFixed64));
assertEquals(-1234,
msg.getExtension(proto.jspb.test.extendOptionalSfixed32));
assertEquals(-0x1234567800000000,
msg.getExtension(proto.jspb.test.extendOptionalSfixed64));
assertEquals(1.5,
msg.getExtension(proto.jspb.test.extendOptionalFloat));
assertEquals(-1.5,
msg.getExtension(proto.jspb.test.extendOptionalDouble));
assertEquals(true,
msg.getExtension(proto.jspb.test.extendOptionalBool));
assertEquals('hello world',
msg.getExtension(proto.jspb.test.extendOptionalString));
assertEquals(
true, bytesCompare(
msg.getExtension(proto.jspb.test.extendOptionalBytes), BYTES));
assertEquals(16,
msg.getExtension(
proto.jspb.test.ExtendsWithMessage.optionalExtension).getFoo());
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendRepeatedInt32List),
[-42]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendRepeatedInt64List),
[-0x7fffffff00000000]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendRepeatedUint32List),
[0x80000000]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendRepeatedUint64List),
[0xf000000000000000]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendRepeatedSint32List),
[-100]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendRepeatedSint64List),
[-0x8000000000000000]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendRepeatedFixed32List),
[1234]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendRepeatedFixed64List),
[0x1234567800000000]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendRepeatedSfixed32List),
[-1234]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendRepeatedSfixed64List),
[-0x1234567800000000]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendRepeatedFloatList),
[1.5]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendRepeatedDoubleList),
[-1.5]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendRepeatedBoolList),
[true]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendRepeatedStringList),
['hello world']);
assertEquals(
true,
bytesCompare(
msg.getExtension(proto.jspb.test.extendRepeatedBytesList)[0], BYTES));
assertEquals(1000,
msg.getExtension(
proto.jspb.test.ExtendsWithMessage.repeatedExtensionList)[0]
.getFoo());
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendRepeatedForeignEnumList),
[proto.jspb.test.ForeignEnum.FOREIGN_FOO]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendPackedRepeatedInt32List),
[-42]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendPackedRepeatedInt64List),
[-0x7fffffff00000000]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendPackedRepeatedUint32List),
[0x80000000]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendPackedRepeatedUint64List),
[0xf000000000000000]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendPackedRepeatedSint32List),
[-100]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendPackedRepeatedSint64List),
[-0x8000000000000000]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendPackedRepeatedFixed32List),
[1234]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendPackedRepeatedFixed64List),
[0x1234567800000000]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendPackedRepeatedSfixed32List),
[-1234]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendPackedRepeatedSfixed64List),
[-0x1234567800000000]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendPackedRepeatedFloatList),
[1.5]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendPackedRepeatedDoubleList),
[-1.5]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendPackedRepeatedBoolList),
[true]);
assertElementsEquals(
msg.getExtension(proto.jspb.test.extendPackedRepeatedForeignEnumList),
[proto.jspb.test.ForeignEnum.FOREIGN_FOO]);
}
describe('protoBinaryTest', function() {
/**
* Tests a basic serialization-deserializaton round-trip with all supported
* field types (on the TestAllTypes message type).
*/
it('testRoundTrip', function() {
var msg = new proto.jspb.test.TestAllTypes();
fillAllFields(msg);
var encoded = msg.serializeBinary();
var decoded = proto.jspb.test.TestAllTypes.deserializeBinary(encoded);
checkAllFields(msg, decoded);
});
/**
* Test that base64 string and Uint8Array are interchangeable in bytes fields.
*/
it('testBytesFieldsGettersInterop', function() {
var msg = new proto.jspb.test.TestAllTypes();
// Set from a base64 string and check all the getters work.
msg.setOptionalBytes(BYTES_B64);
assertTrue(bytesCompare(msg.getOptionalBytes_asU8(), BYTES));
assertTrue(bytesCompare(msg.getOptionalBytes_asB64(), BYTES));
assertTrue(bytesCompare(msg.getOptionalBytes(), BYTES));
// Test binary serialize round trip doesn't break it.
msg = proto.jspb.test.TestAllTypes.deserializeBinary(msg.serializeBinary());
assertTrue(bytesCompare(msg.getOptionalBytes_asU8(), BYTES));
assertTrue(bytesCompare(msg.getOptionalBytes_asB64(), BYTES));
assertTrue(bytesCompare(msg.getOptionalBytes(), BYTES));
msg = new proto.jspb.test.TestAllTypes();
// Set from a Uint8Array and check all the getters work.
msg.setOptionalBytes(BYTES);
assertTrue(bytesCompare(msg.getOptionalBytes_asU8(), BYTES));
assertTrue(bytesCompare(msg.getOptionalBytes_asB64(), BYTES));
assertTrue(bytesCompare(msg.getOptionalBytes(), BYTES));
});
/**
* Test that bytes setters will receive result of any of the getters.
*/
it('testBytesFieldsSettersInterop', function() {
var msg = new proto.jspb.test.TestAllTypes();
msg.setOptionalBytes(BYTES);
assertTrue(bytesCompare(msg.getOptionalBytes(), BYTES));
msg.setOptionalBytes(msg.getOptionalBytes());
assertTrue(bytesCompare(msg.getOptionalBytes(), BYTES));
msg.setOptionalBytes(msg.getOptionalBytes_asB64());
assertTrue(bytesCompare(msg.getOptionalBytes(), BYTES));
msg.setOptionalBytes(msg.getOptionalBytes_asU8());
assertTrue(bytesCompare(msg.getOptionalBytes(), BYTES));
});
/**
* Test that bytes setters will receive result of any of the getters.
*/
it('testRepeatedBytesGetters', function() {
var msg = new proto.jspb.test.TestAllTypes();
function assertGetters() {
assertTrue(goog.isString(msg.getRepeatedBytesList_asB64()[0]));
assertTrue(goog.isString(msg.getRepeatedBytesList_asB64()[1]));
assertTrue(msg.getRepeatedBytesList_asU8()[0] instanceof Uint8Array);
assertTrue(msg.getRepeatedBytesList_asU8()[1] instanceof Uint8Array);
assertTrue(bytesCompare(msg.getRepeatedBytesList()[0], BYTES));
assertTrue(bytesCompare(msg.getRepeatedBytesList()[1], BYTES));
assertTrue(bytesCompare(msg.getRepeatedBytesList_asB64()[0], BYTES));
assertTrue(bytesCompare(msg.getRepeatedBytesList_asB64()[1], BYTES));
assertTrue(bytesCompare(msg.getRepeatedBytesList_asU8()[0], BYTES));
assertTrue(bytesCompare(msg.getRepeatedBytesList_asU8()[1], BYTES));
}
msg.setRepeatedBytesList([BYTES, BYTES]);
assertGetters();
msg.setRepeatedBytesList([BYTES_B64, BYTES_B64]);
assertGetters();
msg.setRepeatedBytesList(null);
assertEquals(0, msg.getRepeatedBytesList().length);
assertEquals(0, msg.getRepeatedBytesList_asB64().length);
assertEquals(0, msg.getRepeatedBytesList_asU8().length);
});
/**
* Helper: fill all extension values.
* @param {proto.jspb.test.TestExtendable} msg
*/
function fillExtensions(msg) {
msg.setExtension(
proto.jspb.test.extendOptionalInt32, -42);
msg.setExtension(
proto.jspb.test.extendOptionalInt64, -0x7fffffff00000000);
msg.setExtension(
proto.jspb.test.extendOptionalUint32, 0x80000000);
msg.setExtension(
proto.jspb.test.extendOptionalUint64, 0xf000000000000000);
msg.setExtension(
proto.jspb.test.extendOptionalSint32, -100);
msg.setExtension(
proto.jspb.test.extendOptionalSint64, -0x8000000000000000);
msg.setExtension(
proto.jspb.test.extendOptionalFixed32, 1234);
msg.setExtension(
proto.jspb.test.extendOptionalFixed64, 0x1234567800000000);
msg.setExtension(
proto.jspb.test.extendOptionalSfixed32, -1234);
msg.setExtension(
proto.jspb.test.extendOptionalSfixed64, -0x1234567800000000);
msg.setExtension(
proto.jspb.test.extendOptionalFloat, 1.5);
msg.setExtension(
proto.jspb.test.extendOptionalDouble, -1.5);
msg.setExtension(
proto.jspb.test.extendOptionalBool, true);
msg.setExtension(
proto.jspb.test.extendOptionalString, 'hello world');
msg.setExtension(proto.jspb.test.extendOptionalBytes, BYTES);
var submsg = new proto.jspb.test.ExtendsWithMessage();
submsg.setFoo(16);
msg.setExtension(
proto.jspb.test.ExtendsWithMessage.optionalExtension, submsg);
msg.setExtension(
proto.jspb.test.extendOptionalForeignEnum,
proto.jspb.test.ForeignEnum.FOREIGN_FOO);
msg.setExtension(
proto.jspb.test.extendRepeatedInt32List, [-42]);
msg.setExtension(
proto.jspb.test.extendRepeatedInt64List, [-0x7fffffff00000000]);
msg.setExtension(
proto.jspb.test.extendRepeatedUint32List, [0x80000000]);
msg.setExtension(
proto.jspb.test.extendRepeatedUint64List, [0xf000000000000000]);
msg.setExtension(
proto.jspb.test.extendRepeatedSint32List, [-100]);
msg.setExtension(
proto.jspb.test.extendRepeatedSint64List, [-0x8000000000000000]);
msg.setExtension(
proto.jspb.test.extendRepeatedFixed32List, [1234]);
msg.setExtension(
proto.jspb.test.extendRepeatedFixed64List, [0x1234567800000000]);
msg.setExtension(
proto.jspb.test.extendRepeatedSfixed32List, [-1234]);
msg.setExtension(
proto.jspb.test.extendRepeatedSfixed64List, [-0x1234567800000000]);
msg.setExtension(
proto.jspb.test.extendRepeatedFloatList, [1.5]);
msg.setExtension(
proto.jspb.test.extendRepeatedDoubleList, [-1.5]);
msg.setExtension(
proto.jspb.test.extendRepeatedBoolList, [true]);
msg.setExtension(
proto.jspb.test.extendRepeatedStringList, ['hello world']);
msg.setExtension(proto.jspb.test.extendRepeatedBytesList, [BYTES]);
submsg = new proto.jspb.test.ExtendsWithMessage();
submsg.setFoo(1000);
msg.setExtension(
proto.jspb.test.ExtendsWithMessage.repeatedExtensionList, [submsg]);
msg.setExtension(proto.jspb.test.extendRepeatedForeignEnumList,
[proto.jspb.test.ForeignEnum.FOREIGN_FOO]);
msg.setExtension(
proto.jspb.test.extendPackedRepeatedInt32List, [-42]);
msg.setExtension(
proto.jspb.test.extendPackedRepeatedInt64List, [-0x7fffffff00000000]);
msg.setExtension(
proto.jspb.test.extendPackedRepeatedUint32List, [0x80000000]);
msg.setExtension(
proto.jspb.test.extendPackedRepeatedUint64List, [0xf000000000000000]);
msg.setExtension(
proto.jspb.test.extendPackedRepeatedSint32List, [-100]);
msg.setExtension(
proto.jspb.test.extendPackedRepeatedSint64List, [-0x8000000000000000]);
msg.setExtension(
proto.jspb.test.extendPackedRepeatedFixed32List, [1234]);
msg.setExtension(
proto.jspb.test.extendPackedRepeatedFixed64List, [0x1234567800000000]);
msg.setExtension(
proto.jspb.test.extendPackedRepeatedSfixed32List, [-1234]);
msg.setExtension(
proto.jspb.test.extendPackedRepeatedSfixed64List,
[-0x1234567800000000]);
msg.setExtension(
proto.jspb.test.extendPackedRepeatedFloatList, [1.5]);
msg.setExtension(
proto.jspb.test.extendPackedRepeatedDoubleList, [-1.5]);
msg.setExtension(
proto.jspb.test.extendPackedRepeatedBoolList, [true]);
msg.setExtension(proto.jspb.test.extendPackedRepeatedForeignEnumList,
[proto.jspb.test.ForeignEnum.FOREIGN_FOO]);
}
/**
* Tests extension serialization and deserialization.
*/
it('testExtensions', function() {
var msg = new proto.jspb.test.TestExtendable();
fillExtensions(msg);
var encoded = msg.serializeBinary();
var decoded = proto.jspb.test.TestExtendable.deserializeBinary(encoded);
checkExtensions(decoded);
});
});
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
/**
* @fileoverview Test cases for jspb's binary protocol buffer reader.
*
* There are two particular magic numbers that need to be pointed out -
* 2^64-1025 is the largest number representable as both a double and an
* unsigned 64-bit integer, and 2^63-513 is the largest number representable as
* both a double and a signed 64-bit integer.
*
* Test suite is written using Jasmine -- see http://jasmine.github.io/
*
* @author aappleby@google.com (Austin Appleby)
*/
goog.require('goog.testing.asserts');
goog.require('jspb.BinaryConstants');
goog.require('jspb.BinaryDecoder');
goog.require('jspb.BinaryReader');
goog.require('jspb.BinaryWriter');
describe('binaryReaderTest', function() {
/**
* Tests the reader instance cache.
*/
it('testInstanceCaches', /** @suppress {visibility} */ function() {
var writer = new jspb.BinaryWriter();
var dummyMessage = /** @type {!jspb.BinaryMessage} */({});
writer.writeMessage(1, dummyMessage, goog.nullFunction);
writer.writeMessage(2, dummyMessage, goog.nullFunction);
var buffer = writer.getResultBuffer();
// Empty the instance caches.
jspb.BinaryReader.instanceCache_ = [];
// Allocating and then freeing three decoders should leave us with three in
// the cache.
var decoder1 = jspb.BinaryDecoder.alloc();
var decoder2 = jspb.BinaryDecoder.alloc();
var decoder3 = jspb.BinaryDecoder.alloc();
decoder1.free();
decoder2.free();
decoder3.free();
assertEquals(3, jspb.BinaryDecoder.instanceCache_.length);
assertEquals(0, jspb.BinaryReader.instanceCache_.length);
// Allocating and then freeing a reader should remove one decoder from its
// cache, but it should stay stuck to the reader afterwards since we can't
// have a reader without a decoder.
jspb.BinaryReader.alloc().free();
assertEquals(2, jspb.BinaryDecoder.instanceCache_.length);
assertEquals(1, jspb.BinaryReader.instanceCache_.length);
// Allocating a reader should remove a reader from the cache.
var reader = jspb.BinaryReader.alloc(buffer);
assertEquals(2, jspb.BinaryDecoder.instanceCache_.length);
assertEquals(0, jspb.BinaryReader.instanceCache_.length);
// Processing the message reuses the current reader.
reader.nextField();
assertEquals(1, reader.getFieldNumber());
reader.readMessage(dummyMessage, function() {
assertEquals(0, jspb.BinaryReader.instanceCache_.length);
});
reader.nextField();
assertEquals(2, reader.getFieldNumber());
reader.readMessage(dummyMessage, function() {
assertEquals(0, jspb.BinaryReader.instanceCache_.length);
});
assertEquals(false, reader.nextField());
assertEquals(2, jspb.BinaryDecoder.instanceCache_.length);
assertEquals(0, jspb.BinaryReader.instanceCache_.length);
// Freeing the reader should put it back into the cache.
reader.free();
assertEquals(2, jspb.BinaryDecoder.instanceCache_.length);
assertEquals(1, jspb.BinaryReader.instanceCache_.length);
});
/**
* @param {number} x
* @return {number}
*/
function truncate(x) {
var temp = new Float32Array(1);
temp[0] = x;
return temp[0];
}
/**
* Verifies that misuse of the reader class triggers assertions.
*/
it('testReadErrors', /** @suppress {checkTypes|visibility} */ function() {
// Calling readMessage on a non-delimited field should trigger an
// assertion.
var reader = jspb.BinaryReader.alloc([8, 1]);
var dummyMessage = /** @type {!jspb.BinaryMessage} */({});
reader.nextField();
assertThrows(function() {
reader.readMessage(dummyMessage, goog.nullFunction);
});
// Reading past the end of the stream should trigger an assertion.
reader = jspb.BinaryReader.alloc([9, 1]);
reader.nextField();
assertThrows(function() {reader.readFixed64()});
// Reading past the end of a submessage should trigger an assertion.
reader = jspb.BinaryReader.alloc([10, 4, 13, 1, 1, 1]);
reader.nextField();
reader.readMessage(dummyMessage, function() {
reader.nextField();
assertThrows(function() {reader.readFixed32()});
});
// Skipping an invalid field should trigger an assertion.
reader = jspb.BinaryReader.alloc([12, 1]);
reader.nextWireType_ = 1000;
assertThrows(function() {reader.skipField()});
// Reading fields with the wrong wire type should assert.
reader = jspb.BinaryReader.alloc([9, 0, 0, 0, 0, 0, 0, 0, 0]);
reader.nextField();
assertThrows(function() {reader.readInt32()});
assertThrows(function() {reader.readInt32String()});
assertThrows(function() {reader.readInt64()});
assertThrows(function() {reader.readInt64String()});
assertThrows(function() {reader.readUint32()});
assertThrows(function() {reader.readUint32String()});
assertThrows(function() {reader.readUint64()});
assertThrows(function() {reader.readUint64String()});
assertThrows(function() {reader.readSint32()});
assertThrows(function() {reader.readBool()});
assertThrows(function() {reader.readEnum()});
reader = jspb.BinaryReader.alloc([8, 1]);
reader.nextField();
assertThrows(function() {reader.readFixed32()});
assertThrows(function() {reader.readFixed64()});
assertThrows(function() {reader.readSfixed32()});
assertThrows(function() {reader.readSfixed64()});
assertThrows(function() {reader.readFloat()});
assertThrows(function() {reader.readDouble()});
assertThrows(function() {reader.readString()});
assertThrows(function() {reader.readBytes()});
});
/**
* Tests encoding and decoding of unsigned field types.
* @param {Function} readField
* @param {Function} writeField
* @param {number} epsilon
* @param {number} upperLimit
* @param {Function} filter
* @private
* @suppress {missingProperties}
*/
var doTestUnsignedField_ = function(readField,
writeField, epsilon, upperLimit, filter) {
assertNotNull(readField);
assertNotNull(writeField);
var writer = new jspb.BinaryWriter();
// Encode zero and limits.
writeField.call(writer, 1, filter(0));
writeField.call(writer, 2, filter(epsilon));
writeField.call(writer, 3, filter(upperLimit));
// Encode positive values.
for (var cursor = epsilon; cursor < upperLimit; cursor *= 1.1) {
writeField.call(writer, 4, filter(cursor));
}
var reader = jspb.BinaryReader.alloc(writer.getResultBuffer());
// Check zero and limits.
reader.nextField();
assertEquals(1, reader.getFieldNumber());
assertEquals(filter(0), readField.call(reader));
reader.nextField();
assertEquals(2, reader.getFieldNumber());
assertEquals(filter(epsilon), readField.call(reader));
reader.nextField();
assertEquals(3, reader.getFieldNumber());
assertEquals(filter(upperLimit), readField.call(reader));
// Check positive values.
for (var cursor = epsilon; cursor < upperLimit; cursor *= 1.1) {
reader.nextField();
if (4 != reader.getFieldNumber()) throw 'fail!';
if (filter(cursor) != readField.call(reader)) throw 'fail!';
}
};
/**
* Tests encoding and decoding of signed field types.
* @param {Function} readField
* @param {Function} writeField
* @param {number} epsilon
* @param {number} lowerLimit
* @param {number} upperLimit
* @param {Function} filter
* @private
* @suppress {missingProperties}
*/
var doTestSignedField_ = function(readField,
writeField, epsilon, lowerLimit, upperLimit, filter) {
var writer = new jspb.BinaryWriter();
// Encode zero and limits.
writeField.call(writer, 1, filter(lowerLimit));
writeField.call(writer, 2, filter(-epsilon));
writeField.call(writer, 3, filter(0));
writeField.call(writer, 4, filter(epsilon));
writeField.call(writer, 5, filter(upperLimit));
var inputValues = [];
// Encode negative values.
for (var cursor = lowerLimit; cursor < -epsilon; cursor /= 1.1) {
var val = filter(cursor);
writeField.call(writer, 6, val);
inputValues.push({
fieldNumber: 6,
value: val
});
}
// Encode positive values.
for (var cursor = epsilon; cursor < upperLimit; cursor *= 1.1) {
var val = filter(cursor);
writeField.call(writer, 7, val);
inputValues.push({
fieldNumber: 7,
value: val
});
}
var reader = jspb.BinaryReader.alloc(writer.getResultBuffer());
// Check zero and limits.
reader.nextField();
assertEquals(1, reader.getFieldNumber());
assertEquals(filter(lowerLimit), readField.call(reader));
reader.nextField();
assertEquals(2, reader.getFieldNumber());
assertEquals(filter(-epsilon), readField.call(reader));
reader.nextField();
assertEquals(3, reader.getFieldNumber());
assertEquals(filter(0), readField.call(reader));
reader.nextField();
assertEquals(4, reader.getFieldNumber());
assertEquals(filter(epsilon), readField.call(reader));
reader.nextField();
assertEquals(5, reader.getFieldNumber());
assertEquals(filter(upperLimit), readField.call(reader));
for (var i = 0; i < inputValues.length; i++) {
var expected = inputValues[i];
reader.nextField();
assertEquals(expected.fieldNumber, reader.getFieldNumber());
assertEquals(expected.value, readField.call(reader));
}
};
/**
* Tests fields that use varint encoding.
*/
it('testVarintFields', function() {
assertNotUndefined(jspb.BinaryReader.prototype.readUint32);
assertNotUndefined(jspb.BinaryWriter.prototype.writeUint32);
assertNotUndefined(jspb.BinaryReader.prototype.readUint64);
assertNotUndefined(jspb.BinaryWriter.prototype.writeUint64);
assertNotUndefined(jspb.BinaryReader.prototype.readBool);
assertNotUndefined(jspb.BinaryWriter.prototype.writeBool);
doTestUnsignedField_(
jspb.BinaryReader.prototype.readUint32,
jspb.BinaryWriter.prototype.writeUint32,
1, Math.pow(2, 32) - 1, Math.round);
doTestUnsignedField_(
jspb.BinaryReader.prototype.readUint64,
jspb.BinaryWriter.prototype.writeUint64,
1, Math.pow(2, 64) - 1025, Math.round);
doTestSignedField_(
jspb.BinaryReader.prototype.readInt32,
jspb.BinaryWriter.prototype.writeInt32,
1, -Math.pow(2, 31), Math.pow(2, 31) - 1, Math.round);
doTestSignedField_(
jspb.BinaryReader.prototype.readInt64,
jspb.BinaryWriter.prototype.writeInt64,
1, -Math.pow(2, 63), Math.pow(2, 63) - 513, Math.round);
doTestSignedField_(
jspb.BinaryReader.prototype.readEnum,
jspb.BinaryWriter.prototype.writeEnum,
1, -Math.pow(2, 31), Math.pow(2, 31) - 1, Math.round);
doTestUnsignedField_(
jspb.BinaryReader.prototype.readBool,
jspb.BinaryWriter.prototype.writeBool,
1, 1, function(x) { return !!x; });
});
/**
* Tests reading a field from hexadecimal string (format: '08 BE EF').
* @param {Function} readField
* @param {number} expected
* @param {string} hexString
*/
function doTestHexStringVarint_(readField, expected, hexString) {
var bytesCount = (hexString.length + 1) / 3;
var bytes = new Uint8Array(bytesCount);
for (var i = 0; i < bytesCount; i++) {
bytes[i] = parseInt(hexString.substring(i * 3, i * 3 + 2), 16);
}
var reader = jspb.BinaryReader.alloc(bytes);
reader.nextField();
assertEquals(expected, readField.call(reader));
}
/**
* Tests non-canonical redundant varint decoding.
*/
it('testRedundantVarintFields', function() {
assertNotNull(jspb.BinaryReader.prototype.readUint32);
assertNotNull(jspb.BinaryReader.prototype.readUint64);
assertNotNull(jspb.BinaryReader.prototype.readSint32);
assertNotNull(jspb.BinaryReader.prototype.readSint64);
// uint32 and sint32 take no more than 5 bytes
// 08 - field prefix (type = 0 means varint)
doTestHexStringVarint_(
jspb.BinaryReader.prototype.readUint32,
12, '08 8C 80 80 80 00');
// 11 stands for -6 in zigzag encoding
doTestHexStringVarint_(
jspb.BinaryReader.prototype.readSint32,
-6, '08 8B 80 80 80 00');
// uint64 and sint64 take no more than 10 bytes
// 08 - field prefix (type = 0 means varint)
doTestHexStringVarint_(
jspb.BinaryReader.prototype.readUint64,
12, '08 8C 80 80 80 80 80 80 80 80 00');
// 11 stands for -6 in zigzag encoding
doTestHexStringVarint_(
jspb.BinaryReader.prototype.readSint64,
-6, '08 8B 80 80 80 80 80 80 80 80 00');
});
/**
* Tests 64-bit fields that are handled as strings.
*/
it('testStringInt64Fields', function() {
var writer = new jspb.BinaryWriter();
var testSignedData = [
'2730538252207801776',
'-2688470994844604560',
'3398529779486536359',
'3568577411627971000',
'272477188847484900',
'-6649058714086158188',
'-7695254765712060806',
'-4525541438037104029',
'-4993706538836508568',
'4990160321893729138'
];
var testUnsignedData = [
'7822732630241694882',
'6753602971916687352',
'2399935075244442116',
'8724292567325338867',
'16948784802625696584',
'4136275908516066934',
'3575388346793700364',
'5167142028379259461',
'1557573948689737699',
'17100725280812548567'
];
for (var i = 0; i < testSignedData.length; i++) {
writer.writeInt64String(2 * i + 1, testSignedData[i]);
writer.writeUint64String(2 * i + 2, testUnsignedData[i]);
}
var reader = jspb.BinaryReader.alloc(writer.getResultBuffer());
for (var i = 0; i < testSignedData.length; i++) {
reader.nextField();
assertEquals(2 * i + 1, reader.getFieldNumber());
assertEquals(testSignedData[i], reader.readInt64String());
reader.nextField();
assertEquals(2 * i + 2, reader.getFieldNumber());
assertEquals(testUnsignedData[i], reader.readUint64String());
}
});
/**
* Tests fields that use zigzag encoding.
*/
it('testZigzagFields', function() {
doTestSignedField_(
jspb.BinaryReader.prototype.readSint32,
jspb.BinaryWriter.prototype.writeSint32,
1, -Math.pow(2, 31), Math.pow(2, 31) - 1, Math.round);
doTestSignedField_(
jspb.BinaryReader.prototype.readSint64,
jspb.BinaryWriter.prototype.writeSint64,
1, -Math.pow(2, 63), Math.pow(2, 63) - 513, Math.round);
});
/**
* Tests fields that use fixed-length encoding.
*/
it('testFixedFields', function() {
doTestUnsignedField_(
jspb.BinaryReader.prototype.readFixed32,
jspb.BinaryWriter.prototype.writeFixed32,
1, Math.pow(2, 32) - 1, Math.round);
doTestUnsignedField_(
jspb.BinaryReader.prototype.readFixed64,
jspb.BinaryWriter.prototype.writeFixed64,
1, Math.pow(2, 64) - 1025, Math.round);
doTestSignedField_(
jspb.BinaryReader.prototype.readSfixed32,
jspb.BinaryWriter.prototype.writeSfixed32,
1, -Math.pow(2, 31), Math.pow(2, 31) - 1, Math.round);
doTestSignedField_(
jspb.BinaryReader.prototype.readSfixed64,
jspb.BinaryWriter.prototype.writeSfixed64,
1, -Math.pow(2, 63), Math.pow(2, 63) - 513, Math.round);
});
/**
* Tests floating point fields.
*/
it('testFloatFields', function() {
doTestSignedField_(
jspb.BinaryReader.prototype.readFloat,
jspb.BinaryWriter.prototype.writeFloat,
jspb.BinaryConstants.FLOAT32_MIN,
-jspb.BinaryConstants.FLOAT32_MAX,
jspb.BinaryConstants.FLOAT32_MAX,
truncate);
doTestSignedField_(
jspb.BinaryReader.prototype.readDouble,
jspb.BinaryWriter.prototype.writeDouble,
jspb.BinaryConstants.FLOAT64_EPS * 10,
-jspb.BinaryConstants.FLOAT64_MIN,
jspb.BinaryConstants.FLOAT64_MIN,
function(x) { return x; });
});
/**
* Tests length-delimited string fields.
*/
it('testStringFields', function() {
var s1 = 'The quick brown fox jumps over the lazy dog.';
var s2 = '人人生而自由,在尊嚴和權利上一律平等。';
var writer = new jspb.BinaryWriter();
writer.writeString(1, s1);
writer.writeString(2, s2);
var reader = jspb.BinaryReader.alloc(writer.getResultBuffer());
reader.nextField();
assertEquals(1, reader.getFieldNumber());
assertEquals(s1, reader.readString());
reader.nextField();
assertEquals(2, reader.getFieldNumber());
assertEquals(s2, reader.readString());
});
/**
* Tests length-delimited byte fields.
*/
it('testByteFields', function() {
var message = [];
var lowerLimit = 1;
var upperLimit = 256;
var scale = 1.1;
var writer = new jspb.BinaryWriter();
for (var cursor = lowerLimit; cursor < upperLimit; cursor *= 1.1) {
var len = Math.round(cursor);
var bytes = [];
for (var i = 0; i < len; i++) bytes.push(i % 256);
writer.writeBytes(len, bytes);
}
var reader = jspb.BinaryReader.alloc(writer.getResultBuffer());
for (var cursor = lowerLimit; reader.nextField(); cursor *= 1.1) {
var len = Math.round(cursor);
if (len != reader.getFieldNumber()) throw 'fail!';
var bytes = reader.readBytes();
if (len != bytes.length) throw 'fail!';
for (var i = 0; i < bytes.length; i++) {
if (i % 256 != bytes[i]) throw 'fail!';
}
}
});
/**
* Tests nested messages.
*/
it('testNesting', function() {
var writer = new jspb.BinaryWriter();
var dummyMessage = /** @type {!jspb.BinaryMessage} */({});
writer.writeInt32(1, 100);
// Add one message with 3 int fields.
writer.writeMessage(2, dummyMessage, function() {
writer.writeInt32(3, 300);
writer.writeInt32(4, 400);
writer.writeInt32(5, 500);
});
// Add one empty message.
writer.writeMessage(6, dummyMessage, goog.nullFunction);
writer.writeInt32(7, 700);
var reader = jspb.BinaryReader.alloc(writer.getResultBuffer());
// Validate outermost message.
reader.nextField();
assertEquals(1, reader.getFieldNumber());
assertEquals(100, reader.readInt32());
reader.nextField();
assertEquals(2, reader.getFieldNumber());
reader.readMessage(dummyMessage, function() {
// Validate embedded message 1.
reader.nextField();
assertEquals(3, reader.getFieldNumber());
assertEquals(300, reader.readInt32());
reader.nextField();
assertEquals(4, reader.getFieldNumber());
assertEquals(400, reader.readInt32());
reader.nextField();
assertEquals(5, reader.getFieldNumber());
assertEquals(500, reader.readInt32());
assertEquals(false, reader.nextField());
});
reader.nextField();
assertEquals(6, reader.getFieldNumber());
reader.readMessage(dummyMessage, function() {
// Validate embedded message 2.
assertEquals(false, reader.nextField());
});
reader.nextField();
assertEquals(7, reader.getFieldNumber());
assertEquals(700, reader.readInt32());
assertEquals(false, reader.nextField());
});
/**
* Tests skipping fields of each type by interleaving them with sentinel
* values and skipping everything that's not a sentinel.
*/
it('testSkipField', function() {
var writer = new jspb.BinaryWriter();
var sentinel = 123456789;
// Write varint fields of different sizes.
writer.writeInt32(1, sentinel);
writer.writeInt32(1, 1);
writer.writeInt32(1, 1000);
writer.writeInt32(1, 1000000);
writer.writeInt32(1, 1000000000);
// Write fixed 64-bit encoded fields.
writer.writeInt32(2, sentinel);
writer.writeDouble(2, 1);
writer.writeFixed64(2, 1);
writer.writeSfixed64(2, 1);
// Write fixed 32-bit encoded fields.
writer.writeInt32(3, sentinel);
writer.writeFloat(3, 1);
writer.writeFixed32(3, 1);
writer.writeSfixed32(3, 1);
// Write delimited fields.
writer.writeInt32(4, sentinel);
writer.writeBytes(4, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]);
writer.writeString(4, 'The quick brown fox jumps over the lazy dog');
// Write a group with a nested group inside.
writer.writeInt32(5, sentinel);
var dummyMessage = /** @type {!jspb.BinaryMessage} */({});
writer.writeGroup(5, dummyMessage, function() {
writer.writeInt64(42, 42);
writer.writeGroup(6, dummyMessage, function() {
writer.writeInt64(84, 42);
});
});
// Write final sentinel.
writer.writeInt32(6, sentinel);
var reader = jspb.BinaryReader.alloc(writer.getResultBuffer());
function skip(field, count) {
for (var i = 0; i < count; i++) {
reader.nextField();
if (field != reader.getFieldNumber()) throw 'fail!';
reader.skipField();
}
}
reader.nextField();
assertEquals(1, reader.getFieldNumber());
assertEquals(sentinel, reader.readInt32());
skip(1, 4);
reader.nextField();
assertEquals(2, reader.getFieldNumber());
assertEquals(sentinel, reader.readInt32());
skip(2, 3);
reader.nextField();
assertEquals(3, reader.getFieldNumber());
assertEquals(sentinel, reader.readInt32());
skip(3, 3);
reader.nextField();
assertEquals(4, reader.getFieldNumber());
assertEquals(sentinel, reader.readInt32());
skip(4, 2);
reader.nextField();
assertEquals(5, reader.getFieldNumber());
assertEquals(sentinel, reader.readInt32());
skip(5, 1);
reader.nextField();
assertEquals(6, reader.getFieldNumber());
assertEquals(sentinel, reader.readInt32());
});
/**
* Tests packed fields.
*/
it('testPackedFields', function() {
var writer = new jspb.BinaryWriter();
var sentinel = 123456789;
var unsignedData = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10];
var signedData = [-1, 2, -3, 4, -5, 6, -7, 8, -9, 10];
var floatData = [1.1, 2.2, 3.3, 4.4, 5.5, 6.6, 7.7, 8.8, 9.9, 10.10];
var doubleData = [1.1, 2.2, 3.3, 4.4, 5.5, 6.6, 7.7, 8.8, 9.9, 10.10];
var boolData = [true, false, true, true, false, false, true, false];
for (var i = 0; i < floatData.length; i++) {
floatData[i] = truncate(floatData[i]);
}
writer.writeInt32(1, sentinel);
writer.writePackedInt32(2, signedData);
writer.writePackedInt64(2, signedData);
writer.writePackedUint32(2, unsignedData);
writer.writePackedUint64(2, unsignedData);
writer.writePackedSint32(2, signedData);
writer.writePackedSint64(2, signedData);
writer.writePackedFixed32(2, unsignedData);
writer.writePackedFixed64(2, unsignedData);
writer.writePackedSfixed32(2, signedData);
writer.writePackedSfixed64(2, signedData);
writer.writePackedFloat(2, floatData);
writer.writePackedDouble(2, doubleData);
writer.writePackedBool(2, boolData);
writer.writePackedEnum(2, unsignedData);
writer.writeInt32(3, sentinel);
var reader = jspb.BinaryReader.alloc(writer.getResultBuffer());
reader.nextField();
assertEquals(sentinel, reader.readInt32());
reader.nextField();
assertElementsEquals(reader.readPackedInt32(), signedData);
reader.nextField();
assertElementsEquals(reader.readPackedInt64(), signedData);
reader.nextField();
assertElementsEquals(reader.readPackedUint32(), unsignedData);
reader.nextField();
assertElementsEquals(reader.readPackedUint64(), unsignedData);
reader.nextField();
assertElementsEquals(reader.readPackedSint32(), signedData);
reader.nextField();
assertElementsEquals(reader.readPackedSint64(), signedData);
reader.nextField();
assertElementsEquals(reader.readPackedFixed32(), unsignedData);
reader.nextField();
assertElementsEquals(reader.readPackedFixed64(), unsignedData);
reader.nextField();
assertElementsEquals(reader.readPackedSfixed32(), signedData);
reader.nextField();
assertElementsEquals(reader.readPackedSfixed64(), signedData);
reader.nextField();
assertElementsEquals(reader.readPackedFloat(), floatData);
reader.nextField();
assertElementsEquals(reader.readPackedDouble(), doubleData);
reader.nextField();
assertElementsEquals(reader.readPackedBool(), boolData);
reader.nextField();
assertElementsEquals(reader.readPackedEnum(), unsignedData);
reader.nextField();
assertEquals(sentinel, reader.readInt32());
});
/**
* Byte blobs inside nested messages should always have their byte offset set
* relative to the start of the outermost blob, not the start of their parent
* blob.
*/
it('testNestedBlobs', function() {
// Create a proto consisting of two nested messages, with the inner one
// containing a blob of bytes.
var fieldTag = (1 << 3) | jspb.BinaryConstants.WireType.DELIMITED;
var blob = [1, 2, 3, 4, 5];
var writer = new jspb.BinaryWriter();
var dummyMessage = /** @type {!jspb.BinaryMessage} */({});
writer.writeMessage(1, dummyMessage, function() {
writer.writeMessage(1, dummyMessage, function() {
writer.writeBytes(1, blob);
});
});
// Peel off the outer two message layers. Each layer should have two bytes
// of overhead, one for the field tag and one for the length of the inner
// blob.
var decoder1 = new jspb.BinaryDecoder(writer.getResultBuffer());
assertEquals(fieldTag, decoder1.readUnsignedVarint32());
assertEquals(blob.length + 4, decoder1.readUnsignedVarint32());
var decoder2 = new jspb.BinaryDecoder(decoder1.readBytes(blob.length + 4));
assertEquals(fieldTag, decoder2.readUnsignedVarint32());
assertEquals(blob.length + 2, decoder2.readUnsignedVarint32());
assertEquals(fieldTag, decoder2.readUnsignedVarint32());
assertEquals(blob.length, decoder2.readUnsignedVarint32());
var bytes = decoder2.readBytes(blob.length);
assertElementsEquals(bytes, blob);
});
/**
* Tests read callbacks.
*/
it('testReadCallbacks', function() {
var writer = new jspb.BinaryWriter();
var dummyMessage = /** @type {!jspb.BinaryMessage} */({});
// Add an int, a submessage, and another int.
writer.writeInt32(1, 100);
writer.writeMessage(2, dummyMessage, function() {
writer.writeInt32(3, 300);
writer.writeInt32(4, 400);
writer.writeInt32(5, 500);
});
writer.writeInt32(7, 700);
// Create the reader and register a custom read callback.
var reader = jspb.BinaryReader.alloc(writer.getResultBuffer());
/**
* @param {!jspb.BinaryReader} reader
* @return {*}
*/
function readCallback(reader) {
reader.nextField();
assertEquals(3, reader.getFieldNumber());
assertEquals(300, reader.readInt32());
reader.nextField();
assertEquals(4, reader.getFieldNumber());
assertEquals(400, reader.readInt32());
reader.nextField();
assertEquals(5, reader.getFieldNumber());
assertEquals(500, reader.readInt32());
assertEquals(false, reader.nextField());
};
reader.registerReadCallback('readCallback', readCallback);
// Read the container message.
reader.nextField();
assertEquals(1, reader.getFieldNumber());
assertEquals(100, reader.readInt32());
reader.nextField();
assertEquals(2, reader.getFieldNumber());
reader.readMessage(dummyMessage, function() {
// Decode the embedded message using the registered callback.
reader.runReadCallback('readCallback');
});
reader.nextField();
assertEquals(7, reader.getFieldNumber());
assertEquals(700, reader.readInt32());
assertEquals(false, reader.nextField());
});
});
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
/**
* @fileoverview Test cases for jspb's helper functions.
*
* Test suite is written using Jasmine -- see http://jasmine.github.io/
*
* @author aappleby@google.com (Austin Appleby)
*/
goog.require('goog.crypt.base64');
goog.require('goog.testing.asserts');
goog.require('jspb.BinaryConstants');
goog.require('jspb.BinaryWriter');
goog.require('jspb.utils');
/**
* @param {number} x
* @return {number}
*/
function truncate(x) {
var temp = new Float32Array(1);
temp[0] = x;
return temp[0];
}
/**
* Converts an 64-bit integer in split representation to a 64-bit hash string
* (8 bits encoded per character).
* @param {number} bitsLow The low 32 bits of the split 64-bit integer.
* @param {number} bitsHigh The high 32 bits of the split 64-bit integer.
* @return {string} The encoded hash string, 8 bits per character.
*/
function toHashString(bitsLow, bitsHigh) {
return String.fromCharCode((bitsLow >>> 0) & 0xFF,
(bitsLow >>> 8) & 0xFF,
(bitsLow >>> 16) & 0xFF,
(bitsLow >>> 24) & 0xFF,
(bitsHigh >>> 0) & 0xFF,
(bitsHigh >>> 8) & 0xFF,
(bitsHigh >>> 16) & 0xFF,
(bitsHigh >>> 24) & 0xFF);
}
describe('binaryUtilsTest', function() {
/**
* Tests lossless binary-to-decimal conversion.
*/
it('testDecimalConversion', function() {
// Check some magic numbers.
var result =
jspb.utils.joinUnsignedDecimalString(0x89e80001, 0x8ac72304);
assertEquals('10000000000000000001', result);
result = jspb.utils.joinUnsignedDecimalString(0xacd05f15, 0x1b69b4b);
assertEquals('123456789123456789', result);
result = jspb.utils.joinUnsignedDecimalString(0xeb1f0ad2, 0xab54a98c);
assertEquals('12345678901234567890', result);
result = jspb.utils.joinUnsignedDecimalString(0xe3b70cb1, 0x891087b8);
assertEquals('9876543210987654321', result);
// Check limits.
result = jspb.utils.joinUnsignedDecimalString(0x00000000, 0x00000000);
assertEquals('0', result);
result = jspb.utils.joinUnsignedDecimalString(0xFFFFFFFF, 0xFFFFFFFF);
assertEquals('18446744073709551615', result);
// Check each bit of the low dword.
for (var i = 0; i < 32; i++) {
var low = (1 << i) >>> 0;
result = jspb.utils.joinUnsignedDecimalString(low, 0);
assertEquals('' + Math.pow(2, i), result);
}
// Check the first 20 bits of the high dword.
for (var i = 0; i < 20; i++) {
var high = (1 << i) >>> 0;
result = jspb.utils.joinUnsignedDecimalString(0, high);
assertEquals('' + Math.pow(2, 32 + i), result);
}
// V8's internal double-to-string conversion is inaccurate for values above
// 2^52, even if they're representable integers - check the rest of the bits
// manually against the correct string representations of 2^N.
result = jspb.utils.joinUnsignedDecimalString(0x00000000, 0x00100000);
assertEquals('4503599627370496', result);
result = jspb.utils.joinUnsignedDecimalString(0x00000000, 0x00200000);
assertEquals('9007199254740992', result);
result = jspb.utils.joinUnsignedDecimalString(0x00000000, 0x00400000);
assertEquals('18014398509481984', result);
result = jspb.utils.joinUnsignedDecimalString(0x00000000, 0x00800000);
assertEquals('36028797018963968', result);
result = jspb.utils.joinUnsignedDecimalString(0x00000000, 0x01000000);
assertEquals('72057594037927936', result);
result = jspb.utils.joinUnsignedDecimalString(0x00000000, 0x02000000);
assertEquals('144115188075855872', result);
result = jspb.utils.joinUnsignedDecimalString(0x00000000, 0x04000000);
assertEquals('288230376151711744', result);
result = jspb.utils.joinUnsignedDecimalString(0x00000000, 0x08000000);
assertEquals('576460752303423488', result);
result = jspb.utils.joinUnsignedDecimalString(0x00000000, 0x10000000);
assertEquals('1152921504606846976', result);
result = jspb.utils.joinUnsignedDecimalString(0x00000000, 0x20000000);
assertEquals('2305843009213693952', result);
result = jspb.utils.joinUnsignedDecimalString(0x00000000, 0x40000000);
assertEquals('4611686018427387904', result);
result = jspb.utils.joinUnsignedDecimalString(0x00000000, 0x80000000);
assertEquals('9223372036854775808', result);
});
/**
* Going from hash strings to decimal strings should also be lossless.
*/
it('testHashToDecimalConversion', function() {
var result;
var convert = jspb.utils.hash64ToDecimalString;
result = convert(toHashString(0x00000000, 0x00000000), false);
assertEquals('0', result);
result = convert(toHashString(0x00000000, 0x00000000), true);
assertEquals('0', result);
result = convert(toHashString(0xFFFFFFFF, 0xFFFFFFFF), false);
assertEquals('18446744073709551615', result);
result = convert(toHashString(0xFFFFFFFF, 0xFFFFFFFF), true);
assertEquals('-1', result);
result = convert(toHashString(0x00000000, 0x80000000), false);
assertEquals('9223372036854775808', result);
result = convert(toHashString(0x00000000, 0x80000000), true);
assertEquals('-9223372036854775808', result);
result = convert(toHashString(0xacd05f15, 0x01b69b4b), false);
assertEquals('123456789123456789', result);
result = convert(toHashString(~0xacd05f15 + 1, ~0x01b69b4b), true);
assertEquals('-123456789123456789', result);
// And converting arrays of hashes should work the same way.
result = jspb.utils.hash64ArrayToDecimalStrings([
toHashString(0xFFFFFFFF, 0xFFFFFFFF),
toHashString(0x00000000, 0x80000000),
toHashString(0xacd05f15, 0x01b69b4b)], false);
assertEquals(3, result.length);
assertEquals('18446744073709551615', result[0]);
assertEquals('9223372036854775808', result[1]);
assertEquals('123456789123456789', result[2]);
});
/*
* Going from decimal strings to hash strings should be lossless.
*/
it('testDecimalToHashConversion', function() {
var result;
var convert = jspb.utils.decimalStringToHash64;
result = convert('0');
assertEquals(String.fromCharCode.apply(null,
[0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00]), result);
result = convert('-1');
assertEquals(String.fromCharCode.apply(null,
[0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF]), result);
result = convert('18446744073709551615');
assertEquals(String.fromCharCode.apply(null,
[0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF]), result);
result = convert('9223372036854775808');
assertEquals(String.fromCharCode.apply(null,
[0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80]), result);
result = convert('-9223372036854775808');
assertEquals(String.fromCharCode.apply(null,
[0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80]), result);
result = convert('123456789123456789');
assertEquals(String.fromCharCode.apply(null,
[0x15, 0x5F, 0xD0, 0xAC, 0x4B, 0x9B, 0xB6, 0x01]), result);
result = convert('-123456789123456789');
assertEquals(String.fromCharCode.apply(null,
[0xEB, 0xA0, 0x2F, 0x53, 0xB4, 0x64, 0x49, 0xFE]), result);
});
/**
* Going from hash strings to hex strings should be lossless.
*/
it('testHashToHexConversion', function() {
var result;
var convert = jspb.utils.hash64ToHexString;
result = convert(toHashString(0x00000000, 0x00000000));
assertEquals('0x0000000000000000', result);
result = convert(toHashString(0xFFFFFFFF, 0xFFFFFFFF));
assertEquals('0xffffffffffffffff', result);
result = convert(toHashString(0x12345678, 0x9ABCDEF0));
assertEquals('0x9abcdef012345678', result);
});
/**
* Going from hex strings to hash strings should be lossless.
*/
it('testHexToHashConversion', function() {
var result;
var convert = jspb.utils.hexStringToHash64;
result = convert('0x0000000000000000');
assertEquals(String.fromCharCode.apply(null,
[0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00]), result);
result = convert('0xffffffffffffffff');
assertEquals(String.fromCharCode.apply(null,
[0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF]), result);
// Hex string is big-endian, hash string is little-endian.
result = convert('0x123456789ABCDEF0');
assertEquals(String.fromCharCode.apply(null,
[0xF0, 0xDE, 0xBC, 0x9A, 0x78, 0x56, 0x34, 0x12]), result);
// Capitalization should not matter.
result = convert('0x0000abcdefABCDEF');
assertEquals(String.fromCharCode.apply(null,
[0xEF, 0xCD, 0xAB, 0xEF, 0xCD, 0xAB, 0x00, 0x00]), result);
});
/**
* Going from numbers to hash strings should be lossless for up to 53 bits of
* precision.
*/
it('testNumberToHashConversion', function() {
var result;
var convert = jspb.utils.numberToHash64;
result = convert(0x0000000000000);
assertEquals('0x0000000000000000', jspb.utils.hash64ToHexString(result));
result = convert(0xFFFFFFFFFFFFF);
assertEquals('0x000fffffffffffff', jspb.utils.hash64ToHexString(result));
result = convert(0x123456789ABCD);
assertEquals('0x000123456789abcd', jspb.utils.hash64ToHexString(result));
result = convert(0xDCBA987654321);
assertEquals('0x000dcba987654321', jspb.utils.hash64ToHexString(result));
// 53 bits of precision should not be truncated.
result = convert(0x10000000000001);
assertEquals('0x0010000000000001', jspb.utils.hash64ToHexString(result));
// 54 bits of precision should be truncated.
result = convert(0x20000000000001);
assertNotEquals(
'0x0020000000000001', jspb.utils.hash64ToHexString(result));
});
/**
* Sanity check the behavior of Javascript's strings when doing funny things
* with unicode characters.
*/
it('sanityCheckUnicodeStrings', function() {
var strings = new Array(65536);
// All possible unsigned 16-bit values should be storable in a string, they
// shouldn't do weird things with the length of the string, and they should
// come back out of the string unchanged.
for (var i = 0; i < 65536; i++) {
strings[i] = 'a' + String.fromCharCode(i) + 'a';
if (3 != strings[i].length) throw 'fail!';
if (i != strings[i].charCodeAt(1)) throw 'fail!';
}
// Each unicode character should compare equal to itself and not equal to a
// different unicode character.
for (var i = 0; i < 65536; i++) {
if (strings[i] != strings[i]) throw 'fail!';
if (strings[i] == strings[(i + 1) % 65536]) throw 'fail!';
}
});
/**
* Tests conversion from 32-bit floating point numbers to split64 numbers.
*/
it('testFloat32ToSplit64', function() {
var f32_eps = jspb.BinaryConstants.FLOAT32_EPS;
var f32_min = jspb.BinaryConstants.FLOAT32_MIN;
var f32_max = jspb.BinaryConstants.FLOAT32_MAX;
// NaN.
jspb.utils.splitFloat32(NaN);
if (!isNaN(jspb.utils.joinFloat32(jspb.utils.split64Low,
jspb.utils.split64High))) {
throw 'fail!';
}
/**
* @param {number} x
* @param {number=} opt_bits
*/
function test(x, opt_bits) {
jspb.utils.splitFloat32(x);
if (goog.isDef(opt_bits)) {
if (opt_bits != jspb.utils.split64Low) throw 'fail!';
}
if (truncate(x) != jspb.utils.joinFloat32(jspb.utils.split64Low,
jspb.utils.split64High)) {
throw 'fail!';
}
}
// Positive and negative infinity.
test(Infinity, 0x7f800000);
test(-Infinity, 0xff800000);
// Positive and negative zero.
test(0, 0x00000000);
test(-0, 0x80000000);
// Positive and negative epsilon.
test(f32_eps, 0x00000001);
test(-f32_eps, 0x80000001);
// Positive and negative min.
test(f32_min, 0x00800000);
test(-f32_min, 0x80800000);
// Positive and negative max.
test(f32_max, 0x7F7FFFFF);
test(-f32_max, 0xFF7FFFFF);
// Various positive values.
var cursor = f32_eps * 10;
while (cursor != Infinity) {
test(cursor);
cursor *= 1.1;
}
// Various negative values.
cursor = -f32_eps * 10;
while (cursor != -Infinity) {
test(cursor);
cursor *= 1.1;
}
});
/**
* Tests conversion from 64-bit floating point numbers to split64 numbers.
*/
it('testFloat64ToSplit64', function() {
var f64_eps = jspb.BinaryConstants.FLOAT64_EPS;
var f64_min = jspb.BinaryConstants.FLOAT64_MIN;
var f64_max = jspb.BinaryConstants.FLOAT64_MAX;
// NaN.
jspb.utils.splitFloat64(NaN);
if (!isNaN(jspb.utils.joinFloat64(jspb.utils.split64Low,
jspb.utils.split64High))) {
throw 'fail!';
}
/**
* @param {number} x
* @param {number=} opt_highBits
* @param {number=} opt_lowBits
*/
function test(x, opt_highBits, opt_lowBits) {
jspb.utils.splitFloat64(x);
if (goog.isDef(opt_highBits)) {
if (opt_highBits != jspb.utils.split64High) throw 'fail!';
}
if (goog.isDef(opt_lowBits)) {
if (opt_lowBits != jspb.utils.split64Low) throw 'fail!';
}
if (x != jspb.utils.joinFloat64(jspb.utils.split64Low,
jspb.utils.split64High)) {
throw 'fail!';
}
}
// Positive and negative infinity.
test(Infinity, 0x7ff00000, 0x00000000);
test(-Infinity, 0xfff00000, 0x00000000);
// Positive and negative zero.
test(0, 0x00000000, 0x00000000);
test(-0, 0x80000000, 0x00000000);
// Positive and negative epsilon.
test(f64_eps, 0x00000000, 0x00000001);
test(-f64_eps, 0x80000000, 0x00000001);
// Positive and negative min.
test(f64_min, 0x00100000, 0x00000000);
test(-f64_min, 0x80100000, 0x00000000);
// Positive and negative max.
test(f64_max, 0x7FEFFFFF, 0xFFFFFFFF);
test(-f64_max, 0xFFEFFFFF, 0xFFFFFFFF);
// Various positive values.
var cursor = f64_eps * 10;
while (cursor != Infinity) {
test(cursor);
cursor *= 1.1;
}
// Various negative values.
cursor = -f64_eps * 10;
while (cursor != -Infinity) {
test(cursor);
cursor *= 1.1;
}
});
/**
* Tests counting packed varints.
*/
it('testCountVarints', function() {
var values = [];
for (var i = 1; i < 1000000000; i *= 1.1) {
values.push(Math.floor(i));
}
var writer = new jspb.BinaryWriter();
writer.writePackedUint64(1, values);
var buffer = new Uint8Array(writer.getResultBuffer());
// We should have two more varints than we started with - one for the field
// tag, one for the packed length.
assertEquals(values.length + 2,
jspb.utils.countVarints(buffer, 0, buffer.length));
});
/**
* Tests counting matching varint fields.
*/
it('testCountVarintFields', function() {
var writer = new jspb.BinaryWriter();
var count = 0;
for (var i = 1; i < 1000000000; i *= 1.1) {
writer.writeUint64(1, Math.floor(i));
count++;
}
writer.writeString(2, 'terminator');
var buffer = new Uint8Array(writer.getResultBuffer());
assertEquals(count,
jspb.utils.countVarintFields(buffer, 0, buffer.length, 1));
writer = new jspb.BinaryWriter();
count = 0;
for (var i = 1; i < 1000000000; i *= 1.1) {
writer.writeUint64(123456789, Math.floor(i));
count++;
}
writer.writeString(2, 'terminator');
buffer = new Uint8Array(writer.getResultBuffer());
assertEquals(count,
jspb.utils.countVarintFields(buffer, 0, buffer.length, 123456789));
});
/**
* Tests counting matching fixed32 fields.
*/
it('testCountFixed32Fields', function() {
var writer = new jspb.BinaryWriter();
var count = 0;
for (var i = 1; i < 1000000000; i *= 1.1) {
writer.writeFixed32(1, Math.floor(i));
count++;
}
writer.writeString(2, 'terminator');
var buffer = new Uint8Array(writer.getResultBuffer());
assertEquals(count,
jspb.utils.countFixed32Fields(buffer, 0, buffer.length, 1));
writer = new jspb.BinaryWriter();
count = 0;
for (var i = 1; i < 1000000000; i *= 1.1) {
writer.writeFixed32(123456789, Math.floor(i));
count++;
}
writer.writeString(2, 'terminator');
buffer = new Uint8Array(writer.getResultBuffer());
assertEquals(count,
jspb.utils.countFixed32Fields(buffer, 0, buffer.length, 123456789));
});
/**
* Tests counting matching fixed64 fields.
*/
it('testCountFixed64Fields', function() {
var writer = new jspb.BinaryWriter();
var count = 0;
for (var i = 1; i < 1000000000; i *= 1.1) {
writer.writeDouble(1, i);
count++;
}
writer.writeString(2, 'terminator');
var buffer = new Uint8Array(writer.getResultBuffer());
assertEquals(count,
jspb.utils.countFixed64Fields(buffer, 0, buffer.length, 1));
writer = new jspb.BinaryWriter();
count = 0;
for (var i = 1; i < 1000000000; i *= 1.1) {
writer.writeDouble(123456789, i);
count++;
}
writer.writeString(2, 'terminator');
buffer = new Uint8Array(writer.getResultBuffer());
assertEquals(count,
jspb.utils.countFixed64Fields(buffer, 0, buffer.length, 123456789));
});
/**
* Tests counting matching delimited fields.
*/
it('testCountDelimitedFields', function() {
var writer = new jspb.BinaryWriter();
var count = 0;
for (var i = 1; i < 1000; i *= 1.1) {
writer.writeBytes(1, [Math.floor(i)]);
count++;
}
writer.writeString(2, 'terminator');
var buffer = new Uint8Array(writer.getResultBuffer());
assertEquals(count,
jspb.utils.countDelimitedFields(buffer, 0, buffer.length, 1));
writer = new jspb.BinaryWriter();
count = 0;
for (var i = 1; i < 1000; i *= 1.1) {
writer.writeBytes(123456789, [Math.floor(i)]);
count++;
}
writer.writeString(2, 'terminator');
buffer = new Uint8Array(writer.getResultBuffer());
assertEquals(count,
jspb.utils.countDelimitedFields(buffer, 0, buffer.length, 123456789));
});
/**
* Tests byte format for debug strings.
*/
it('testDebugBytesToTextFormat', function() {
assertEquals('""', jspb.utils.debugBytesToTextFormat(null));
assertEquals('"\\x00\\x10\\xff"',
jspb.utils.debugBytesToTextFormat([0, 16, 255]));
});
/**
* Tests converting byte blob sources into byte blobs.
*/
it('testByteSourceToUint8Array', function() {
var convert = jspb.utils.byteSourceToUint8Array;
var sourceData = [];
for (var i = 0; i < 256; i++) {
sourceData.push(i);
}
var sourceBytes = new Uint8Array(sourceData);
var sourceBuffer = sourceBytes.buffer;
var sourceBase64 = goog.crypt.base64.encodeByteArray(sourceData);
var sourceString = String.fromCharCode.apply(null, sourceData);
function check(result) {
assertEquals(Uint8Array, result.constructor);
assertEquals(sourceData.length, result.length);
for (var i = 0; i < result.length; i++) {
assertEquals(sourceData[i], result[i]);
}
}
// Converting Uint8Arrays into Uint8Arrays should be a no-op.
assertEquals(sourceBytes, convert(sourceBytes));
// Converting Array.<numbers> into Uint8Arrays should work.
check(convert(sourceData));
// Converting ArrayBuffers into Uint8Arrays should work.
check(convert(sourceBuffer));
// Converting base64-encoded strings into Uint8Arrays should work.
check(convert(sourceBase64));
});
});
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
/**
* @fileoverview Test cases for jspb's binary protocol buffer writer. In
* practice BinaryWriter is used to drive the Decoder and Reader test cases,
* so only writer-specific tests are here.
*
* Test suite is written using Jasmine -- see http://jasmine.github.io/
*
* @author aappleby@google.com (Austin Appleby)
*/
goog.require('goog.crypt');
goog.require('goog.testing.asserts');
goog.require('jspb.BinaryWriter');
/**
* @param {function()} func This function should throw an error when run.
*/
function assertFails(func) {
var e = assertThrows(func);
//assertNotNull(e.toString().match(/Error/));
}
describe('binaryWriterTest', function() {
/**
* Verifies that misuse of the writer class triggers assertions.
*/
it('testWriteErrors', function() {
// Submessages with invalid field indices should assert.
var writer = new jspb.BinaryWriter();
var dummyMessage = /** @type {!jspb.BinaryMessage} */({});
assertFails(function() {
writer.writeMessage(-1, dummyMessage, goog.nullFunction);
});
// Writing invalid field indices should assert.
writer = new jspb.BinaryWriter();
assertFails(function() {writer.writeUint64(-1, 1);});
// Writing out-of-range field values should assert.
writer = new jspb.BinaryWriter();
assertFails(function() {writer.writeInt32(1, -Infinity);});
assertFails(function() {writer.writeInt32(1, Infinity);});
assertFails(function() {writer.writeInt64(1, -Infinity);});
assertFails(function() {writer.writeInt64(1, Infinity);});
assertFails(function() {writer.writeUint32(1, -1);});
assertFails(function() {writer.writeUint32(1, Infinity);});
assertFails(function() {writer.writeUint64(1, -1);});
assertFails(function() {writer.writeUint64(1, Infinity);});
assertFails(function() {writer.writeSint32(1, -Infinity);});
assertFails(function() {writer.writeSint32(1, Infinity);});
assertFails(function() {writer.writeSint64(1, -Infinity);});
assertFails(function() {writer.writeSint64(1, Infinity);});
assertFails(function() {writer.writeFixed32(1, -1);});
assertFails(function() {writer.writeFixed32(1, Infinity);});
assertFails(function() {writer.writeFixed64(1, -1);});
assertFails(function() {writer.writeFixed64(1, Infinity);});
assertFails(function() {writer.writeSfixed32(1, -Infinity);});
assertFails(function() {writer.writeSfixed32(1, Infinity);});
assertFails(function() {writer.writeSfixed64(1, -Infinity);});
assertFails(function() {writer.writeSfixed64(1, Infinity);});
});
/**
* Basic test of retrieving the result as a Uint8Array buffer
*/
it('testGetResultBuffer', function() {
var expected = '0864120b48656c6c6f20776f726c641a0301020320c801';
var writer = new jspb.BinaryWriter();
writer.writeUint32(1, 100);
writer.writeString(2, 'Hello world');
writer.writeBytes(3, new Uint8Array([1, 2, 3]));
writer.writeUint32(4, 200);
var buffer = writer.getResultBuffer();
assertEquals(expected, goog.crypt.byteArrayToHex(buffer));
});
});
/**
* @fileoverview Exports symbols needed only by tests.
*
* This file exports several Closure Library symbols that are only
* used by tests. It is used to generate a file
* closure_asserts_commonjs.js that is only used at testing time.
*/
goog.require('goog.testing.asserts');
var global = Function('return this')();
// All of the closure "assert" functions are exported at the global level.
//
// The Google Closure assert functions start with assert, eg.
// assertThrows
// assertNotThrows
// assertTrue
// ...
//
// The one exception is the "fail" function.
function shouldExport(str) {
return str.lastIndexOf('assert') === 0 || str == 'fail';
}
for (var key in global) {
if ((typeof key == "string") && global.hasOwnProperty(key) &&
shouldExport(key)) {
exports[key] = global[key];
}
}
// The COMPILED variable is set by Closure compiler to "true" when it compiles
// JavaScript, so in practice this is equivalent to "exports.COMPILED = true".
// This will disable some debugging functionality in debug.js. We could
// investigate whether this can/should be enabled in CommonJS builds.
exports.COMPILED = COMPILED
/**
* @fileoverview Export symbols needed by tests in CommonJS style.
*
* This file is like export.js, but for symbols that are only used by tests.
* However we exclude assert functions here, because they are exported into
* the global namespace, so those are handled as a special case in
* export_asserts.js.
*/
goog.require('goog.crypt.base64');
goog.require('jspb.arith.Int64');
goog.require('jspb.arith.UInt64');
goog.require('jspb.BinaryEncoder');
goog.require('jspb.BinaryDecoder');
goog.require('jspb.utils');
exports.goog = goog;
exports.jspb = jspb;
// Protocol Buffers - Google's data interchange format
// Copyright 2016 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Test suite is written using Jasmine -- see http://jasmine.github.io/
var googleProtobuf = require('google-protobuf');
var asserts = require('closure_asserts_commonjs');
var global = Function('return this')();
// Bring asserts into the global namespace.
googleProtobuf.object.extend(global, asserts);
googleProtobuf.exportSymbol('jspb.Message', googleProtobuf.Message, global);
var test7_pb = require('./test7/test7_pb');
googleProtobuf.exportSymbol('proto.jspb.test.framing.FramingMessage', test7_pb.FramingMessage, global);
describe('Import test suite', function() {
it('testImportedMessage', function() {
var framing1 = new proto.jspb.test.framing.FramingMessage([]);
var framing2 = new proto.jspb.test.framing.FramingMessage([]);
assertObjectEquals(framing1.toObject(), framing2.toObject());
});
});
{
"spec_dir": "",
"spec_files": [
"*_test.js",
"binary/proto_test.js"
],
"helpers": [
]
}
/**
* @fileoverview Utility to translate test files to CommonJS imports.
*
* This is a somewhat hacky tool designed to do one very specific thing.
* All of the test files in *_test.js are written with Closure-style
* imports (goog.require()). This works great for running the tests
* against Closure-style generated code, but we also want to run the
* tests against CommonJS-style generated code without having to fork
* the tests.
*
* Closure-style imports import each individual type by name. This is
* very different than CommonJS imports which are by file. So we put
* special comments in these tests like:
*
* // CommonJS-LoadFromFile: test_pb
* goog.require('proto.jspb.test.CloneExtension');
* goog.require('proto.jspb.test.Complex');
* goog.require('proto.jspb.test.DefaultValues');
*
* This script parses that special comment and uses it to generate proper
* CommonJS require() statements so that the tests can run and pass using
* CommonJS imports. The script will change the above statements into:
*
* var test_pb = require('test_pb');
* googleProtobuf.exportSymbol('proto.jspb.test.CloneExtension', test_pb.CloneExtension, global);
* googleProtobuf.exportSymbol('proto.jspb.test.Complex', test_pb.Complex, global);
* googleProtobuf.exportSymbol('proto.jspb.test.DefaultValues', test_pb.DefaultValues, global);
*
* (The "exportSymbol" function will define the given names in the global
* namespace, taking care not to overwrite any previous value for
* "proto.jspb.test").
*/
var lineReader = require('readline').createInterface({
input: process.stdin,
output: process.stdout
});
function tryStripPrefix(str, prefix) {
if (str.lastIndexOf(prefix) !== 0) {
throw "String: " + str + " didn't start with: " + prefix;
}
return str.substr(prefix.length);
}
function camelCase(str) {
var ret = '';
var ucaseNext = false;
for (var i = 0; i < str.length; i++) {
if (str[i] == '-') {
ucaseNext = true;
} else if (ucaseNext) {
ret += str[i].toUpperCase();
ucaseNext = false;
} else {
ret += str[i];
}
}
return ret;
}
var module = null;
var pkg = null;
// Header: goes in every file at the top.
console.log("var global = Function('return this')();");
console.log("var googleProtobuf = require('google-protobuf');");
console.log("var testdeps = require('testdeps_commonjs');");
console.log("global.goog = testdeps.goog;");
console.log("global.jspb = testdeps.jspb;");
console.log("var asserts = require('closure_asserts_commonjs');");
console.log("");
console.log("// Bring asserts into the global namespace.");
console.log("googleProtobuf.object.extend(global, asserts);");
lineReader.on('line', function(line) {
var isRequire = line.match(/goog\.require\('([^']*)'\)/);
var isLoadFromFile = line.match(/CommonJS-LoadFromFile: (\S*) (.*)/);
var isSetTestOnly = line.match(/goog.setTestOnly()/);
if (isRequire) {
if (module) { // Skip goog.require() lines before the first directive.
var fullSym = isRequire[1];
var sym = tryStripPrefix(fullSym, pkg);
console.log("googleProtobuf.exportSymbol('" + fullSym + "', " + module + sym + ', global);');
}
} else if (isLoadFromFile) {
var module_path = isLoadFromFile[1].split('/');
module = camelCase(module_path[module_path.length - 1]);
pkg = isLoadFromFile[2];
if (module != "googleProtobuf") { // We unconditionally require this in the header.
console.log("var " + module + " = require('./" + isLoadFromFile[1] + "');");
}
} else if (!isSetTestOnly) { // Remove goog.setTestOnly() lines.
console.log(line);
}
});
// Protocol Buffers - Google's data interchange format
// Copyright 2016 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
syntax = "proto3";
option java_package = "com.google.apps.jspb.proto";
option java_multiple_files = true;
package jspb.test.importing;
message ImportedMessage {
string string_value = 1;
}
// Protocol Buffers - Google's data interchange format
// Copyright 2016 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
syntax = "proto3";
option java_package = "com.google.apps.jspb.proto";
option java_multiple_files = true;
package jspb.test.framing;
import "test6/test6.proto";
message FramingMessage {
jspb.test.importing.ImportedMessage imported_message = 1;
}
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: mwr@google.com (Mark Rawling)
syntax = "proto2";
option java_package = "com.google.apps.jspb.proto";
option java_multiple_files = true;
package jspb.test;
// legacy data, must be nested
message data {
message NestedData {
required string str = 1;
}
}
// new data, does not require nesting
message UnnestedData {
required string str = 1;
}
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
goog.setTestOnly();
goog.require('goog.testing.asserts');
// CommonJS-LoadFromFile: google-protobuf
goog.require('jspb.debug');
// CommonJS-LoadFromFile: test_pb
goog.require('proto.jspb.test.HasExtensions');
goog.require('proto.jspb.test.IsExtension');
goog.require('proto.jspb.test.Simple1');
describe('debugTest', function() {
it('testSimple1', function() {
if (COMPILED) {
return;
}
var message = new proto.jspb.test.Simple1();
message.setAString('foo');
assertObjectEquals({
$name: 'proto.jspb.test.Simple1',
'aString': 'foo',
'aRepeatedStringList': []
}, jspb.debug.dump(message));
message.setABoolean(true);
message.setARepeatedStringList(['1', '2']);
assertObjectEquals({
$name: 'proto.jspb.test.Simple1',
'aString': 'foo',
'aRepeatedStringList': ['1', '2'],
'aBoolean': true
}, jspb.debug.dump(message));
message.setAString(undefined);
assertObjectEquals({
$name: 'proto.jspb.test.Simple1',
'aRepeatedStringList': ['1', '2'],
'aBoolean': true
}, jspb.debug.dump(message));
});
it('testExtensions', function() {
if (COMPILED) {
return;
}
var extension = new proto.jspb.test.IsExtension();
extension.setExt1('ext1field');
var extendable = new proto.jspb.test.HasExtensions();
extendable.setStr1('v1');
extendable.setStr2('v2');
extendable.setStr3('v3');
extendable.setExtension(proto.jspb.test.IsExtension.extField, extension);
assertObjectEquals({
'$name': 'proto.jspb.test.HasExtensions',
'str1': 'v1',
'str2': 'v2',
'str3': 'v3',
'$extensions': {
'extField': {
'$name': 'proto.jspb.test.IsExtension',
'ext1': 'ext1field'
},
'repeatedSimpleList': []
}
}, jspb.debug.dump(extendable));
});
});
{
"spec_dir": "",
"spec_files": [
"*_test.js",
"binary/*_test.js"
],
"helpers": [
"../../../js/node_modules/google-closure-library/closure/goog/bootstrap/nodejs.js",
"../../../js/node_loader.js",
"../../../js/deps.js",
"../../../js/google/protobuf/any.js",
"../../../js/google/protobuf/struct.js",
"../../../js/google/protobuf/timestamp.js",
"testproto_libs1.js",
"testproto_libs2.js"
]
}
{
"spec_dir": "",
"spec_files": [
"*_test.js",
"binary/*_test.js"
],
"helpers": [
"../../../js/node_modules/google-closure-library/closure/goog/bootstrap/nodejs.js",
"../../../js/node_loader.js",
"../../../js/deps.js",
"../../../js/google/protobuf/any.js",
"../../../js/google/protobuf/struct.js",
"../../../js/google/protobuf/timestamp.js",
"testproto_libs1_new.js",
"testproto_libs2.js"
]
}
{
"spec_dir": "",
"spec_files": [
"*_test.js",
"binary/*_test.js"
],
"helpers": [
"../../../js/node_modules/google-closure-library/closure/goog/bootstrap/nodejs.js",
"../../../js/node_loader.js",
"../../../js/deps.js",
"../../../js/google/protobuf/any.js",
"../../../js/google/protobuf/struct.js",
"../../../js/google/protobuf/timestamp.js",
"testproto_libs1.js",
"testproto_libs2_new.js"
]
}
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Test suite is written using Jasmine -- see http://jasmine.github.io/
goog.setTestOnly();
goog.require('goog.json');
goog.require('goog.testing.asserts');
goog.require('goog.userAgent');
// CommonJS-LoadFromFile: google-protobuf jspb
goog.require('jspb.Message');
// CommonJS-LoadFromFile: test5_pb proto.jspb.exttest.beta
goog.require('proto.jspb.exttest.beta.floatingStrField');
// CommonJS-LoadFromFile: test3_pb proto.jspb.exttest
goog.require('proto.jspb.exttest.floatingMsgField');
// CommonJS-LoadFromFile: test4_pb proto.jspb.exttest
goog.require('proto.jspb.exttest.floatingMsgFieldTwo');
// CommonJS-LoadFromFile: test_pb proto.jspb.test
goog.require('proto.jspb.test.CloneExtension');
goog.require('proto.jspb.test.Complex');
goog.require('proto.jspb.test.DefaultValues');
goog.require('proto.jspb.test.Empty');
goog.require('proto.jspb.test.EnumContainer');
goog.require('proto.jspb.test.floatingMsgField');
goog.require('proto.jspb.test.FloatingPointFields');
goog.require('proto.jspb.test.floatingStrField');
goog.require('proto.jspb.test.HasExtensions');
goog.require('proto.jspb.test.IndirectExtension');
goog.require('proto.jspb.test.IsExtension');
goog.require('proto.jspb.test.OptionalFields');
goog.require('proto.jspb.test.OuterEnum');
goog.require('proto.jspb.test.OuterMessage.Complex');
goog.require('proto.jspb.test.Simple1');
goog.require('proto.jspb.test.Simple2');
goog.require('proto.jspb.test.SpecialCases');
goog.require('proto.jspb.test.TestClone');
goog.require('proto.jspb.test.TestEndsWithBytes');
goog.require('proto.jspb.test.TestGroup');
goog.require('proto.jspb.test.TestGroup1');
goog.require('proto.jspb.test.TestMessageWithOneof');
goog.require('proto.jspb.test.TestReservedNames');
goog.require('proto.jspb.test.TestReservedNamesExtension');
// CommonJS-LoadFromFile: test2_pb proto.jspb.test
goog.require('proto.jspb.test.ExtensionMessage');
goog.require('proto.jspb.test.TestExtensionsMessage');
describe('Message test suite', function() {
it('testEmptyProto', function() {
var empty1 = new proto.jspb.test.Empty([]);
var empty2 = new proto.jspb.test.Empty([]);
assertObjectEquals({}, empty1.toObject());
assertObjectEquals('Message should not be corrupted:', empty2, empty1);
});
it('testTopLevelEnum', function() {
var response = new proto.jspb.test.EnumContainer([]);
response.setOuterEnum(proto.jspb.test.OuterEnum.FOO);
assertEquals(proto.jspb.test.OuterEnum.FOO, response.getOuterEnum());
});
it('testByteStrings', function() {
var data = new proto.jspb.test.DefaultValues([]);
data.setBytesField('some_bytes');
assertEquals('some_bytes', data.getBytesField());
});
it('testComplexConversion', function() {
var data1 = ['a',,, [, 11], [[, 22], [, 33]],, ['s1', 's2'],, 1];
var data2 = ['a',,, [, 11], [[, 22], [, 33]],, ['s1', 's2'],, 1];
var foo = new proto.jspb.test.Complex(data1);
var bar = new proto.jspb.test.Complex(data2);
var result = foo.toObject();
assertObjectEquals({
aString: 'a',
anOutOfOrderBool: 1,
aNestedMessage: {
anInt: 11
},
aRepeatedMessageList: [{anInt: 22}, {anInt: 33}],
aRepeatedStringList: ['s1', 's2']
}, result);
// Now test with the jspb instances included.
result = foo.toObject(true /* opt_includeInstance */);
assertObjectEquals({
aString: 'a',
anOutOfOrderBool: 1,
aNestedMessage: {
anInt: 11,
$jspbMessageInstance: foo.getANestedMessage()
},
aRepeatedMessageList: [
{anInt: 22, $jspbMessageInstance: foo.getARepeatedMessageList()[0]},
{anInt: 33, $jspbMessageInstance: foo.getARepeatedMessageList()[1]}
],
aRepeatedStringList: ['s1', 's2'],
$jspbMessageInstance: foo
}, result);
});
it('testMissingFields', function() {
var foo = new proto.jspb.test.Complex([
undefined, undefined, undefined, [],
undefined, undefined, undefined, undefined]);
var bar = new proto.jspb.test.Complex([
undefined, undefined, undefined, [],
undefined, undefined, undefined, undefined]);
var result = foo.toObject();
assertObjectEquals({
aString: undefined,
anOutOfOrderBool: undefined,
aNestedMessage: {
anInt: undefined
},
// Note: JsPb converts undefined repeated fields to empty arrays.
aRepeatedMessageList: [],
aRepeatedStringList: []
}, result);
});
it('testNestedComplexMessage', function() {
// Instantiate the message and set a unique field, just to ensure that we
// are not getting jspb.test.Complex instead.
var msg = new proto.jspb.test.OuterMessage.Complex();
msg.setInnerComplexField(5);
});
it('testSpecialCases', function() {
// Note: Some property names are reserved in JavaScript.
// These names are converted to the Js property named pb_<reserved_name>.
var special =
new proto.jspb.test.SpecialCases(['normal', 'default', 'function',
'var']);
var result = special.toObject();
assertObjectEquals({
normal: 'normal',
pb_default: 'default',
pb_function: 'function',
pb_var: 'var'
}, result);
});
it('testDefaultValues', function() {
var defaultString = "default<>\'\"abc";
var response = new proto.jspb.test.DefaultValues();
// Test toObject
var expectedObject = {
stringField: defaultString,
boolField: true,
intField: 11,
enumField: 13,
emptyField: '',
bytesField: 'bW9v'
};
assertObjectEquals(expectedObject, response.toObject());
// Test getters
response = new proto.jspb.test.DefaultValues();
assertEquals(defaultString, response.getStringField());
assertEquals(true, response.getBoolField());
assertEquals(11, response.getIntField());
assertEquals(13, response.getEnumField());
assertEquals('', response.getEmptyField());
assertEquals('bW9v', response.getBytesField());
function makeDefault(values) {
return new proto.jspb.test.DefaultValues(values);
}
// Test with undefined values,
// Use push to workaround IE treating undefined array elements as holes.
response = makeDefault([undefined, undefined, undefined, undefined]);
assertEquals(defaultString, response.getStringField());
assertEquals(true, response.getBoolField());
assertEquals(11, response.getIntField());
assertEquals(13, response.getEnumField());
assertFalse(response.hasStringField());
assertFalse(response.hasBoolField());
assertFalse(response.hasIntField());
assertFalse(response.hasEnumField());
// Test with null values, as would be returned by a JSON serializer.
response = makeDefault([null, null, null, null]);
assertEquals(defaultString, response.getStringField());
assertEquals(true, response.getBoolField());
assertEquals(11, response.getIntField());
assertEquals(13, response.getEnumField());
assertFalse(response.hasStringField());
assertFalse(response.hasBoolField());
assertFalse(response.hasIntField());
assertFalse(response.hasEnumField());
// Test with false-like values.
response = makeDefault(['', false, 0, 0]);
assertEquals('', response.getStringField());
assertEquals(false, response.getBoolField());
assertEquals(true, response.getIntField() == 0);
assertEquals(true, response.getEnumField() == 0);
assertTrue(response.hasStringField());
assertTrue(response.hasBoolField());
assertTrue(response.hasIntField());
assertTrue(response.hasEnumField());
// Test that clearing the values reverts them to the default state.
response = makeDefault(['blah', false, 111, 77]);
response.clearStringField(); response.clearBoolField();
response.clearIntField(); response.clearEnumField();
assertEquals(defaultString, response.getStringField());
assertEquals(true, response.getBoolField());
assertEquals(11, response.getIntField());
assertEquals(13, response.getEnumField());
assertFalse(response.hasStringField());
assertFalse(response.hasBoolField());
assertFalse(response.hasIntField());
assertFalse(response.hasEnumField());
// Test that setFoo(null) clears the values.
response = makeDefault(['blah', false, 111, 77]);
response.setStringField(null); response.setBoolField(null);
response.setIntField(undefined); response.setEnumField(undefined);
assertEquals(defaultString, response.getStringField());
assertEquals(true, response.getBoolField());
assertEquals(11, response.getIntField());
assertEquals(13, response.getEnumField());
assertFalse(response.hasStringField());
assertFalse(response.hasBoolField());
assertFalse(response.hasIntField());
assertFalse(response.hasEnumField());
});
it('testMessageRegistration', function() {
// goog.require(SomeResponse) will include its library, which will in
// turn add SomeResponse to the message registry.
assertEquals(jspb.Message.registry_['res'], proto.jspb.test.SomeResponse);
});
it('testClearFields', function() {
var data = ['str', true, [11], [[22], [33]], ['s1', 's2']];
var foo = new proto.jspb.test.OptionalFields(data);
foo.clearAString();
foo.clearABool();
foo.clearANestedMessage();
foo.clearARepeatedMessageList();
foo.clearARepeatedStringList();
assertEquals('', foo.getAString());
assertEquals(false, foo.getABool());
assertUndefined(foo.getANestedMessage());
assertFalse(foo.hasAString());
assertFalse(foo.hasABool());
assertObjectEquals([], foo.getARepeatedMessageList());
assertObjectEquals([], foo.getARepeatedStringList());
// NOTE: We want the missing fields in 'expected' to be undefined,
// but we actually get a sparse array instead. We could use something
// like [1,undefined,2] to avoid this, except that this is still
// sparse on IE. No comment...
var expected = [,,, [], []];
expected[0] = expected[1] = expected[2] = undefined;
assertObjectEquals(expected, foo.toArray());
// Test set(null). We could deprecated this in favor of clear(), but
// it's also convenient to have.
data = ['str', true, [11], [[22], [33]], ['s1', 's2']];
foo = new proto.jspb.test.OptionalFields(data);
foo.setAString(null);
foo.setABool(null);
foo.setANestedMessage(null);
foo.setARepeatedMessageList(null);
foo.setARepeatedStringList(null);
assertEquals('', foo.getAString());
assertEquals(false, foo.getABool());
assertNull(foo.getANestedMessage());
assertFalse(foo.hasAString());
assertFalse(foo.hasABool());
assertObjectEquals([], foo.getARepeatedMessageList());
assertObjectEquals([], foo.getARepeatedStringList());
assertObjectEquals([null, null, null, [], []], foo.toArray());
// Test set(undefined). Again, not something we really need, and not
// supported directly by our typing, but it should 'do the right thing'.
data = ['str', true, [11], [[22], [33]], ['s1', 's2']];
foo = new proto.jspb.test.OptionalFields(data);
foo.setAString(undefined);
foo.setABool(undefined);
foo.setANestedMessage(undefined);
foo.setARepeatedMessageList(undefined);
foo.setARepeatedStringList(undefined);
assertEquals('', foo.getAString());
assertEquals(false, foo.getABool());
assertUndefined(foo.getANestedMessage());
assertFalse(foo.hasAString());
assertFalse(foo.hasABool());
assertObjectEquals([], foo.getARepeatedMessageList());
assertObjectEquals([], foo.getARepeatedStringList());
expected = [,,, [], []];
expected[0] = expected[1] = expected[2] = undefined;
assertObjectEquals(expected, foo.toArray());
});
it('testDifferenceRawObject', function() {
var p1 = new proto.jspb.test.HasExtensions(['hi', 'diff', {}]);
var p2 = new proto.jspb.test.HasExtensions(['hi', 'what',
{1000: 'unique'}]);
var diff = /** @type {proto.jspb.test.HasExtensions} */
(jspb.Message.difference(p1, p2));
assertEquals('', diff.getStr1());
assertEquals('what', diff.getStr2());
assertEquals('', diff.getStr3());
assertEquals('unique', diff.extensionObject_[1000]);
});
it('testEqualsSimple', function() {
var s1 = new proto.jspb.test.Simple1(['hi']);
assertTrue(jspb.Message.equals(s1, new proto.jspb.test.Simple1(['hi'])));
assertFalse(jspb.Message.equals(s1, new proto.jspb.test.Simple1(['bye'])));
var s1b = new proto.jspb.test.Simple1(['hi', ['hello']]);
assertTrue(jspb.Message.equals(s1b,
new proto.jspb.test.Simple1(['hi', ['hello']])));
assertTrue(jspb.Message.equals(s1b,
new proto.jspb.test.Simple1(['hi', ['hello', undefined,
undefined, undefined]])));
assertFalse(jspb.Message.equals(s1b,
new proto.jspb.test.Simple1(['no', ['hello']])));
// Test with messages of different types
var s2 = new proto.jspb.test.Simple2(['hi']);
assertFalse(jspb.Message.equals(s1, s2));
});
it('testEquals_softComparison', function() {
var s1 = new proto.jspb.test.Simple1(['hi', [], null]);
assertTrue(jspb.Message.equals(s1,
new proto.jspb.test.Simple1(['hi', []])));
var s1b = new proto.jspb.test.Simple1(['hi', [], true]);
assertTrue(jspb.Message.equals(s1b,
new proto.jspb.test.Simple1(['hi', [], 1])));
});
it('testEqualsComplex', function() {
var data1 = ['a',,, [, 11], [[, 22], [, 33]],, ['s1', 's2'],, 1];
var data2 = ['a',,, [, 11], [[, 22], [, 34]],, ['s1', 's2'],, 1];
var data3 = ['a',,, [, 11], [[, 22]],, ['s1', 's2'],, 1];
var data4 = ['hi'];
var c1a = new proto.jspb.test.Complex(data1);
var c1b = new proto.jspb.test.Complex(data1);
var c2 = new proto.jspb.test.Complex(data2);
var c3 = new proto.jspb.test.Complex(data3);
var s1 = new proto.jspb.test.Simple1(data4);
assertTrue(jspb.Message.equals(c1a, c1b));
assertFalse(jspb.Message.equals(c1a, c2));
assertFalse(jspb.Message.equals(c2, c3));
assertFalse(jspb.Message.equals(c1a, s1));
});
it('testEqualsExtensionsConstructed', function() {
assertTrue(jspb.Message.equals(
new proto.jspb.test.HasExtensions([]),
new proto.jspb.test.HasExtensions([{}])
));
assertTrue(jspb.Message.equals(
new proto.jspb.test.HasExtensions(['hi', {100: [{200: 'a'}]}]),
new proto.jspb.test.HasExtensions(['hi', {100: [{200: 'a'}]}])
));
assertFalse(jspb.Message.equals(
new proto.jspb.test.HasExtensions(['hi', {100: [{200: 'a'}]}]),
new proto.jspb.test.HasExtensions(['hi', {100: [{200: 'b'}]}])
));
assertTrue(jspb.Message.equals(
new proto.jspb.test.HasExtensions([{100: [{200: 'a'}]}]),
new proto.jspb.test.HasExtensions([{100: [{200: 'a'}]}])
));
assertTrue(jspb.Message.equals(
new proto.jspb.test.HasExtensions([{100: [{200: 'a'}]}]),
new proto.jspb.test.HasExtensions([,,, {100: [{200: 'a'}]}])
));
assertTrue(jspb.Message.equals(
new proto.jspb.test.HasExtensions([,,, {100: [{200: 'a'}]}]),
new proto.jspb.test.HasExtensions([{100: [{200: 'a'}]}])
));
assertTrue(jspb.Message.equals(
new proto.jspb.test.HasExtensions(['hi', {100: [{200: 'a'}]}]),
new proto.jspb.test.HasExtensions(['hi',,, {100: [{200: 'a'}]}])
));
assertTrue(jspb.Message.equals(
new proto.jspb.test.HasExtensions(['hi',,, {100: [{200: 'a'}]}]),
new proto.jspb.test.HasExtensions(['hi', {100: [{200: 'a'}]}])
));
});
it('testEqualsExtensionsUnconstructed', function() {
assertTrue(jspb.Message.compareFields([], [{}]));
assertTrue(jspb.Message.compareFields([,,, {}], []));
assertTrue(jspb.Message.compareFields([,,, {}], [,, {}]));
assertTrue(jspb.Message.compareFields(
['hi', {100: [{200: 'a'}]}], ['hi', {100: [{200: 'a'}]}]));
assertFalse(jspb.Message.compareFields(
['hi', {100: [{200: 'a'}]}], ['hi', {100: [{200: 'b'}]}]));
assertTrue(jspb.Message.compareFields(
[{100: [{200: 'a'}]}], [{100: [{200: 'a'}]}]));
assertTrue(jspb.Message.compareFields(
[{100: [{200: 'a'}]}], [,,, {100: [{200: 'a'}]}]));
assertTrue(jspb.Message.compareFields(
[,,, {100: [{200: 'a'}]}], [{100: [{200: 'a'}]}]));
assertTrue(jspb.Message.compareFields(
['hi', {100: [{200: 'a'}]}], ['hi',,, {100: [{200: 'a'}]}]));
assertTrue(jspb.Message.compareFields(
['hi',,, {100: [{200: 'a'}]}], ['hi', {100: [{200: 'a'}]}]));
});
it('testToMap', function() {
var p1 = new proto.jspb.test.Simple1(['k', ['v']]);
var p2 = new proto.jspb.test.Simple1(['k1', ['v1', 'v2']]);
var soymap = jspb.Message.toMap([p1, p2],
proto.jspb.test.Simple1.prototype.getAString,
proto.jspb.test.Simple1.prototype.toObject);
assertEquals('k', soymap['k'].aString);
assertArrayEquals(['v'], soymap['k'].aRepeatedStringList);
var protomap = jspb.Message.toMap([p1, p2],
proto.jspb.test.Simple1.prototype.getAString);
assertEquals('k', protomap['k'].getAString());
assertArrayEquals(['v'], protomap['k'].getARepeatedStringList());
});
it('testClone', function() {
var supportsUint8Array =
!goog.userAgent.IE || goog.userAgent.isVersionOrHigher('10');
var original = new proto.jspb.test.TestClone();
original.setStr('v1');
var simple1 = new proto.jspb.test.Simple1(['x1', ['y1', 'z1']]);
var simple2 = new proto.jspb.test.Simple1(['x2', ['y2', 'z2']]);
var simple3 = new proto.jspb.test.Simple1(['x3', ['y3', 'z3']]);
original.setSimple1(simple1);
original.setSimple2List([simple2, simple3]);
var bytes1 = supportsUint8Array ? new Uint8Array([1, 2, 3]) : '123';
original.setBytesField(bytes1);
var extension = new proto.jspb.test.CloneExtension();
extension.setExt('e1');
original.setExtension(proto.jspb.test.IsExtension.extField, extension);
var clone = original.cloneMessage();
assertArrayEquals(['v1',, ['x1', ['y1', 'z1']],,
[['x2', ['y2', 'z2']], ['x3', ['y3', 'z3']]], bytes1,, { 100: [, 'e1'] }],
clone.toArray());
clone.setStr('v2');
var simple4 = new proto.jspb.test.Simple1(['a1', ['b1', 'c1']]);
var simple5 = new proto.jspb.test.Simple1(['a2', ['b2', 'c2']]);
var simple6 = new proto.jspb.test.Simple1(['a3', ['b3', 'c3']]);
clone.setSimple1(simple4);
clone.setSimple2List([simple5, simple6]);
if (supportsUint8Array) {
clone.getBytesField()[0] = 4;
assertObjectEquals(bytes1, original.getBytesField());
}
var bytes2 = supportsUint8Array ? new Uint8Array([4, 5, 6]) : '456';
clone.setBytesField(bytes2);
var newExtension = new proto.jspb.test.CloneExtension();
newExtension.setExt('e2');
clone.setExtension(proto.jspb.test.CloneExtension.extField, newExtension);
assertArrayEquals(['v2',, ['a1', ['b1', 'c1']],,
[['a2', ['b2', 'c2']], ['a3', ['b3', 'c3']]], bytes2,, { 100: [, 'e2'] }],
clone.toArray());
assertArrayEquals(['v1',, ['x1', ['y1', 'z1']],,
[['x2', ['y2', 'z2']], ['x3', ['y3', 'z3']]], bytes1,, { 100: [, 'e1'] }],
original.toArray());
});
it('testCopyInto', function() {
var supportsUint8Array =
!goog.userAgent.IE || goog.userAgent.isVersionOrHigher('10');
var original = new proto.jspb.test.TestClone();
original.setStr('v1');
var dest = new proto.jspb.test.TestClone();
dest.setStr('override');
var simple1 = new proto.jspb.test.Simple1(['x1', ['y1', 'z1']]);
var simple2 = new proto.jspb.test.Simple1(['x2', ['y2', 'z2']]);
var simple3 = new proto.jspb.test.Simple1(['x3', ['y3', 'z3']]);
var destSimple1 = new proto.jspb.test.Simple1(['ox1', ['oy1', 'oz1']]);
var destSimple2 = new proto.jspb.test.Simple1(['ox2', ['oy2', 'oz2']]);
var destSimple3 = new proto.jspb.test.Simple1(['ox3', ['oy3', 'oz3']]);
original.setSimple1(simple1);
original.setSimple2List([simple2, simple3]);
dest.setSimple1(destSimple1);
dest.setSimple2List([destSimple2, destSimple3]);
var bytes1 = supportsUint8Array ? new Uint8Array([1, 2, 3]) : '123';
var bytes2 = supportsUint8Array ? new Uint8Array([4, 5, 6]) : '456';
original.setBytesField(bytes1);
dest.setBytesField(bytes2);
var extension = new proto.jspb.test.CloneExtension();
extension.setExt('e1');
original.setExtension(proto.jspb.test.CloneExtension.extField, extension);
jspb.Message.copyInto(original, dest);
assertArrayEquals(original.toArray(), dest.toArray());
assertEquals('x1', dest.getSimple1().getAString());
assertEquals('e1',
dest.getExtension(proto.jspb.test.CloneExtension.extField).getExt());
dest.getSimple1().setAString('new value');
assertNotEquals(dest.getSimple1().getAString(),
original.getSimple1().getAString());
if (supportsUint8Array) {
dest.getBytesField()[0] = 7;
assertObjectEquals(bytes1, original.getBytesField());
assertObjectEquals(new Uint8Array([7, 2, 3]), dest.getBytesField());
} else {
dest.setBytesField('789');
assertObjectEquals(bytes1, original.getBytesField());
assertObjectEquals('789', dest.getBytesField());
}
dest.getExtension(proto.jspb.test.CloneExtension.extField).
setExt('new value');
assertNotEquals(
dest.getExtension(proto.jspb.test.CloneExtension.extField).getExt(),
original.getExtension(
proto.jspb.test.CloneExtension.extField).getExt());
});
it('testCopyInto_notSameType', function() {
var a = new proto.jspb.test.TestClone();
var b = new proto.jspb.test.Simple1(['str', ['s1', 's2']]);
var e = assertThrows(function() {
jspb.Message.copyInto(a, b);
});
assertContains('should have the same type', e.message);
});
it('testExtensions', function() {
var extension1 = new proto.jspb.test.IsExtension(['ext1field']);
var extension2 = new proto.jspb.test.Simple1(['str', ['s1', 's2']]);
var extendable = new proto.jspb.test.HasExtensions(['v1', 'v2', 'v3']);
extendable.setExtension(proto.jspb.test.IsExtension.extField, extension1);
extendable.setExtension(proto.jspb.test.IndirectExtension.simple,
extension2);
extendable.setExtension(proto.jspb.test.IndirectExtension.str, 'xyzzy');
extendable.setExtension(proto.jspb.test.IndirectExtension.repeatedStrList,
['a', 'b']);
var s1 = new proto.jspb.test.Simple1(['foo', ['s1', 's2']]);
var s2 = new proto.jspb.test.Simple1(['bar', ['t1', 't2']]);
extendable.setExtension(
proto.jspb.test.IndirectExtension.repeatedSimpleList,
[s1, s2]);
assertObjectEquals(extension1,
extendable.getExtension(proto.jspb.test.IsExtension.extField));
assertObjectEquals(extension2,
extendable.getExtension(proto.jspb.test.IndirectExtension.simple));
assertObjectEquals('xyzzy',
extendable.getExtension(proto.jspb.test.IndirectExtension.str));
assertObjectEquals(['a', 'b'], extendable.getExtension(
proto.jspb.test.IndirectExtension.repeatedStrList));
assertObjectEquals([s1, s2], extendable.getExtension(
proto.jspb.test.IndirectExtension.repeatedSimpleList));
// Not supported yet, but it should work...
extendable.setExtension(proto.jspb.test.IndirectExtension.simple, null);
assertNull(
extendable.getExtension(proto.jspb.test.IndirectExtension.simple));
extendable.setExtension(proto.jspb.test.IndirectExtension.str, null);
assertNull(extendable.getExtension(proto.jspb.test.IndirectExtension.str));
// Extension fields with jspb.ignore = true are ignored.
assertUndefined(proto.jspb.test.IndirectExtension['ignored']);
assertUndefined(proto.jspb.test.HasExtensions['ignoredFloating']);
});
it('testFloatingExtensions', function() {
// From an autogenerated container.
var extendable = new proto.jspb.test.HasExtensions(['v1', 'v2', 'v3']);
var extension = new proto.jspb.test.Simple1(['foo', ['s1', 's2']]);
extendable.setExtension(proto.jspb.test.simple1, extension);
assertObjectEquals(extension,
extendable.getExtension(proto.jspb.test.simple1));
// From _lib mode.
extension = new proto.jspb.test.ExtensionMessage(['s1']);
extendable = new proto.jspb.test.TestExtensionsMessage([16]);
extendable.setExtension(proto.jspb.test.floatingMsgField, extension);
extendable.setExtension(proto.jspb.test.floatingStrField, 's2');
assertObjectEquals(extension,
extendable.getExtension(proto.jspb.test.floatingMsgField));
assertObjectEquals('s2',
extendable.getExtension(proto.jspb.test.floatingStrField));
assertNotUndefined(proto.jspb.exttest.floatingMsgField);
assertNotUndefined(proto.jspb.exttest.floatingMsgFieldTwo);
assertNotUndefined(proto.jspb.exttest.beta.floatingStrField);
});
it('testToObject_extendedObject', function() {
var extension1 = new proto.jspb.test.IsExtension(['ext1field']);
var extension2 = new proto.jspb.test.Simple1(['str', ['s1', 's2'], true]);
var extendable = new proto.jspb.test.HasExtensions(['v1', 'v2', 'v3']);
extendable.setExtension(proto.jspb.test.IsExtension.extField, extension1);
extendable.setExtension(proto.jspb.test.IndirectExtension.simple,
extension2);
extendable.setExtension(proto.jspb.test.IndirectExtension.str, 'xyzzy');
extendable.setExtension(proto.jspb.test.IndirectExtension.repeatedStrList,
['a', 'b']);
var s1 = new proto.jspb.test.Simple1(['foo', ['s1', 's2'], true]);
var s2 = new proto.jspb.test.Simple1(['bar', ['t1', 't2'], false]);
extendable.setExtension(
proto.jspb.test.IndirectExtension.repeatedSimpleList,
[s1, s2]);
assertObjectEquals({
str1: 'v1', str2: 'v2', str3: 'v3',
extField: { ext1: 'ext1field' },
simple: {
aString: 'str', aRepeatedStringList: ['s1', 's2'], aBoolean: true
},
str: 'xyzzy',
repeatedStrList: ['a', 'b'],
repeatedSimpleList: [
{ aString: 'foo', aRepeatedStringList: ['s1', 's2'], aBoolean: true},
{ aString: 'bar', aRepeatedStringList: ['t1', 't2'], aBoolean: false}
]
}, extendable.toObject());
// Now, with instances included.
assertObjectEquals({
str1: 'v1', str2: 'v2', str3: 'v3',
extField: {
ext1: 'ext1field',
$jspbMessageInstance:
extendable.getExtension(proto.jspb.test.IsExtension.extField)
},
simple: {
aString: 'str',
aRepeatedStringList: ['s1', 's2'],
aBoolean: true,
$jspbMessageInstance:
extendable.getExtension(proto.jspb.test.IndirectExtension.simple)
},
str: 'xyzzy',
repeatedStrList: ['a', 'b'],
repeatedSimpleList: [{
aString: 'foo',
aRepeatedStringList: ['s1', 's2'],
aBoolean: true,
$jspbMessageInstance: s1
}, {
aString: 'bar',
aRepeatedStringList: ['t1', 't2'],
aBoolean: false,
$jspbMessageInstance: s2
}],
$jspbMessageInstance: extendable
}, extendable.toObject(true /* opt_includeInstance */));
});
it('testInitialization_emptyArray', function() {
var msg = new proto.jspb.test.HasExtensions([]);
if (jspb.Message.MINIMIZE_MEMORY_ALLOCATIONS) {
assertArrayEquals([], msg.toArray());
} else {
// Extension object is created past all regular fields.
assertArrayEquals([,,, {}], msg.toArray());
}
});
it('testInitialization_justExtensionObject', function() {
var msg = new proto.jspb.test.Empty([{1: 'hi'}]);
// The extensionObject is not moved from its original location.
assertArrayEquals([{1: 'hi'}], msg.toArray());
});
it('testInitialization_incompleteList', function() {
var msg = new proto.jspb.test.Empty([1, {4: 'hi'}]);
// The extensionObject is not moved from its original location.
assertArrayEquals([1, {4: 'hi'}], msg.toArray());
});
it('testInitialization_forwardCompatible', function() {
var msg = new proto.jspb.test.Empty([1, 2, 3, {1: 'hi'}]);
assertArrayEquals([1, 2, 3, {1: 'hi'}], msg.toArray());
});
it('testExtendedMessageEnsureObject', function() {
var data = new proto.jspb.test.HasExtensions(['str1',
{'a_key': 'an_object'}]);
assertEquals('an_object', data.extensionObject_['a_key']);
});
it('testToObject_hasExtensionField', function() {
var data = new proto.jspb.test.HasExtensions(['str1', {100: ['ext1']}]);
var obj = data.toObject();
assertEquals('str1', obj.str1);
assertEquals('ext1', obj.extField.ext1);
});
it('testGetExtension', function() {
var data = new proto.jspb.test.HasExtensions(['str1', {100: ['ext1']}]);
assertEquals('str1', data.getStr1());
var extension = data.getExtension(proto.jspb.test.IsExtension.extField);
assertNotNull(extension);
assertEquals('ext1', extension.getExt1());
});
it('testSetExtension', function() {
var data = new proto.jspb.test.HasExtensions();
var extensionMessage = new proto.jspb.test.IsExtension(['is_extension']);
data.setExtension(proto.jspb.test.IsExtension.extField, extensionMessage);
var obj = data.toObject();
assertNotNull(
data.getExtension(proto.jspb.test.IsExtension.extField));
assertEquals('is_extension', obj.extField.ext1);
});
/**
* Note that group is long deprecated, we only support it because JsPb has
* a goal of being able to generate JS classes for all proto descriptors.
*/
it('testGroups', function() {
var group = new proto.jspb.test.TestGroup();
var someGroup = new proto.jspb.test.TestGroup.RepeatedGroup();
someGroup.setId('g1');
someGroup.setSomeBoolList([true, false]);
group.setRepeatedGroupList([someGroup]);
var groups = group.getRepeatedGroupList();
assertEquals('g1', groups[0].getId());
assertObjectEquals([true, false], groups[0].getSomeBoolList());
assertObjectEquals({id: 'g1', someBoolList: [true, false]},
groups[0].toObject());
assertObjectEquals({
repeatedGroupList: [{id: 'g1', someBoolList: [true, false]}],
requiredGroup: {id: undefined},
optionalGroup: undefined,
requiredSimple: {aRepeatedStringList: [], aString: undefined},
optionalSimple: undefined,
id: undefined
}, group.toObject());
var group1 = new proto.jspb.test.TestGroup1();
group1.setGroup(someGroup);
assertEquals(someGroup, group1.getGroup());
});
it('testNonExtensionFieldsAfterExtensionRange', function() {
var data = [{'1': 'a_string'}];
var message = new proto.jspb.test.Complex(data);
assertArrayEquals([], message.getARepeatedStringList());
});
it('testReservedGetterNames', function() {
var message = new proto.jspb.test.TestReservedNames();
message.setExtension$(11);
message.setExtension(proto.jspb.test.TestReservedNamesExtension.foo, 12);
assertEquals(11, message.getExtension$());
assertEquals(12, message.getExtension(
proto.jspb.test.TestReservedNamesExtension.foo));
assertObjectEquals({extension: 11, foo: 12}, message.toObject());
});
it('testInitializeMessageWithUnsetOneof', function() {
var message = new proto.jspb.test.TestMessageWithOneof([]);
assertEquals(
proto.jspb.test.TestMessageWithOneof.PartialOneofCase.
PARTIAL_ONEOF_NOT_SET,
message.getPartialOneofCase());
assertEquals(
proto.jspb.test.TestMessageWithOneof.RecursiveOneofCase.
RECURSIVE_ONEOF_NOT_SET,
message.getRecursiveOneofCase());
});
it('testInitializeMessageWithSingleValueSetInOneof', function() {
var message = new proto.jspb.test.TestMessageWithOneof([,, 'x']);
assertEquals('x', message.getPone());
assertEquals('', message.getPthree());
assertEquals(
proto.jspb.test.TestMessageWithOneof.PartialOneofCase.PONE,
message.getPartialOneofCase());
});
it('testKeepsLastWireValueSetInUnion_multipleValues', function() {
var message = new proto.jspb.test.TestMessageWithOneof([,, 'x',, 'y']);
assertEquals('', message.getPone());
assertEquals('y', message.getPthree());
assertEquals(
proto.jspb.test.TestMessageWithOneof.PartialOneofCase.PTHREE,
message.getPartialOneofCase());
});
it('testSettingOneofFieldClearsOthers', function() {
var message = new proto.jspb.test.TestMessageWithOneof;
assertEquals('', message.getPone());
assertEquals('', message.getPthree());
assertFalse(message.hasPone());
assertFalse(message.hasPthree());
message.setPone('hi');
assertEquals('hi', message.getPone());
assertEquals('', message.getPthree());
assertTrue(message.hasPone());
assertFalse(message.hasPthree());
message.setPthree('bye');
assertEquals('', message.getPone());
assertEquals('bye', message.getPthree());
assertFalse(message.hasPone());
assertTrue(message.hasPthree());
});
it('testSettingOneofFieldDoesNotClearFieldsFromOtherUnions', function() {
var other = new proto.jspb.test.TestMessageWithOneof;
var message = new proto.jspb.test.TestMessageWithOneof;
assertEquals('', message.getPone());
assertEquals('', message.getPthree());
assertUndefined(message.getRone());
assertFalse(message.hasPone());
assertFalse(message.hasPthree());
message.setPone('hi');
message.setRone(other);
assertEquals('hi', message.getPone());
assertEquals('', message.getPthree());
assertEquals(other, message.getRone());
assertTrue(message.hasPone());
assertFalse(message.hasPthree());
message.setPthree('bye');
assertEquals('', message.getPone());
assertEquals('bye', message.getPthree());
assertEquals(other, message.getRone());
assertFalse(message.hasPone());
assertTrue(message.hasPthree());
});
it('testUnsetsOneofCaseWhenFieldIsCleared', function() {
var message = new proto.jspb.test.TestMessageWithOneof;
assertEquals(
proto.jspb.test.TestMessageWithOneof.PartialOneofCase.
PARTIAL_ONEOF_NOT_SET,
message.getPartialOneofCase());
message.setPone('hi');
assertEquals(
proto.jspb.test.TestMessageWithOneof.PartialOneofCase.PONE,
message.getPartialOneofCase());
message.clearPone();
assertEquals(
proto.jspb.test.TestMessageWithOneof.PartialOneofCase.
PARTIAL_ONEOF_NOT_SET,
message.getPartialOneofCase());
});
it('testMessageWithDefaultOneofValues', function() {
var message = new proto.jspb.test.TestMessageWithOneof;
assertEquals(1234, message.getAone());
assertEquals(0, message.getAtwo());
assertEquals(
proto.jspb.test.TestMessageWithOneof.DefaultOneofACase
.DEFAULT_ONEOF_A_NOT_SET,
message.getDefaultOneofACase());
message.setAone(567);
assertEquals(567, message.getAone());
assertEquals(0, message.getAtwo());
assertEquals(
proto.jspb.test.TestMessageWithOneof.DefaultOneofACase.AONE,
message.getDefaultOneofACase());
message.setAtwo(890);
assertEquals(1234, message.getAone());
assertEquals(890, message.getAtwo());
assertEquals(
proto.jspb.test.TestMessageWithOneof.DefaultOneofACase.ATWO,
message.getDefaultOneofACase());
message.clearAtwo();
assertEquals(1234, message.getAone());
assertEquals(0, message.getAtwo());
assertEquals(
proto.jspb.test.TestMessageWithOneof.DefaultOneofACase
.DEFAULT_ONEOF_A_NOT_SET,
message.getDefaultOneofACase());
});
it('testMessageWithDefaultOneofValues_defaultNotOnFirstField', function() {
var message = new proto.jspb.test.TestMessageWithOneof;
assertEquals(0, message.getBone());
assertEquals(1234, message.getBtwo());
assertFalse(message.hasBone());
assertFalse(message.hasBtwo());
assertEquals(
proto.jspb.test.TestMessageWithOneof.DefaultOneofBCase
.DEFAULT_ONEOF_B_NOT_SET,
message.getDefaultOneofBCase());
message.setBone(2);
assertEquals(2, message.getBone());
assertEquals(1234, message.getBtwo());
assertTrue(message.hasBone());
assertFalse(message.hasBtwo());
assertEquals(
proto.jspb.test.TestMessageWithOneof.DefaultOneofBCase.BONE,
message.getDefaultOneofBCase());
message.setBtwo(3);
assertEquals(0, message.getBone());
assertFalse(message.hasBone());
assertTrue(message.hasBtwo());
assertEquals(3, message.getBtwo());
assertEquals(
proto.jspb.test.TestMessageWithOneof.DefaultOneofBCase.BTWO,
message.getDefaultOneofBCase());
message.clearBtwo();
assertEquals(0, message.getBone());
assertFalse(message.hasBone());
assertFalse(message.hasBtwo());
assertEquals(1234, message.getBtwo());
assertEquals(
proto.jspb.test.TestMessageWithOneof.DefaultOneofBCase
.DEFAULT_ONEOF_B_NOT_SET,
message.getDefaultOneofBCase());
});
it('testInitializeMessageWithOneofDefaults', function() {
var message =
new proto.jspb.test.TestMessageWithOneof(new Array(9).concat(567));
assertEquals(567, message.getAone());
assertEquals(0, message.getAtwo());
assertEquals(
proto.jspb.test.TestMessageWithOneof.DefaultOneofACase.AONE,
message.getDefaultOneofACase());
message =
new proto.jspb.test.TestMessageWithOneof(new Array(10).concat(890));
assertEquals(1234, message.getAone());
assertEquals(890, message.getAtwo());
assertEquals(
proto.jspb.test.TestMessageWithOneof.DefaultOneofACase.ATWO,
message.getDefaultOneofACase());
message =
new proto.jspb.test.TestMessageWithOneof(new Array(9).concat(567, 890));
assertEquals(1234, message.getAone());
assertEquals(890, message.getAtwo());
assertEquals(
proto.jspb.test.TestMessageWithOneof.DefaultOneofACase.ATWO,
message.getDefaultOneofACase());
});
it('testInitializeMessageWithOneofDefaults_defaultNotSetOnFirstField',
function() {
var message;
message =
new proto.jspb.test.TestMessageWithOneof(new Array(11).concat(567));
assertEquals(567, message.getBone());
assertEquals(1234, message.getBtwo());
assertEquals(
proto.jspb.test.TestMessageWithOneof.DefaultOneofBCase.BONE,
message.getDefaultOneofBCase());
message =
new proto.jspb.test.TestMessageWithOneof(new Array(12).concat(890));
assertEquals(0, message.getBone());
assertEquals(890, message.getBtwo());
assertEquals(
proto.jspb.test.TestMessageWithOneof.DefaultOneofBCase.BTWO,
message.getDefaultOneofBCase());
message = new proto.jspb.test.TestMessageWithOneof(
new Array(11).concat(567, 890));
assertEquals(0, message.getBone());
assertEquals(890, message.getBtwo());
assertEquals(
proto.jspb.test.TestMessageWithOneof.DefaultOneofBCase.BTWO,
message.getDefaultOneofBCase());
});
it('testOneofContainingAnotherMessage', function() {
var message = new proto.jspb.test.TestMessageWithOneof;
assertEquals(
proto.jspb.test.TestMessageWithOneof.RecursiveOneofCase.
RECURSIVE_ONEOF_NOT_SET,
message.getRecursiveOneofCase());
var other = new proto.jspb.test.TestMessageWithOneof;
message.setRone(other);
assertEquals(other, message.getRone());
assertEquals('', message.getRtwo());
assertEquals(
proto.jspb.test.TestMessageWithOneof.RecursiveOneofCase.RONE,
message.getRecursiveOneofCase());
message.setRtwo('hi');
assertUndefined(message.getRone());
assertEquals('hi', message.getRtwo());
assertEquals(
proto.jspb.test.TestMessageWithOneof.RecursiveOneofCase.RTWO,
message.getRecursiveOneofCase());
});
it('testQueryingOneofCaseEnsuresOnlyOneFieldIsSetInUnderlyingArray',
function() {
var message = new proto.jspb.test.TestMessageWithOneof;
message.setPone('x');
assertEquals('x', message.getPone());
assertEquals('', message.getPthree());
assertEquals(
proto.jspb.test.TestMessageWithOneof.PartialOneofCase.PONE,
message.getPartialOneofCase());
var array = message.toArray();
assertEquals('x', array[2]);
assertUndefined(array[4]);
array[4] = 'y';
assertEquals(
proto.jspb.test.TestMessageWithOneof.PartialOneofCase.PTHREE,
message.getPartialOneofCase());
assertUndefined(array[2]);
assertEquals('y', array[4]);
});
it('testFloatingPointFieldsSupportNan', function() {
var assertNan = function(x) {
assertTrue('Expected ' + x + ' (' + goog.typeOf(x) + ') to be NaN.',
goog.isNumber(x) && isNaN(x));
};
var message = new proto.jspb.test.FloatingPointFields([
'NaN', 'NaN', ['NaN', 'NaN'], 'NaN',
'NaN', 'NaN', ['NaN', 'NaN'], 'NaN'
]);
assertNan(message.getOptionalFloatField());
assertNan(message.getRequiredFloatField());
assertNan(message.getRepeatedFloatFieldList()[0]);
assertNan(message.getRepeatedFloatFieldList()[1]);
assertNan(message.getDefaultFloatField());
assertNan(message.getOptionalDoubleField());
assertNan(message.getRequiredDoubleField());
assertNan(message.getRepeatedDoubleFieldList()[0]);
assertNan(message.getRepeatedDoubleFieldList()[1]);
assertNan(message.getDefaultDoubleField());
});
});
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
goog.require('goog.crypt.base64');
goog.require('goog.testing.asserts');
// CommonJS-LoadFromFile: testbinary_pb proto.jspb.test
goog.require('proto.jspb.test.ForeignMessage');
// CommonJS-LoadFromFile: proto3_test_pb proto.jspb.test
goog.require('proto.jspb.test.Proto3Enum');
goog.require('proto.jspb.test.TestProto3');
var BYTES = new Uint8Array([1, 2, 8, 9]);
var BYTES_B64 = goog.crypt.base64.encodeByteArray(BYTES);
/**
* Helper: compare a bytes field to an expected value
* @param {Uint8Array|string} arr
* @param {Uint8Array} expected
* @return {boolean}
*/
function bytesCompare(arr, expected) {
if (goog.isString(arr)) {
arr = goog.crypt.base64.decodeStringToUint8Array(arr);
}
if (arr.length != expected.length) {
return false;
}
for (var i = 0; i < arr.length; i++) {
if (arr[i] != expected[i]) {
return false;
}
}
return true;
}
describe('proto3Test', function() {
/**
* Test defaults for proto3 message fields.
*/
it('testProto3FieldDefaults', function() {
var msg = new proto.jspb.test.TestProto3();
assertEquals(msg.getOptionalInt32(), 0);
assertEquals(msg.getOptionalInt64(), 0);
assertEquals(msg.getOptionalUint32(), 0);
assertEquals(msg.getOptionalUint64(), 0);
assertEquals(msg.getOptionalSint32(), 0);
assertEquals(msg.getOptionalSint64(), 0);
assertEquals(msg.getOptionalFixed32(), 0);
assertEquals(msg.getOptionalFixed64(), 0);
assertEquals(msg.getOptionalSfixed32(), 0);
assertEquals(msg.getOptionalSfixed64(), 0);
assertEquals(msg.getOptionalFloat(), 0);
assertEquals(msg.getOptionalDouble(), 0);
assertEquals(msg.getOptionalString(), '');
// TODO(b/26173701): when we change bytes fields default getter to return
// Uint8Array, we'll want to switch this assertion to match the u8 case.
assertEquals(typeof msg.getOptionalBytes(), 'string');
assertEquals(msg.getOptionalBytes_asU8() instanceof Uint8Array, true);
assertEquals(typeof msg.getOptionalBytes_asB64(), 'string');
assertEquals(msg.getOptionalBytes().length, 0);
assertEquals(msg.getOptionalBytes_asU8().length, 0);
assertEquals(msg.getOptionalBytes_asB64(), '');
assertEquals(msg.getOptionalForeignEnum(),
proto.jspb.test.Proto3Enum.PROTO3_FOO);
assertEquals(msg.getOptionalForeignMessage(), undefined);
assertEquals(msg.getOptionalForeignMessage(), undefined);
assertEquals(msg.getRepeatedInt32List().length, 0);
assertEquals(msg.getRepeatedInt64List().length, 0);
assertEquals(msg.getRepeatedUint32List().length, 0);
assertEquals(msg.getRepeatedUint64List().length, 0);
assertEquals(msg.getRepeatedSint32List().length, 0);
assertEquals(msg.getRepeatedSint64List().length, 0);
assertEquals(msg.getRepeatedFixed32List().length, 0);
assertEquals(msg.getRepeatedFixed64List().length, 0);
assertEquals(msg.getRepeatedSfixed32List().length, 0);
assertEquals(msg.getRepeatedSfixed64List().length, 0);
assertEquals(msg.getRepeatedFloatList().length, 0);
assertEquals(msg.getRepeatedDoubleList().length, 0);
assertEquals(msg.getRepeatedStringList().length, 0);
assertEquals(msg.getRepeatedBytesList().length, 0);
assertEquals(msg.getRepeatedForeignEnumList().length, 0);
assertEquals(msg.getRepeatedForeignMessageList().length, 0);
});
/**
* Test that all fields can be set and read via a serialization roundtrip.
*/
it('testProto3FieldSetGet', function() {
var msg = new proto.jspb.test.TestProto3();
msg.setOptionalInt32(-42);
msg.setOptionalInt64(-0x7fffffff00000000);
msg.setOptionalUint32(0x80000000);
msg.setOptionalUint64(0xf000000000000000);
msg.setOptionalSint32(-100);
msg.setOptionalSint64(-0x8000000000000000);
msg.setOptionalFixed32(1234);
msg.setOptionalFixed64(0x1234567800000000);
msg.setOptionalSfixed32(-1234);
msg.setOptionalSfixed64(-0x1234567800000000);
msg.setOptionalFloat(1.5);
msg.setOptionalDouble(-1.5);
msg.setOptionalBool(true);
msg.setOptionalString('hello world');
msg.setOptionalBytes(BYTES);
var submsg = new proto.jspb.test.ForeignMessage();
submsg.setC(16);
msg.setOptionalForeignMessage(submsg);
msg.setOptionalForeignEnum(proto.jspb.test.Proto3Enum.PROTO3_BAR);
msg.setRepeatedInt32List([-42]);
msg.setRepeatedInt64List([-0x7fffffff00000000]);
msg.setRepeatedUint32List([0x80000000]);
msg.setRepeatedUint64List([0xf000000000000000]);
msg.setRepeatedSint32List([-100]);
msg.setRepeatedSint64List([-0x8000000000000000]);
msg.setRepeatedFixed32List([1234]);
msg.setRepeatedFixed64List([0x1234567800000000]);
msg.setRepeatedSfixed32List([-1234]);
msg.setRepeatedSfixed64List([-0x1234567800000000]);
msg.setRepeatedFloatList([1.5]);
msg.setRepeatedDoubleList([-1.5]);
msg.setRepeatedBoolList([true]);
msg.setRepeatedStringList(['hello world']);
msg.setRepeatedBytesList([BYTES]);
submsg = new proto.jspb.test.ForeignMessage();
submsg.setC(1000);
msg.setRepeatedForeignMessageList([submsg]);
msg.setRepeatedForeignEnumList([proto.jspb.test.Proto3Enum.PROTO3_BAR]);
msg.setOneofString('asdf');
var serialized = msg.serializeBinary();
msg = proto.jspb.test.TestProto3.deserializeBinary(serialized);
assertEquals(msg.getOptionalInt32(), -42);
assertEquals(msg.getOptionalInt64(), -0x7fffffff00000000);
assertEquals(msg.getOptionalUint32(), 0x80000000);
assertEquals(msg.getOptionalUint64(), 0xf000000000000000);
assertEquals(msg.getOptionalSint32(), -100);
assertEquals(msg.getOptionalSint64(), -0x8000000000000000);
assertEquals(msg.getOptionalFixed32(), 1234);
assertEquals(msg.getOptionalFixed64(), 0x1234567800000000);
assertEquals(msg.getOptionalSfixed32(), -1234);
assertEquals(msg.getOptionalSfixed64(), -0x1234567800000000);
assertEquals(msg.getOptionalFloat(), 1.5);
assertEquals(msg.getOptionalDouble(), -1.5);
assertEquals(msg.getOptionalBool(), true);
assertEquals(msg.getOptionalString(), 'hello world');
assertEquals(true, bytesCompare(msg.getOptionalBytes(), BYTES));
assertEquals(msg.getOptionalForeignMessage().getC(), 16);
assertEquals(msg.getOptionalForeignEnum(),
proto.jspb.test.Proto3Enum.PROTO3_BAR);
assertElementsEquals(msg.getRepeatedInt32List(), [-42]);
assertElementsEquals(msg.getRepeatedInt64List(), [-0x7fffffff00000000]);
assertElementsEquals(msg.getRepeatedUint32List(), [0x80000000]);
assertElementsEquals(msg.getRepeatedUint64List(), [0xf000000000000000]);
assertElementsEquals(msg.getRepeatedSint32List(), [-100]);
assertElementsEquals(msg.getRepeatedSint64List(), [-0x8000000000000000]);
assertElementsEquals(msg.getRepeatedFixed32List(), [1234]);
assertElementsEquals(msg.getRepeatedFixed64List(), [0x1234567800000000]);
assertElementsEquals(msg.getRepeatedSfixed32List(), [-1234]);
assertElementsEquals(msg.getRepeatedSfixed64List(), [-0x1234567800000000]);
assertElementsEquals(msg.getRepeatedFloatList(), [1.5]);
assertElementsEquals(msg.getRepeatedDoubleList(), [-1.5]);
assertElementsEquals(msg.getRepeatedBoolList(), [true]);
assertElementsEquals(msg.getRepeatedStringList(), ['hello world']);
assertEquals(msg.getRepeatedBytesList().length, 1);
assertEquals(true, bytesCompare(msg.getRepeatedBytesList()[0], BYTES));
assertEquals(msg.getRepeatedForeignMessageList().length, 1);
assertEquals(msg.getRepeatedForeignMessageList()[0].getC(), 1000);
assertElementsEquals(msg.getRepeatedForeignEnumList(),
[proto.jspb.test.Proto3Enum.PROTO3_BAR]);
assertEquals(msg.getOneofString(), 'asdf');
});
/**
* Test that oneofs continue to have a notion of field presence.
*/
it('testOneofs', function() {
var msg = new proto.jspb.test.TestProto3();
assertEquals(msg.getOneofUint32(), 0);
assertEquals(msg.getOneofForeignMessage(), undefined);
assertEquals(msg.getOneofString(), '');
assertEquals(msg.getOneofBytes(), '');
assertFalse(msg.hasOneofUint32());
assertFalse(msg.hasOneofString());
assertFalse(msg.hasOneofBytes());
msg.setOneofUint32(42);
assertEquals(msg.getOneofUint32(), 42);
assertEquals(msg.getOneofForeignMessage(), undefined);
assertEquals(msg.getOneofString(), '');
assertEquals(msg.getOneofBytes(), '');
assertTrue(msg.hasOneofUint32());
assertFalse(msg.hasOneofString());
assertFalse(msg.hasOneofBytes());
var submsg = new proto.jspb.test.ForeignMessage();
msg.setOneofForeignMessage(submsg);
assertEquals(msg.getOneofUint32(), 0);
assertEquals(msg.getOneofForeignMessage(), submsg);
assertEquals(msg.getOneofString(), '');
assertEquals(msg.getOneofBytes(), '');
assertFalse(msg.hasOneofUint32());
assertFalse(msg.hasOneofString());
assertFalse(msg.hasOneofBytes());
msg.setOneofString('hello');
assertEquals(msg.getOneofUint32(), 0);
assertEquals(msg.getOneofForeignMessage(), undefined);
assertEquals(msg.getOneofString(), 'hello');
assertEquals(msg.getOneofBytes(), '');
assertFalse(msg.hasOneofUint32());
assertTrue(msg.hasOneofString());
assertFalse(msg.hasOneofBytes());
msg.setOneofBytes(goog.crypt.base64.encodeString('\u00FF\u00FF'));
assertEquals(msg.getOneofUint32(), 0);
assertEquals(msg.getOneofForeignMessage(), undefined);
assertEquals(msg.getOneofString(), '');
assertEquals(msg.getOneofBytes_asB64(),
goog.crypt.base64.encodeString('\u00FF\u00FF'));
assertFalse(msg.hasOneofUint32());
assertFalse(msg.hasOneofString());
assertTrue(msg.hasOneofBytes());
});
/**
* Test that "default"-valued primitive fields are not emitted on the wire.
*/
it('testNoSerializeDefaults', function() {
var msg = new proto.jspb.test.TestProto3();
// Set each primitive to a non-default value, then back to its default, to
// ensure that the serialization is actually checking the value and not just
// whether it has ever been set.
msg.setOptionalInt32(42);
msg.setOptionalInt32(0);
msg.setOptionalDouble(3.14);
msg.setOptionalDouble(0.0);
msg.setOptionalBool(true);
msg.setOptionalBool(false);
msg.setOptionalString('hello world');
msg.setOptionalString('');
msg.setOptionalBytes(goog.crypt.base64.encodeString('\u00FF\u00FF'));
msg.setOptionalBytes('');
msg.setOptionalForeignMessage(new proto.jspb.test.ForeignMessage());
msg.setOptionalForeignMessage(null);
msg.setOptionalForeignEnum(proto.jspb.test.Proto3Enum.PROTO3_BAR);
msg.setOptionalForeignEnum(proto.jspb.test.Proto3Enum.PROTO3_FOO);
msg.setOneofUint32(32);
msg.setOneofUint32(null);
var serialized = msg.serializeBinary();
assertEquals(0, serialized.length);
});
/**
* Test that base64 string and Uint8Array are interchangeable in bytes fields.
*/
it('testBytesFieldsInterop', function() {
var msg = new proto.jspb.test.TestProto3();
// Set as a base64 string and check all the getters work.
msg.setOptionalBytes(BYTES_B64);
assertTrue(bytesCompare(msg.getOptionalBytes_asU8(), BYTES));
assertTrue(bytesCompare(msg.getOptionalBytes_asB64(), BYTES));
assertTrue(bytesCompare(msg.getOptionalBytes(), BYTES));
// Test binary serialize round trip doesn't break it.
msg = proto.jspb.test.TestProto3.deserializeBinary(msg.serializeBinary());
assertTrue(bytesCompare(msg.getOptionalBytes_asU8(), BYTES));
assertTrue(bytesCompare(msg.getOptionalBytes_asB64(), BYTES));
assertTrue(bytesCompare(msg.getOptionalBytes(), BYTES));
msg = new proto.jspb.test.TestProto3();
// Set as a Uint8Array and check all the getters work.
msg.setOptionalBytes(BYTES);
assertTrue(bytesCompare(msg.getOptionalBytes_asU8(), BYTES));
assertTrue(bytesCompare(msg.getOptionalBytes_asB64(), BYTES));
assertTrue(bytesCompare(msg.getOptionalBytes(), BYTES));
});
});
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
syntax = "proto3";
import "testbinary.proto";
package jspb.test;
message TestProto3 {
int32 optional_int32 = 1;
int64 optional_int64 = 2;
uint32 optional_uint32 = 3;
uint64 optional_uint64 = 4;
sint32 optional_sint32 = 5;
sint64 optional_sint64 = 6;
fixed32 optional_fixed32 = 7;
fixed64 optional_fixed64 = 8;
sfixed32 optional_sfixed32 = 9;
sfixed64 optional_sfixed64 = 10;
float optional_float = 11;
double optional_double = 12;
bool optional_bool = 13;
string optional_string = 14;
bytes optional_bytes = 15;
ForeignMessage optional_foreign_message = 19;
Proto3Enum optional_foreign_enum = 22;
repeated int32 repeated_int32 = 31;
repeated int64 repeated_int64 = 32;
repeated uint32 repeated_uint32 = 33;
repeated uint64 repeated_uint64 = 34;
repeated sint32 repeated_sint32 = 35;
repeated sint64 repeated_sint64 = 36;
repeated fixed32 repeated_fixed32 = 37;
repeated fixed64 repeated_fixed64 = 38;
repeated sfixed32 repeated_sfixed32 = 39;
repeated sfixed64 repeated_sfixed64 = 40;
repeated float repeated_float = 41;
repeated double repeated_double = 42;
repeated bool repeated_bool = 43;
repeated string repeated_string = 44;
repeated bytes repeated_bytes = 45;
repeated ForeignMessage repeated_foreign_message = 49;
repeated Proto3Enum repeated_foreign_enum = 52;
oneof oneof_field {
uint32 oneof_uint32 = 111;
ForeignMessage oneof_foreign_message = 112;
string oneof_string = 113;
bytes oneof_bytes = 114;
}
}
enum Proto3Enum {
PROTO3_FOO = 0;
PROTO3_BAR = 1;
PROTO3_BAZ = 2;
}
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: mwr@google.com (Mark Rawling)
syntax = "proto2";
option java_package = "com.google.apps.jspb.proto";
option java_multiple_files = true;
import "google/protobuf/descriptor.proto";
package jspb.test;
message Empty {
}
enum OuterEnum {
FOO = 1;
BAR = 2;
}
message EnumContainer {
optional OuterEnum outer_enum = 1;
}
message Simple1 {
required string a_string = 1;
repeated string a_repeated_string = 2;
optional bool a_boolean = 3;
}
// A message that differs from Simple1 only by name
message Simple2 {
required string a_string = 1;
repeated string a_repeated_string = 2;
}
message SpecialCases {
required string normal = 1;
// Examples of Js reserved names that are converted to pb_<name>.
required string default = 2;
required string function = 3;
required string var = 4;
}
message OptionalFields {
message Nested {
optional int32 an_int = 1;
}
optional string a_string = 1;
required bool a_bool = 2;
optional Nested a_nested_message = 3;
repeated Nested a_repeated_message = 4;
repeated string a_repeated_string = 5;
}
message HasExtensions {
optional string str1 = 1;
optional string str2 = 2;
optional string str3 = 3;
extensions 10 to max;
}
message Complex {
message Nested {
required int32 an_int = 2;
}
required string a_string = 1;
required bool an_out_of_order_bool = 9;
optional Nested a_nested_message = 4;
repeated Nested a_repeated_message = 5;
repeated string a_repeated_string = 7;
}
message OuterMessage {
// Make sure this doesn't conflict with the other Complex message.
message Complex {
optional int32 inner_complex_field = 1;
}
}
message IsExtension {
extend HasExtensions {
optional IsExtension ext_field = 100;
}
optional string ext1 = 1;
// Extensions of proto2 Descriptor messages will be ignored.
extend google.protobuf.EnumOptions {
optional string simple_option = 42113038;
}
}
message IndirectExtension {
extend HasExtensions {
optional Simple1 simple = 101;
optional string str = 102;
repeated string repeated_str = 103;
repeated Simple1 repeated_simple = 104;
}
}
extend HasExtensions {
optional Simple1 simple1 = 105;
}
message DefaultValues {
enum Enum {
E1 = 13;
E2 = 77;
}
optional string string_field = 1 [default="default<>\'\"abc"];
optional bool bool_field = 2 [default=true];
optional int64 int_field = 3 [default=11];
optional Enum enum_field = 4 [default=E1];
optional string empty_field = 6 [default=""];
optional bytes bytes_field = 8 [default="moo"]; // Base64 encoding is "bW9v"
}
message FloatingPointFields {
optional float optional_float_field = 1;
required float required_float_field = 2;
repeated float repeated_float_field = 3;
optional float default_float_field = 4 [default = 2.0];
optional double optional_double_field = 5;
required double required_double_field = 6;
repeated double repeated_double_field = 7;
optional double default_double_field = 8 [default = 2.0];
}
message TestClone {
optional string str = 1;
optional Simple1 simple1 = 3;
repeated Simple1 simple2 = 5;
optional bytes bytes_field = 6;
optional string unused = 7;
extensions 10 to max;
}
message CloneExtension {
extend TestClone {
optional CloneExtension ext_field = 100;
}
optional string ext = 2;
}
message TestGroup {
repeated group RepeatedGroup = 1 {
required string id = 1;
repeated bool some_bool = 2;
}
required group RequiredGroup = 2 {
required string id = 1;
}
optional group OptionalGroup = 3 {
required string id = 1;
}
optional string id = 4;
required Simple2 required_simple = 5;
optional Simple2 optional_simple = 6;
}
message TestGroup1 {
optional TestGroup.RepeatedGroup group = 1;
}
message TestReservedNames {
optional int32 extension = 1;
extensions 10 to max;
}
message TestReservedNamesExtension {
extend TestReservedNames {
optional int32 foo = 10;
}
}
message TestMessageWithOneof {
oneof partial_oneof {
string pone = 3;
string pthree = 5;
}
oneof recursive_oneof {
TestMessageWithOneof rone = 6;
string rtwo = 7;
}
optional bool normal_field = 8;
repeated string repeated_field = 9;
oneof default_oneof_a {
int32 aone = 10 [default = 1234];
int32 atwo = 11;
}
oneof default_oneof_b {
int32 bone = 12;
int32 btwo = 13 [default = 1234];
}
}
message TestEndsWithBytes {
optional int32 value = 1;
optional bytes data = 2;
}
#!/bin/bash
set -e
# Download protoc 3.0.0 from Maven if it is not already present.
OLD_PROTOC_URL=https://repo1.maven.org/maven2/com/google/protobuf/protoc/3.0.0/protoc-3.0.0-linux-x86_64.exe
if [ ! -f protoc ]; then
wget $OLD_PROTOC_URL -O protoc
chmod +x protoc
fi
pushd ../..
npm install && npm test
popd
old_protoc=./protoc
new_protoc=../../../src/protoc
# The protos in group 2 have some dependencies on protos in group 1. The tests
# will verify that the generated code for one group can be regenerated
# independently of the other group in a compatible way.
#
# Note: these lists of protos duplicate the lists in gulpfile.js. Ideally we
# should find a good way of having a single source of truth for this.
group1_protos="data.proto test3.proto test5.proto commonjs/test6/test6.proto testbinary.proto testempty.proto test.proto"
group2_protos="proto3_test.proto test2.proto test4.proto commonjs/test7/test7.proto"
# We test the following cases:
#
# Case 1: build groups 1 and 2 with the old protoc
# Case 2: build group 1 with new protoc but group 2 with old protoc
# Case 3: build group 1 with old protoc but group 2 with new protoc
#
# In each case, we use the current runtime.
#
# CommonJS tests
#
mkdir -p commonjs_out{1,2,3}
# Case 1
$old_protoc --js_out=import_style=commonjs,binary:commonjs_out1 -I ../../../src -I commonjs -I . $group1_protos
$old_protoc --js_out=import_style=commonjs,binary:commonjs_out1 -I ../../../src -I commonjs -I . $group2_protos
# Case 2
$new_protoc --js_out=import_style=commonjs,binary:commonjs_out2 -I ../../../src -I commonjs -I . $group1_protos
$old_protoc --js_out=import_style=commonjs,binary:commonjs_out2 -I ../../../src -I commonjs -I . $group2_protos
# Case 3
$old_protoc --js_out=import_style=commonjs,binary:commonjs_out3 -I ../../../src -I commonjs -I . $group1_protos
$new_protoc --js_out=import_style=commonjs,binary:commonjs_out3 -I ../../../src -I commonjs -I . $group2_protos
mkdir -p commonjs_out/binary
for file in *_test.js binary/*_test.js; do
node commonjs/rewrite_tests_for_commonjs.js < "$file" > "commonjs_out/$file"
done
cp commonjs/{jasmine.json,import_test.js} commonjs_out/
mkdir -p commonjs_out/test_node_modules
../../node_modules/google-closure-library/closure/bin/calcdeps.py -i commonjs/export_asserts.js -p . -p ../../node_modules/google-closure-library/closure -o compiled --compiler_jar ../../node_modules/google-closure-compiler/compiler.jar > commonjs_out/test_node_modules/closure_asserts_commonjs.js
../../node_modules/google-closure-library/closure/bin/calcdeps.py -i commonjs/export_testdeps.js -p ../.. -p ../../node_modules/google-closure-library/closure -o compiled --compiler_jar ../../node_modules/google-closure-compiler/compiler.jar > commonjs_out/test_node_modules/testdeps_commonjs.js
cp ../../google-protobuf.js commonjs_out/test_node_modules
cp -r ../../commonjs_out/node_modules commonjs_out
echo
echo "Running tests with CommonJS imports"
echo "-----------------------------------"
for i in 1 2 3; do
cp -r commonjs_out/* "commonjs_out$i"
pushd "commonjs_out$i"
JASMINE_CONFIG_PATH=jasmine.json NODE_PATH=test_node_modules ../../../node_modules/.bin/jasmine
popd
done
#
# Closure tests
#
$old_protoc --js_out=library=testproto_libs1,binary:. -I ../../../src -I commonjs -I . $group1_protos
$old_protoc --js_out=library=testproto_libs2,binary:. -I ../../../src -I commonjs -I . $group2_protos
$new_protoc --js_out=library=testproto_libs1_new,binary:. -I ../../../src -I commonjs -I . $group1_protos
$new_protoc --js_out=library=testproto_libs2_new,binary:. -I ../../../src -I commonjs -I . $group2_protos
echo
echo "Running tests with Closure-style imports"
echo "----------------------------------------"
# Case 1
JASMINE_CONFIG_PATH=jasmine1.json ../../node_modules/.bin/jasmine
# Case 2
JASMINE_CONFIG_PATH=jasmine2.json ../../node_modules/.bin/jasmine
# Case 3
JASMINE_CONFIG_PATH=jasmine3.json ../../node_modules/.bin/jasmine
# Remove these files so that calcdeps.py does not get confused by them the next
# time this script runs.
rm testproto_libs[12]*
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
syntax = "proto2";
option java_package = "com.google.apps.jspb.proto";
option java_multiple_files = true;
package jspb.test;
message TestExtensionsMessage {
optional int32 intfield = 1;
extensions 100 to max;
}
message ExtensionMessage {
extend TestExtensionsMessage {
optional ExtensionMessage ext_field = 100;
}
optional string ext1 = 1;
}
// Floating extensions are only supported when generating a _lib.js library.
extend TestExtensionsMessage {
optional ExtensionMessage floating_msg_field = 101;
optional string floating_str_field = 102;
}
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
syntax = "proto2";
option java_package = "com.google.apps.jspb.proto";
option java_multiple_files = true;
package jspb.exttest;
message TestExtensionsMessage {
optional int32 intfield = 1;
extensions 100 to max;
}
message ExtensionMessage {
extend TestExtensionsMessage {
optional ExtensionMessage ext_field = 100;
}
optional string ext1 = 1;
}
extend TestExtensionsMessage {
optional ExtensionMessage floating_msg_field = 101;
optional string floating_str_field = 102;
}
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
syntax = "proto2";
option java_package = "com.google.apps.jspb.proto";
option java_multiple_files = true;
package jspb.exttest;
import "test3.proto";
extend TestExtensionsMessage {
optional ExtensionMessage floating_msg_field_two = 103;
}
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
syntax = "proto2";
option java_package = "com.google.apps.jspb.proto";
option java_multiple_files = true;
package jspb.exttest.beta;
message TestBetaExtensionsMessage {
extensions 100 to max;
}
extend TestBetaExtensionsMessage {
optional string floating_str_field = 101;
}
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// LINT: ALLOW_GROUPS
syntax = "proto2";
package jspb.test;
// These types are borrowed from `unittest.proto` in the protobuf tree. We want
// to ensure that the binary-format support will handle all field types
// properly.
message TestAllTypes {
optional int32 optional_int32 = 1;
optional int64 optional_int64 = 2;
optional uint32 optional_uint32 = 3;
optional uint64 optional_uint64 = 4;
optional sint32 optional_sint32 = 5;
optional sint64 optional_sint64 = 6;
optional fixed32 optional_fixed32 = 7;
optional fixed64 optional_fixed64 = 8;
optional sfixed32 optional_sfixed32 = 9;
optional sfixed64 optional_sfixed64 = 10;
optional float optional_float = 11;
optional double optional_double = 12;
optional bool optional_bool = 13;
optional string optional_string = 14;
optional bytes optional_bytes = 15;
optional group OptionalGroup = 16 {
optional int32 a = 17;
}
optional ForeignMessage optional_foreign_message = 19;
optional ForeignEnum optional_foreign_enum = 22;
// Repeated
repeated int32 repeated_int32 = 31;
repeated int64 repeated_int64 = 32;
repeated uint32 repeated_uint32 = 33;
repeated uint64 repeated_uint64 = 34;
repeated sint32 repeated_sint32 = 35;
repeated sint64 repeated_sint64 = 36;
repeated fixed32 repeated_fixed32 = 37;
repeated fixed64 repeated_fixed64 = 38;
repeated sfixed32 repeated_sfixed32 = 39;
repeated sfixed64 repeated_sfixed64 = 40;
repeated float repeated_float = 41;
repeated double repeated_double = 42;
repeated bool repeated_bool = 43;
repeated string repeated_string = 44;
repeated bytes repeated_bytes = 45;
repeated group RepeatedGroup = 46 {
optional int32 a = 47;
}
repeated ForeignMessage repeated_foreign_message = 49;
repeated ForeignEnum repeated_foreign_enum = 52;
// Packed repeated
repeated int32 packed_repeated_int32 = 61 [packed=true];
repeated int64 packed_repeated_int64 = 62 [packed=true];
repeated uint32 packed_repeated_uint32 = 63 [packed=true];
repeated uint64 packed_repeated_uint64 = 64 [packed=true];
repeated sint32 packed_repeated_sint32 = 65 [packed=true];
repeated sint64 packed_repeated_sint64 = 66 [packed=true];
repeated fixed32 packed_repeated_fixed32 = 67 [packed=true];
repeated fixed64 packed_repeated_fixed64 = 68 [packed=true];
repeated sfixed32 packed_repeated_sfixed32 = 69 [packed=true];
repeated sfixed64 packed_repeated_sfixed64 = 70 [packed=true];
repeated float packed_repeated_float = 71 [packed=true];
repeated double packed_repeated_double = 72 [packed=true];
repeated bool packed_repeated_bool = 73 [packed=true];
oneof oneof_field {
uint32 oneof_uint32 = 111;
ForeignMessage oneof_foreign_message = 112;
string oneof_string = 113;
bytes oneof_bytes = 114;
}
}
message ForeignMessage {
optional int32 c = 1;
}
enum ForeignEnum {
FOREIGN_FOO = 4;
FOREIGN_BAR = 5;
FOREIGN_BAZ = 6;
}
message TestExtendable {
extensions 1 to max;
}
message ExtendsWithMessage {
extend TestExtendable {
optional ExtendsWithMessage optional_extension = 19;
repeated ExtendsWithMessage repeated_extension = 49;
}
optional int32 foo = 1;
}
extend TestExtendable {
optional int32 extend_optional_int32 = 1;
optional int64 extend_optional_int64 = 2;
optional uint32 extend_optional_uint32 = 3;
optional uint64 extend_optional_uint64 = 4;
optional sint32 extend_optional_sint32 = 5;
optional sint64 extend_optional_sint64 = 6;
optional fixed32 extend_optional_fixed32 = 7;
optional fixed64 extend_optional_fixed64 = 8;
optional sfixed32 extend_optional_sfixed32 = 9;
optional sfixed64 extend_optional_sfixed64 = 10;
optional float extend_optional_float = 11;
optional double extend_optional_double = 12;
optional bool extend_optional_bool = 13;
optional string extend_optional_string = 14;
optional bytes extend_optional_bytes = 15;
optional ForeignEnum extend_optional_foreign_enum = 22;
repeated int32 extend_repeated_int32 = 31;
repeated int64 extend_repeated_int64 = 32;
repeated uint32 extend_repeated_uint32 = 33;
repeated uint64 extend_repeated_uint64 = 34;
repeated sint32 extend_repeated_sint32 = 35;
repeated sint64 extend_repeated_sint64 = 36;
repeated fixed32 extend_repeated_fixed32 = 37;
repeated fixed64 extend_repeated_fixed64 = 38;
repeated sfixed32 extend_repeated_sfixed32 = 39;
repeated sfixed64 extend_repeated_sfixed64 = 40;
repeated float extend_repeated_float = 41;
repeated double extend_repeated_double = 42;
repeated bool extend_repeated_bool = 43;
repeated string extend_repeated_string = 44;
repeated bytes extend_repeated_bytes = 45;
repeated ForeignEnum extend_repeated_foreign_enum = 52;
repeated int32 extend_packed_repeated_int32 = 61 [packed=true];
repeated int64 extend_packed_repeated_int64 = 62 [packed=true];
repeated uint32 extend_packed_repeated_uint32 = 63 [packed=true];
repeated uint64 extend_packed_repeated_uint64 = 64 [packed=true];
repeated sint32 extend_packed_repeated_sint32 = 65 [packed=true];
repeated sint64 extend_packed_repeated_sint64 = 66 [packed=true];
repeated fixed32 extend_packed_repeated_fixed32 = 67 [packed=true];
repeated fixed64 extend_packed_repeated_fixed64 = 68 [packed=true];
repeated sfixed32 extend_packed_repeated_sfixed32 = 69 [packed=true];
repeated sfixed64 extend_packed_repeated_sfixed64 = 70 [packed=true];
repeated float extend_packed_repeated_float = 71 [packed=true];
repeated double extend_packed_repeated_double = 72 [packed=true];
repeated bool extend_packed_repeated_bool = 73 [packed=true];
repeated ForeignEnum extend_packed_repeated_foreign_enum = 82
[packed=true];
}
message TestMapFields {
map<string, string> map_string_string = 1;
map<string, int32> map_string_int32 = 2;
map<string, int64> map_string_int64 = 3;
map<string, bool> map_string_bool = 4;
map<string, double> map_string_double = 5;
map<string, MapValueEnum> map_string_enum = 6;
map<string, MapValueMessage> map_string_msg = 7;
map<int32, string> map_int32_string = 8;
map<int64, string> map_int64_string = 9;
map<bool, string> map_bool_string = 10;
optional TestMapFields test_map_fields = 11;
map<string, TestMapFields> map_string_testmapfields = 12;
}
enum MapValueEnum {
MAP_VALUE_FOO = 0;
MAP_VALUE_BAR = 1;
MAP_VALUE_BAZ = 2;
}
message MapValueMessage {
optional int32 foo = 1;
}
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
syntax = "proto2";
package javatests.com.google.apps.jspb;
......@@ -23,8 +23,62 @@ var wellKnownTypes = [
'../src/google/protobuf/wrappers.proto',
];
gulp.task('genproto_closure', function (cb) {
exec(protoc + ' --js_out=library=testproto_libs,binary:. -I ../src -I . *.proto && ' + protoc + ' --js_out=one_output_file_per_input_file,binary:. -I ../src -I . ' + wellKnownTypes.join(' '),
var group1Protos = [
'data.proto',
'test3.proto',
'test5.proto',
'commonjs/test6/test6.proto',
'test8.proto',
'testbinary.proto',
'testempty.proto',
'test.proto',
];
var group2Protos = [
'proto3_test.proto',
'test2.proto',
'test4.proto',
'commonjs/test7/test7.proto',
];
gulp.task('genproto_well_known_types_closure', function (cb) {
exec(protoc + ' --js_out=one_output_file_per_input_file,binary:. -I ../src -I . ' + wellKnownTypes.join(' '),
function (err, stdout, stderr) {
console.log(stdout);
console.log(stderr);
cb(err);
});
});
gulp.task('genproto_group1_closure', function (cb) {
exec(protoc + ' --js_out=library=testproto_libs1,binary:. -I ../src -I . ' + group1Protos.join(' '),
function (err, stdout, stderr) {
console.log(stdout);
console.log(stderr);
cb(err);
});
});
gulp.task('genproto_group2_closure', function (cb) {
exec(protoc + ' --js_out=library=testproto_libs2,binary:. -I ../src -I . -I commonjs ' + group2Protos.join(' '),
function (err, stdout, stderr) {
console.log(stdout);
console.log(stderr);
cb(err);
});
});
gulp.task('genproto_well_known_types_commonjs', function (cb) {
exec('mkdir -p commonjs_out && ' + protoc + ' --js_out=import_style=commonjs,binary:commonjs_out -I ../src ' + wellKnownTypes.join(' '),
function (err, stdout, stderr) {
console.log(stdout);
console.log(stderr);
cb(err);
});
});
gulp.task('genproto_group1_commonjs', function (cb) {
exec('mkdir -p commonjs_out && ' + protoc + ' --js_out=import_style=commonjs,binary:commonjs_out -I ../src -I commonjs -I . ' + group1Protos.join(' '),
function (err, stdout, stderr) {
console.log(stdout);
console.log(stderr);
......@@ -32,8 +86,8 @@ gulp.task('genproto_closure', function (cb) {
});
});
gulp.task('genproto_commonjs', function (cb) {
exec('mkdir -p commonjs_out && ' + protoc + ' --js_out=import_style=commonjs,binary:commonjs_out -I ../src -I commonjs -I . *.proto commonjs/test*/*.proto ' + wellKnownTypes.join(' '),
gulp.task('genproto_group2_commonjs', function (cb) {
exec('mkdir -p commonjs_out && ' + protoc + ' --js_out=import_style=commonjs,binary:commonjs_out -I ../src -I commonjs -I . ' + group2Protos.join(' '),
function (err, stdout, stderr) {
console.log(stdout);
console.log(stderr);
......@@ -105,7 +159,7 @@ gulp.task('commonjs_testdeps', function (cb) {
});
});
gulp.task('make_commonjs_out', ['dist', 'genproto_commonjs', 'genproto_commonjs_wellknowntypes', 'commonjs_asserts', 'commonjs_testdeps'], function (cb) {
gulp.task('make_commonjs_out', ['dist', 'genproto_well_known_types_commonjs', 'genproto_group1_commonjs', 'genproto_group2_commonjs', 'genproto_commonjs_wellknowntypes', 'commonjs_asserts', 'commonjs_testdeps'], function (cb) {
// TODO(haberman): minify this more aggressively.
// Will require proper externs/exports.
var cmd = "mkdir -p commonjs_out/binary && mkdir -p commonjs_out/test_node_modules && ";
......@@ -128,8 +182,8 @@ gulp.task('make_commonjs_out', ['dist', 'genproto_commonjs', 'genproto_commonjs_
});
});
gulp.task('deps', ['genproto_closure'], function (cb) {
exec('./node_modules/google-closure-library/closure/bin/build/depswriter.py *.js binary/*.js > deps.js',
gulp.task('deps', ['genproto_well_known_types_closure', 'genproto_group1_closure', 'genproto_group2_closure'], function (cb) {
exec('./node_modules/google-closure-library/closure/bin/build/depswriter.py binary/arith.js binary/constants.js binary/decoder.js binary/encoder.js binary/reader.js binary/utils.js binary/writer.js debug.js map.js message.js node_loader.js test_bootstrap.js > deps.js',
function (err, stdout, stderr) {
console.log(stdout);
console.log(stderr);
......@@ -137,7 +191,7 @@ gulp.task('deps', ['genproto_closure'], function (cb) {
});
});
gulp.task('test_closure', ['genproto_closure', 'deps'], function (cb) {
gulp.task('test_closure', ['genproto_well_known_types_closure', 'genproto_group1_closure', 'genproto_group2_closure', 'deps'], function (cb) {
exec('JASMINE_CONFIG_PATH=jasmine.json ./node_modules/.bin/jasmine',
function (err, stdout, stderr) {
console.log(stdout);
......
......@@ -10,6 +10,8 @@
"deps.js",
"google/protobuf/any.js",
"google/protobuf/struct.js",
"google/protobuf/timestamp.js"
"google/protobuf/timestamp.js",
"testproto_libs1.js",
"testproto_libs2.js"
]
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment