diff --git a/lib/fake-server/index.js b/lib/fake-server/index.js index 8ae64f7..e4ee4d9 100644 --- a/lib/fake-server/index.js +++ b/lib/fake-server/index.js @@ -71,7 +71,8 @@ function matchOne(response, reqMethod, reqUrl) { var matchUrl = !url || url === reqUrl || - (typeof url.test === "function" && url.test(reqUrl)); + (typeof url.test === "function" && url.test(reqUrl)) || + (typeof url === "function" && url(reqUrl) === true); return matchMethod && matchUrl; } diff --git a/lib/fake-server/index.test.js b/lib/fake-server/index.test.js index 0f56365..eb23c4d 100644 --- a/lib/fake-server/index.test.js +++ b/lib/fake-server/index.test.js @@ -369,6 +369,20 @@ describe("sinonFakeServer", function() { ]); }); + it("responds to URL matched by url matcher function", function() { + this.server.respondWith(function() { + return true; + }, "FuncMatcher"); + + this.server.respond(); + + assert.equals(this.getPathAsync.respond.args[0], [ + 200, + {}, + "FuncMatcher" + ]); + }); + it("does not respond to URL not matched by regexp", function() { this.server.respondWith(/^\/p.*/, "No regexp match"); @@ -377,6 +391,16 @@ describe("sinonFakeServer", function() { assert.equals(this.getRootAsync.respond.args[0], [404, {}, ""]); }); + it("does not respond to URL not matched by function url matcher", function() { + this.server.respondWith(function() { + return false; + }, "No function match"); + + this.server.respond(); + + assert.equals(this.getRootAsync.respond.args[0], [404, {}, ""]); + }); + it("responds to all URLs matched by regexp", function() { this.server.respondWith(/^\/.*/, "Match all URLs"); @@ -394,6 +418,25 @@ describe("sinonFakeServer", function() { ]); }); + it("responds to all URLs matched by function matcher", function() { + this.server.respondWith(function() { + return true; + }, "Match all URLs"); + + this.server.respond(); + + assert.equals(this.getRootAsync.respond.args[0], [ + 200, + {}, + "Match all URLs" + ]); + assert.equals(this.getPathAsync.respond.args[0], [ + 200, + {}, + "Match all URLs" + ]); + }); + it("responds to all requests when match URL is falsy", function() { this.server.respondWith("", "Falsy URL"); @@ -411,6 +454,17 @@ describe("sinonFakeServer", function() { ]); }); + it("responds to no requests when function matcher is falsy", function() { + this.server.respondWith(function() { + return false; + }, "Falsy URL"); + + this.server.respond(); + + assert.equals(this.getRootAsync.respond.args[0], [404, {}, ""]); + assert.equals(this.getPathAsync.respond.args[0], [404, {}, ""]); + }); + it("responds to all GET requests", function() { this.server.respondWith("GET", "", "All GETs"); @@ -856,6 +910,41 @@ describe("sinonFakeServer", function() { assert(handler.calledOnce); }); + function equalMatcher(expected) { + return function(test) { + return expected === test; + }; + } + + it("yields response to request function handler when url is a function that returns true", function() { + var handler = sinon.spy(); + this.server.respondWith( + "GET", + equalMatcher("/hello?world"), + handler + ); + var xhr = new FakeXMLHttpRequest(); + xhr.open("GET", "/hello?world"); + xhr.send(); + + this.server.respond(); + + assert(handler.calledOnce); + }); + + // eslint-disable-next-line max-len + it("yields response to request function handler when url is a function that returns true with no Http Method specified", function() { + var handler = sinon.spy(); + this.server.respondWith(equalMatcher("/hello?world"), handler); + var xhr = new FakeXMLHttpRequest(); + xhr.open("GET", "/hello?world"); + xhr.send(); + + this.server.respond(); + + assert(handler.calledOnce); + }); + it("does not yield response to request function handler when method does not match", function() { var handler = sinon.spy(); this.server.respondWith("GET", "/hello", handler); @@ -868,6 +957,19 @@ describe("sinonFakeServer", function() { assert(!handler.called); }); + // eslint-disable-next-line max-len + it("does not yield response to request function handler when method does not match (using url mather function)", function() { + var handler = sinon.spy(); + this.server.respondWith("GET", equalMatcher("/hello"), handler); + var xhr = new FakeXMLHttpRequest(); + xhr.open("POST", "/hello"); + xhr.send(); + + this.server.respond(); + + assert(!handler.called); + }); + it("yields response to request function handler when regexp url matches", function() { var handler = sinon.spy(); this.server.respondWith("GET", /\/.*/, handler); @@ -892,6 +994,56 @@ describe("sinonFakeServer", function() { assert(!handler.called); }); + it("does not yield response to request function handler when urlMatcher function returns false", function() { + var handler = sinon.spy(); + this.server.respondWith("GET", equalMatcher("/goodbye"), handler); + var xhr = new FakeXMLHttpRequest(); + xhr.open("GET", "/hello"); + xhr.send(); + + this.server.respond(); + + assert(!handler.called); + }); + + // eslint-disable-next-line max-len + it("does not yield response to request function handler when urlMatcher function returns non Boolean truthy value", function() { + var handler = sinon.spy(); + this.server.respondWith( + "GET", + function() { + return "truthy"; + }, + handler + ); + var xhr = new FakeXMLHttpRequest(); + xhr.open("GET", "/hello"); + xhr.send(); + + this.server.respond(); + + assert(!handler.called); + }); + + // eslint-disable-next-line max-len + it("does not yield response to request function handler when urlMatcher function returns non Boolean falsey value", function() { + var handler = sinon.spy(); + this.server.respondWith( + "GET", + function() { + return undefined; + }, + handler + ); + var xhr = new FakeXMLHttpRequest(); + xhr.open("GET", "/hello"); + xhr.send(); + + this.server.respond(); + + assert(!handler.called); + }); + it("adds function handler without method or url filter", function() { this.server.respondWith(function(xhr) { xhr.respond(