Skip to content

Commit

Permalink
feat: Use deep equality for matching params
Browse files Browse the repository at this point in the history
Closes #102
  • Loading branch information
kingjan1999 committed Nov 5, 2024
1 parent 1305822 commit 2f2df2d
Show file tree
Hide file tree
Showing 2 changed files with 37 additions and 2 deletions.
29 changes: 28 additions & 1 deletion lib/mock-axios.ts
Original file line number Diff line number Diff line change
Expand Up @@ -301,6 +301,33 @@ const _findReqByPredicate = (predicate: (item: AxiosMockQueueItem) => boolean) =
.find(predicate);
}

const deepEqual = (x: any, y: any): boolean => {
// adapted from https://stackoverflow.com/a/16788517
// should handle most relevant edge cases (except for circular references etc.)

if (x === null || x === undefined || y === null || y === undefined) { return x === y; }
// after this just checking type of one would be enough
if (x.constructor !== y.constructor) { return false; }
// if they are functions, they should exactly refer to same one (because of closures)
if (x instanceof Function) { return x === y; }
// if they are regexps, they should exactly refer to same one (it is hard to better equality check on current ES)
if (x instanceof RegExp) { return x === y; }
if (x === y || x.valueOf() === y.valueOf()) { return true; }
if (Array.isArray(x) && x.length !== y.length) { return false; }

// if they are dates, they must had equal valueOf
if (x instanceof Date) { return false; }

// if they are strictly equal, they both need to be object at least
if (!(x instanceof Object)) { return false; }
if (!(y instanceof Object)) { return false; }

// recursive object equality check
var p = Object.keys(x);
return Object.keys(y).every(function (i) { return p.indexOf(i) !== -1; }) &&
p.every(function (i) { return deepEqual(x[i], y[i]); });
}

const _checkCriteria = (item: AxiosMockQueueItem, criteria: AxiosMockRequestCriteria) => {
if (criteria.method !== undefined && criteria.method.toLowerCase() !== item.method.toLowerCase()) {
return false;
Expand All @@ -315,7 +342,7 @@ const _checkCriteria = (item: AxiosMockQueueItem, criteria: AxiosMockRequestCrit
return false;
}

const paramsMatching = Object.entries(criteria.params).every(([key, value]) => item.config.params[key] === value);
const paramsMatching = Object.entries(criteria.params).every(([key, value]) => deepEqual(item.config.params[key], value));
if(!paramsMatching) {
return false;
}
Expand Down
10 changes: 9 additions & 1 deletion test/index.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -348,7 +348,6 @@ describe("MockAxios", () => {
});

describe("getReqMatching", () => {

it("`getReqMatching` should return the most recent request matching the criteria", () => {
const url = "url";
MockAxios.delete(url);
Expand All @@ -374,6 +373,15 @@ describe("MockAxios", () => {
expect(matchingReq.url).toEqual(url);
});

it("`getReqMatching` should match when params match (nested)", () => {
const url = "url";
MockAxios.get(url, { params: { a: ["b", "c"] } });

const matchingReq = MockAxios.getReqMatching({ params: { a: ["b", "c"] } });
expect(matchingReq).toBeDefined();
expect(matchingReq.url).toEqual(url);
});

it("`getReqMatching` should not match when params do not match", () => {
const url = "url";
MockAxios.get(url, { params: { a: "b", c: "d" } });
Expand Down

0 comments on commit 2f2df2d

Please sign in to comment.