Skip to content

Commit ba3e89b

Browse files
authored
Merge pull request #13 from syarul/refactor
added waterfall, class Extender
2 parents e0af61a + d45c3f2 commit ba3e89b

File tree

4 files changed

+166
-4
lines changed

4 files changed

+166
-4
lines changed

libs/executor.cjs

Lines changed: 63 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,13 +3,41 @@ const executeQuery = require("./executeQuery.cjs");
33
const arrayToObject = require("./arrayToObject.cjs");
44
const dataPath = require("./dataPath.cjs");
55

6+
/**
7+
* Using waterfall structure for better readability
8+
* @param {*} query
9+
* @returns
10+
*/
11+
function waterfallParser(query) {
12+
if (query.name && Array.isArray(query.computes)) {
13+
const result = {};
14+
const current = result;
15+
16+
query.computes.reduce((acc, item) => {
17+
if (typeof item === "string") {
18+
acc[item] = {};
19+
return acc[item];
20+
} else if (typeof item === "object" && item !== null) {
21+
Object.assign(acc, item);
22+
return acc;
23+
}
24+
}, current);
25+
26+
return {
27+
[query.name]: result,
28+
};
29+
} else {
30+
return query;
31+
}
32+
}
33+
634
/**
735
* Options for query execution.
836
*
937
* @typedef {object} QueryOptions
1038
* @property {object} methods - Methods configuration.
1139
* @property {object} config - Configuration settings.
12-
* @property {string} dataUrl - Data url path.
40+
* @property {string} [dataUrl] - Data url path.
1341
*/
1442

1543
function postProcessing(options) {
@@ -29,12 +57,45 @@ function postProcessing(options) {
2957
* @returns {Promise<object>} A promise that resolves to the result object.
3058
*/
3159
const rq = (query, options) => {
32-
return executeQuery(query, null, options)
60+
const parseQuery = waterfallParser(query);
61+
return executeQuery(parseQuery, null, options)
3362
.then(postProcessing(options))
3463
.catch((error) => console.error("rql Error:", error.message));
3564
};
3665

66+
class RqExtender {
67+
constructor() {
68+
this.methods = {};
69+
}
70+
compute(payload) {
71+
return rq(payload, {
72+
methods: this.methods,
73+
config: (param) => this.getMethodsMap()[param],
74+
});
75+
}
76+
77+
getMethodsMap() {
78+
const prototype = Object.getPrototypeOf(this);
79+
const methodNames = Object.getOwnPropertyNames(prototype).filter(
80+
(name) =>
81+
typeof this[name] === "function" &&
82+
name !== "constructor" &&
83+
name !== "compute" &&
84+
name !== "getMethodsMap",
85+
);
86+
const methodsMap = {};
87+
for (const name of methodNames) {
88+
methodsMap[name] = this[name].bind(this);
89+
}
90+
return methodsMap;
91+
}
92+
}
93+
3794
global.rq = rq;
3895
exports.rq = rq;
3996
module.exports = rq;
4097
module.exports.default = rq;
98+
99+
global.RqExtender = RqExtender;
100+
exports.RqExtender = RqExtender;
101+
module.exports.RqExtender = RqExtender;

package.json

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "requrse",
3-
"version": "0.3.4",
3+
"version": "0.4.0",
44
"type": "module",
55
"description": "Lightweight driven query language",
66
"main": "libs/executor.cjs",
@@ -17,7 +17,9 @@
1717
"test:array-string": "node test/arrayString.test.mjs",
1818
"test:duplicate": "node test/duplicateField.test.mjs",
1919
"test:array-index": "node test/arrayIndex.test.mjs",
20-
"test": "npm run test:starwars && npm run test:mongoose && npm run test:mongoose-lookup && npm run test:redis && npm run test:requrse && npm run test:inflight-request-cancelation && npm run test:fantasy && npm run test:basic && npm run test:array && npm run test:array-string && npm run test:duplicate && npm run test:array-index",
20+
"test:waterfall": "node test/waterfall.test.mjs",
21+
"test:class": "node test/class.test.mjs",
22+
"test": "npm run test:starwars && npm run test:mongoose && npm run test:mongoose-lookup && npm run test:redis && npm run test:requrse && npm run test:inflight-request-cancelation && npm run test:fantasy && npm run test:basic && npm run test:array && npm run test:array-string && npm run test:duplicate && npm run test:array-index && npm run test:waterfall && npm run test:class",
2123
"test:coverage": "c8 --exclude samples --exclude test npm run test",
2224
"test:lcov": "c8 --exclude samples --exclude test --reporter lcov npm run test",
2325
"coverage": "coveralls < coverage/lcov.info"

test/class.test.mjs

Lines changed: 67 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,67 @@
1+
import assert from "assert";
2+
import { RqExtender } from "../libs/executor.cjs";
3+
import { test } from "./fixture/test.mjs";
4+
5+
await test("Classes config", () => {
6+
class TestConfig extends RqExtender {
7+
constructor() {
8+
super();
9+
this.methods = {
10+
area: "area",
11+
occupation: "occupation",
12+
person: "getPerson",
13+
birth: "birth",
14+
};
15+
}
16+
area() {
17+
return { city: "NY" };
18+
}
19+
occupation() {
20+
return { type: "CT0" };
21+
}
22+
birth() {
23+
return { year: "1981" };
24+
}
25+
getPerson(name) {
26+
return { name, age: 42 };
27+
}
28+
}
29+
30+
const test = new TestConfig();
31+
32+
const payload = {
33+
Test: {
34+
test: {
35+
person: {
36+
$params: { name: "Foo" },
37+
name: 1,
38+
age: 1,
39+
birth: {
40+
year: 1,
41+
area: {
42+
city: 1,
43+
},
44+
},
45+
occupation: {
46+
type: 1,
47+
},
48+
},
49+
},
50+
},
51+
};
52+
53+
test.compute(payload).then((result) => {
54+
assert.deepEqual(result, {
55+
Test: {
56+
test: {
57+
person: {
58+
name: "Foo",
59+
age: 42,
60+
birth: { year: "1981", area: { city: "NY" } },
61+
occupation: { type: "CT0" },
62+
},
63+
},
64+
},
65+
});
66+
});
67+
});

test/waterfall.test.mjs

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
import assert from "assert";
2+
import rq from "../libs/executor.cjs";
3+
import { test } from "./fixture/test.mjs";
4+
5+
await test("Foo Bar", () => {
6+
rq(
7+
{
8+
name: "Test",
9+
computes: [
10+
"test", // placeholder
11+
"foo",
12+
{
13+
bar: "*",
14+
},
15+
],
16+
},
17+
{
18+
methods: {
19+
bar() {
20+
return "another";
21+
},
22+
foo() {
23+
return {
24+
bar: "foobar",
25+
};
26+
},
27+
},
28+
},
29+
).then((result) => {
30+
assert.deepEqual(result, { Test: { test: { foo: { bar: "another" } } } });
31+
});
32+
});

0 commit comments

Comments
 (0)