summaryrefslogtreecommitdiffstats
path: root/src/jaegertracing/thrift/lib/nodejs/test/test_driver.js
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--src/jaegertracing/thrift/lib/nodejs/test/test_driver.js361
1 files changed, 361 insertions, 0 deletions
diff --git a/src/jaegertracing/thrift/lib/nodejs/test/test_driver.js b/src/jaegertracing/thrift/lib/nodejs/test/test_driver.js
new file mode 100644
index 000000000..7c9a91914
--- /dev/null
+++ b/src/jaegertracing/thrift/lib/nodejs/test/test_driver.js
@@ -0,0 +1,361 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * 'License'); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * 'AS IS' BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+// This is the Node.js test driver for the standard Apache Thrift
+// test service. The driver invokes every function defined in the
+// Thrift Test service with a representative range of parameters.
+//
+// The ThriftTestDriver function requires a client object
+// connected to a server hosting the Thrift Test service and
+// supports an optional callback function which is called with
+// a status message when the test is complete.
+
+const test = require("tape");
+
+const helpers = require("./helpers");
+const ttypes = require(`./${helpers.genPath}/ThriftTest_types`);
+const TException = require("thrift").Thrift.TException;
+const Int64 = require("node-int64");
+const testCases = require("./test-cases");
+
+exports.ThriftTestDriver = function(client, callback) {
+ test(
+ "NodeJS Style Callback Client Tests",
+ { skip: helpers.ecmaMode === "es6" },
+ function(assert) {
+ const checkRecursively = makeRecursiveCheck(assert);
+
+ function makeAsserter(assertionFn) {
+ return function(c) {
+ const fnName = c[0];
+ const expected = c[1];
+ client[fnName](expected, function(err, actual) {
+ assert.error(err, fnName + ": no callback error");
+ assertionFn(actual, expected, fnName);
+ });
+ };
+ }
+
+ testCases.simple.forEach(
+ makeAsserter(function(a, e, m) {
+ if (a instanceof Int64) {
+ const e64 = e instanceof Int64 ? e : new Int64(e);
+ assert.deepEqual(a.buffer, e64.buffer, m);
+ } else {
+ assert.equal(a, e, m);
+ }
+ })
+ );
+ testCases.deep.forEach(makeAsserter(assert.deepEqual));
+ testCases.deepUnordered.forEach(
+ makeAsserter(makeUnorderedDeepEqual(assert))
+ );
+
+ const arr = [];
+ for (let i = 0; i < 256; ++i) {
+ arr[i] = 255 - i;
+ }
+ let buf = new Buffer(arr);
+ client.testBinary(buf, function(err, response) {
+ assert.error(err, "testBinary: no callback error");
+ assert.equal(response.length, 256, "testBinary");
+ assert.deepEqual(response, buf, "testBinary(Buffer)");
+ });
+ buf = new Buffer(arr);
+ client.testBinary(buf.toString("binary"), function(err, response) {
+ assert.error(err, "testBinary: no callback error");
+ assert.equal(response.length, 256, "testBinary");
+ assert.deepEqual(response, buf, "testBinary(string)");
+ });
+
+ client.testMapMap(42, function(err, response) {
+ const expected = {
+ "4": { "1": 1, "2": 2, "3": 3, "4": 4 },
+ "-4": { "-4": -4, "-3": -3, "-2": -2, "-1": -1 }
+ };
+ assert.error(err, "testMapMap: no callback error");
+ assert.deepEqual(expected, response, "testMapMap");
+ });
+
+ client.testStruct(testCases.out, function(err, response) {
+ assert.error(err, "testStruct: no callback error");
+ checkRecursively(testCases.out, response, "testStruct");
+ });
+
+ client.testNest(testCases.out2, function(err, response) {
+ assert.error(err, "testNest: no callback error");
+ checkRecursively(testCases.out2, response, "testNest");
+ });
+
+ client.testInsanity(testCases.crazy, function(err, response) {
+ assert.error(err, "testInsanity: no callback error");
+ checkRecursively(testCases.insanity, response, "testInsanity");
+ });
+
+ client.testInsanity(testCases.crazy2, function(err, response) {
+ assert.error(err, "testInsanity2: no callback error");
+ checkRecursively(testCases.insanity, response, "testInsanity2");
+ });
+
+ client.testException("TException", function(err, response) {
+ assert.ok(
+ err instanceof TException,
+ "testException: correct error type"
+ );
+ assert.ok(!response, "testException: no response");
+ });
+
+ client.testException("Xception", function(err, response) {
+ assert.ok(
+ err instanceof ttypes.Xception,
+ "testException: correct error type"
+ );
+ assert.ok(!response, "testException: no response");
+ assert.equal(err.errorCode, 1001, "testException: correct error code");
+ assert.equal(
+ "Xception",
+ err.message,
+ "testException: correct error message"
+ );
+ });
+
+ client.testException("no Exception", function(err, response) {
+ assert.error(err, "testException: no callback error");
+ assert.ok(!response, "testException: no response");
+ });
+
+ client.testOneway(0, function(err, response) {
+ assert.error(err, "testOneway: no callback error");
+ assert.strictEqual(response, undefined, "testOneway: void response");
+ });
+
+ checkOffByOne(function(done) {
+ client.testI32(-1, function(err, response) {
+ assert.error(err, "checkOffByOne: no callback error");
+ assert.equal(-1, response);
+ assert.end();
+ done();
+ });
+ }, callback);
+ }
+ );
+
+ // ES6 does not support callback style
+ if (helpers.ecmaMode === "es6") {
+ checkOffByOne(done => done(), callback);
+ }
+};
+
+exports.ThriftTestDriverPromise = function(client, callback) {
+ test("Promise Client Tests", function(assert) {
+ const checkRecursively = makeRecursiveCheck(assert);
+
+ function makeAsserter(assertionFn) {
+ return function(c) {
+ const fnName = c[0];
+ const expected = c[1];
+ client[fnName](expected)
+ .then(function(actual) {
+ assertionFn(actual, expected, fnName);
+ })
+ .catch(() => assert.fail("fnName"));
+ };
+ }
+
+ testCases.simple.forEach(
+ makeAsserter(function(a, e, m) {
+ if (a instanceof Int64) {
+ const e64 = e instanceof Int64 ? e : new Int64(e);
+ assert.deepEqual(a.buffer, e64.buffer, m);
+ } else {
+ assert.equal(a, e, m);
+ }
+ })
+ );
+ testCases.deep.forEach(makeAsserter(assert.deepEqual));
+ testCases.deepUnordered.forEach(
+ makeAsserter(makeUnorderedDeepEqual(assert))
+ );
+
+ client
+ .testStruct(testCases.out)
+ .then(function(response) {
+ checkRecursively(testCases.out, response, "testStruct");
+ })
+ .catch(() => assert.fail("testStruct"));
+
+ client
+ .testNest(testCases.out2)
+ .then(function(response) {
+ checkRecursively(testCases.out2, response, "testNest");
+ })
+ .catch(() => assert.fail("testNest"));
+
+ client
+ .testInsanity(testCases.crazy)
+ .then(function(response) {
+ checkRecursively(testCases.insanity, response, "testInsanity");
+ })
+ .catch(() => assert.fail("testInsanity"));
+
+ client
+ .testInsanity(testCases.crazy2)
+ .then(function(response) {
+ checkRecursively(testCases.insanity, response, "testInsanity2");
+ })
+ .catch(() => assert.fail("testInsanity2"));
+
+ client
+ .testException("TException")
+ .then(function() {
+ assert.fail("testException: TException");
+ })
+ .catch(function(err) {
+ assert.ok(err instanceof TException);
+ });
+
+ client
+ .testException("Xception")
+ .then(function() {
+ assert.fail("testException: Xception");
+ })
+ .catch(function(err) {
+ assert.ok(err instanceof ttypes.Xception);
+ assert.equal(err.errorCode, 1001);
+ assert.equal("Xception", err.message);
+ });
+
+ client
+ .testException("no Exception")
+ .then(function(response) {
+ assert.equal(undefined, response); //void
+ })
+ .catch(() => assert.fail("testException"));
+
+ client
+ .testOneway(0)
+ .then(function(response) {
+ assert.strictEqual(response, undefined, "testOneway: void response");
+ })
+ .catch(() => assert.fail("testOneway: should not reject"));
+
+ checkOffByOne(function(done) {
+ client
+ .testI32(-1)
+ .then(function(response) {
+ assert.equal(-1, response);
+ assert.end();
+ done();
+ })
+ .catch(() => assert.fail("checkOffByOne"));
+ }, callback);
+ });
+};
+
+// Helper Functions
+// =========================================================
+
+function makeRecursiveCheck(assert) {
+ return function(map1, map2, msg) {
+ const equal = checkRecursively(map1, map2);
+
+ assert.ok(equal, msg);
+
+ // deepEqual doesn't work with fields using node-int64
+ function checkRecursively(map1, map2) {
+ if (typeof map1 !== "function" && typeof map2 !== "function") {
+ if (!map1 || typeof map1 !== "object") {
+ //Handle int64 types (which use node-int64 in Node.js JavaScript)
+ if (
+ typeof map1 === "number" &&
+ typeof map2 === "object" &&
+ map2.buffer &&
+ map2.buffer instanceof Buffer &&
+ map2.buffer.length === 8
+ ) {
+ const n = new Int64(map2.buffer);
+ return map1 === n.toNumber();
+ } else {
+ return map1 == map2;
+ }
+ } else {
+ return Object.keys(map1).every(function(key) {
+ return checkRecursively(map1[key], map2[key]);
+ });
+ }
+ }
+ }
+ };
+}
+
+function checkOffByOne(done, callback) {
+ const retry_limit = 30;
+ const retry_interval = 100;
+ let test_complete = false;
+ let retrys = 0;
+
+ /**
+ * redo a simple test after the oneway to make sure we aren't "off by one" --
+ * if the server treated oneway void like normal void, this next test will
+ * fail since it will get the void confirmation rather than the correct
+ * result. In this circumstance, the client will throw the exception:
+ *
+ * Because this is the last test against the server, when it completes
+ * the entire suite is complete by definition (the tests run serially).
+ */
+ done(function() {
+ test_complete = true;
+ });
+
+ //We wait up to retry_limit * retry_interval for the test suite to complete
+ function TestForCompletion() {
+ if (test_complete && callback) {
+ callback("Server successfully tested!");
+ } else {
+ if (++retrys < retry_limit) {
+ setTimeout(TestForCompletion, retry_interval);
+ } else if (callback) {
+ callback(
+ "Server test failed to complete after " +
+ (retry_limit * retry_interval) / 1000 +
+ " seconds"
+ );
+ }
+ }
+ }
+
+ setTimeout(TestForCompletion, retry_interval);
+}
+
+function makeUnorderedDeepEqual(assert) {
+ return function(actual, expected, name) {
+ assert.equal(actual.length, expected.length, name);
+ for (const k in actual) {
+ let found = false;
+ for (const k2 in expected) {
+ if (actual[k] === expected[k2]) {
+ found = true;
+ }
+ }
+ if (!found) {
+ assert.fail("Unexpected value " + actual[k] + " with key " + k);
+ }
+ }
+ };
+}