UNPKG

moleculer

Version:

Fast & powerful microservices framework for Node.JS

258 lines (191 loc) 7.33 kB
"use strict"; let Promise = require("bluebird"); let Context = require("../../src/context"); let ServiceBroker = require("../../src/service-broker"); let { MoleculerError, RequestSkippedError } = require("../../src/errors"); describe("Test Context", () => { it("test with empty opts", () => { let ctx = new Context(); expect(ctx.id).toBeNull(); expect(ctx.broker).not.toBeDefined(); expect(ctx.action).not.toBeDefined(); expect(ctx.nodeID).toBeNull(); expect(ctx.parentID).toBeNull(); expect(ctx.metrics).toBe(false); expect(ctx.level).toBe(1); expect(ctx.timeout).toBe(0); expect(ctx.retryCount).toBe(0); expect(ctx.params).toEqual({}); expect(ctx.meta).toEqual({}); expect(ctx.requestID).toBeNull(); expect(ctx.startTime).toBeNull(); expect(ctx.startHrTime).toBeNull(); expect(ctx.stopTime).toBeNull(); expect(ctx.duration).toBe(0); expect(ctx.cachedResult).toBe(false); }); it("test with constructor params", () => { let broker = new ServiceBroker(); let action = { name: "posts.find" }; let ctx = new Context(broker, action); expect(ctx.broker).toBe(broker); expect(ctx.action).toBe(action); }); }); describe("Test setParams", () => { it("should override the params", () => { let params1 = { a: 1 }; let params2 = { b: 5 }; let ctx = new Context(); ctx.params = params1; ctx.setParams(params2); expect(ctx.params).not.toBe(params1); expect(ctx.params).toBe(params2); }); it("should clone the params", () => { let params1 = { a: 1 }; let ctx = new Context(); ctx.params1 = params1; let params2 = { b: 5 }; ctx.setParams(params2, true); expect(ctx.params).not.toBe(params2); expect(ctx.params).toEqual(params2); }); }); describe("Test call method", () => { let broker = new ServiceBroker(); broker.call = jest.fn(); it("should call broker.call method with itself", () => { let ctx = new Context(broker); let p = { id: 5 }; ctx.call("posts.find", p); expect(broker.call).toHaveBeenCalledTimes(1); expect(broker.call).toHaveBeenCalledWith("posts.find", p, { parentCtx: ctx }); }); it("should call broker.call method with options", () => { broker.call.mockClear(); let ctx = new Context(broker); let p = { id: 5 }; ctx.call("posts.find", p, { timeout: 2500 }); expect(broker.call).toHaveBeenCalledTimes(1); expect(broker.call).toHaveBeenCalledWith("posts.find", p, { parentCtx: ctx, timeout: 2500 }); }); it("should decrement the timeout with elapsed time", () => { broker.call.mockClear(); let ctx = new Context(broker); ctx._metricStart(); ctx.timeout = 1000; return Promise.delay(300).then(() => { ctx.call("posts.find", {}); expect(broker.call).toHaveBeenCalledTimes(1); let opts = broker.call.mock.calls[0][2]; expect(opts.timeout).toBeGreaterThan(500); expect(opts.timeout).toBeLessThan(800); }); }); it("should throw RequestSkippedError", () => { broker.call.mockClear(); let ctx = new Context(broker); ctx._metricStart(); ctx.timeout = 200; return Promise.delay(300).then(() => { return ctx.call("posts.find", {}); }).catch(err => { expect(err).toBeInstanceOf(RequestSkippedError); expect(err.data.action).toBe("posts.find"); }); }); }); describe("Test emit method", () => { let broker = new ServiceBroker(); broker.emit = jest.fn(); let ctx = new Context(broker); it("should call broker.emit method with object param", () => { let data = { id: 5 }; ctx.emit("request.rest", data); expect(broker.emit).toHaveBeenCalledTimes(1); expect(broker.emit).toHaveBeenCalledWith("request.rest", data); }); it("should call broker.emit method with string param", () => { broker.emit.mockClear(); ctx.emit("request.rest", "string-data"); expect(broker.emit).toHaveBeenCalledTimes(1); expect(broker.emit).toHaveBeenCalledWith("request.rest", "string-data"); }); }); describe("Test _metricStart method", () => { let broker = new ServiceBroker({ metrics: true, nodeID: "master" }); let ctx = new Context(broker, { name: "users.get" }); ctx.requestID = "abcdef"; ctx.parentID = 123; ctx.metrics = true; broker.emit = jest.fn(); it("should not emit start event", () => { ctx._metricStart(); expect(ctx.startTime).toBeDefined(); expect(ctx.stopTime).toBeNull(); expect(ctx.duration).toBe(0); expect(broker.emit).toHaveBeenCalledTimes(0); }); it("should emit start event", () => { broker.emit.mockClear(); ctx.nodeID = "remote-node"; ctx._metricStart(true); expect(ctx.startTime).toBeDefined(); expect(ctx.stopTime).toBeNull(); expect(ctx.duration).toBe(0); expect(broker.emit).toHaveBeenCalledTimes(1); expect(broker.emit).toHaveBeenCalledWith("metrics.trace.span.start", {"action": {"name": "users.get"}, "id": ctx.id, "level": 1, "parent": 123, "remoteCall": true, "requestID": "abcdef", "startTime": ctx.startTime, "nodeID": broker.nodeID, "targetNodeID": "remote-node"}); }); }); describe("Test _metricFinish method", () => { let broker = new ServiceBroker({ metrics: true }); let ctx = new Context(broker, { name: "users.get" }); ctx.nodeID = "server-2"; ctx.parentID = 123; ctx.metrics = true; ctx.generateID(); broker.emit = jest.fn(); ctx._metricStart(); it("should emit finish event", () => { broker.emit.mockClear(); return new Promise(resolve => { setTimeout(() => { ctx._metricFinish(null, true); expect(ctx.stopTime).toBeGreaterThan(0); expect(ctx.duration).toBeGreaterThan(0); expect(broker.emit).toHaveBeenCalledTimes(1); expect(broker.emit).toHaveBeenCalledWith("metrics.trace.span.finish", {"action": {"name": "users.get"}, "duration": ctx.duration, "id": ctx.id, "parent": 123, "requestID": ctx.requestID, "startTime": ctx.startTime, "endTime": ctx.stopTime, "fromCache": false, "level": 1, "remoteCall": true, "nodeID": broker.nodeID, "targetNodeID": "server-2"}); resolve(); }, 100); }); }); it("should emit finish event with error", () => { broker.emit.mockClear(); return new Promise(resolve => { ctx._metricFinish(new MoleculerError("Some error!", 511, "ERR_CUSTOM", { a: 5 }), true); expect(ctx.stopTime).toBeGreaterThan(0); expect(broker.emit).toHaveBeenCalledTimes(1); expect(broker.emit).toHaveBeenCalledWith("metrics.trace.span.finish", {"action": {"name": "users.get"}, "duration": ctx.duration, "error": { "message": "Some error!", "name": "MoleculerError", "code": 511, "type": "ERR_CUSTOM" }, "id": ctx.id, "parent": 123, "requestID": ctx.requestID, "startTime": ctx.startTime, "endTime": ctx.stopTime, "fromCache": false, "level": 1, "remoteCall": true, "nodeID": broker.nodeID, "targetNodeID": "server-2" }); resolve(); }); }); it("should not emit finish event", () => { broker.emit.mockClear(); return new Promise(resolve => { setTimeout(() => { ctx._metricFinish(); expect(ctx.stopTime).toBeGreaterThan(0); expect(ctx.duration).toBeGreaterThan(0); expect(broker.emit).toHaveBeenCalledTimes(0); resolve(); }, 100); }); }); });