pacc 4.15.1 → 4.16.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +1 -1
- package/src/attributes.mjs +11 -5
- package/src/expression.mjs +36 -41
- package/src/filter.mjs +29 -42
- package/types/attributes.d.mts +1 -0
- package/types/expression.d.mts +1 -0
package/package.json
CHANGED
package/src/attributes.mjs
CHANGED
|
@@ -1,5 +1,10 @@
|
|
|
1
|
+
|
|
2
|
+
|
|
3
|
+
export const baseTypes = new Set(["string", "number", "bigint", "boolean"]);
|
|
4
|
+
|
|
1
5
|
const types = {
|
|
2
6
|
base: { name: "base" },
|
|
7
|
+
|
|
3
8
|
string: { name: "string", extends: "base" },
|
|
4
9
|
number: {
|
|
5
10
|
name: "number",
|
|
@@ -7,6 +12,12 @@ const types = {
|
|
|
7
12
|
convertValue: (value, attribute) =>
|
|
8
13
|
typeof value === "string" ? parseFloat(value) : value
|
|
9
14
|
},
|
|
15
|
+
boolean: {
|
|
16
|
+
name: "boolean",
|
|
17
|
+
extends: "base",
|
|
18
|
+
convertValue: (value, attribute) => (!value || value === "0" ? false : true)
|
|
19
|
+
},
|
|
20
|
+
|
|
10
21
|
integer: {
|
|
11
22
|
name: "integer",
|
|
12
23
|
extends: "base",
|
|
@@ -14,11 +25,6 @@ const types = {
|
|
|
14
25
|
typeof value === "string" ? parseInt(value) : value
|
|
15
26
|
},
|
|
16
27
|
"unsigned-integer": { name: "unsigned-integer", extends: "integer" },
|
|
17
|
-
boolean: {
|
|
18
|
-
name: "boolean",
|
|
19
|
-
extends: "base",
|
|
20
|
-
convertValue: (value, attribute) => (!value || value === "0" ? false : true)
|
|
21
|
-
},
|
|
22
28
|
url: { name: "url", extends: "string" },
|
|
23
29
|
object: { name: "object", extends: "base" }
|
|
24
30
|
};
|
package/src/expression.mjs
CHANGED
|
@@ -19,6 +19,35 @@ import {
|
|
|
19
19
|
EOF
|
|
20
20
|
} from "./tokens.mjs";
|
|
21
21
|
|
|
22
|
+
export function binop(op, left, right) {
|
|
23
|
+
switch (op) {
|
|
24
|
+
case DOUBLE_BAR:
|
|
25
|
+
return left || right;
|
|
26
|
+
case DOUBLE_AMPERSAND:
|
|
27
|
+
return left && right;
|
|
28
|
+
case EQUAL:
|
|
29
|
+
return left == right;
|
|
30
|
+
case NOT_EQUAL:
|
|
31
|
+
return left != right;
|
|
32
|
+
case GREATER:
|
|
33
|
+
return left > right;
|
|
34
|
+
case LESS:
|
|
35
|
+
return left < right;
|
|
36
|
+
case GREATER_EQUAL:
|
|
37
|
+
return left >= right;
|
|
38
|
+
case LESS_EQUAL:
|
|
39
|
+
return left <= right;
|
|
40
|
+
case PLUS:
|
|
41
|
+
return left + right;
|
|
42
|
+
case MINUS:
|
|
43
|
+
return left - right;
|
|
44
|
+
case STAR:
|
|
45
|
+
return left * right;
|
|
46
|
+
case DIVIDE:
|
|
47
|
+
return left / right;
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
|
|
22
51
|
export function parse(context) {
|
|
23
52
|
let node, token;
|
|
24
53
|
|
|
@@ -65,9 +94,9 @@ export function parse(context) {
|
|
|
65
94
|
switch (typeof token) {
|
|
66
95
|
case "string":
|
|
67
96
|
return { path: [token] };
|
|
68
|
-
case "boolean":
|
|
69
|
-
case "bigint":
|
|
70
97
|
case "number":
|
|
98
|
+
case "bigint":
|
|
99
|
+
case "boolean":
|
|
71
100
|
return token;
|
|
72
101
|
}
|
|
73
102
|
|
|
@@ -80,35 +109,11 @@ export function parse(context) {
|
|
|
80
109
|
const right = expression(token.precedence - 1);
|
|
81
110
|
if (typeof left === typeof right) {
|
|
82
111
|
switch (typeof left) {
|
|
83
|
-
case "bigint":
|
|
84
|
-
case "number":
|
|
85
112
|
case "string":
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
return left > right;
|
|
89
|
-
case GREATER_EQUAL:
|
|
90
|
-
return left >= right;
|
|
91
|
-
case LESS:
|
|
92
|
-
return left < right;
|
|
93
|
-
case LESS_EQUAL:
|
|
94
|
-
return left <= right;
|
|
95
|
-
case EQUAL:
|
|
96
|
-
return left == right;
|
|
97
|
-
case NOT_EQUAL:
|
|
98
|
-
return left != right;
|
|
99
|
-
}
|
|
100
|
-
break;
|
|
113
|
+
case "number":
|
|
114
|
+
case "bigint":
|
|
101
115
|
case "boolean":
|
|
102
|
-
|
|
103
|
-
case DOUBLE_BAR:
|
|
104
|
-
return left || right;
|
|
105
|
-
case DOUBLE_AMPERSAND:
|
|
106
|
-
return left && right;
|
|
107
|
-
case EQUAL:
|
|
108
|
-
return left == right;
|
|
109
|
-
case NOT_EQUAL:
|
|
110
|
-
return left != right;
|
|
111
|
-
}
|
|
116
|
+
return binop(token, left, right);
|
|
112
117
|
}
|
|
113
118
|
}
|
|
114
119
|
return {
|
|
@@ -122,19 +127,9 @@ export function parse(context) {
|
|
|
122
127
|
const right = expression(token.precedence);
|
|
123
128
|
if (typeof left === typeof right) {
|
|
124
129
|
switch (typeof left) {
|
|
125
|
-
case "bigint":
|
|
126
130
|
case "number":
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
return left + right;
|
|
130
|
-
case MINUS:
|
|
131
|
-
return left - right;
|
|
132
|
-
case STAR:
|
|
133
|
-
return left * right;
|
|
134
|
-
case DIVIDE:
|
|
135
|
-
return left / right;
|
|
136
|
-
}
|
|
137
|
-
break;
|
|
131
|
+
case "bigint":
|
|
132
|
+
return binop(token, left, right);
|
|
138
133
|
}
|
|
139
134
|
}
|
|
140
135
|
if (token === DOT) {
|
package/src/filter.mjs
CHANGED
|
@@ -7,14 +7,15 @@ import {
|
|
|
7
7
|
GREATER,
|
|
8
8
|
GREATER_EQUAL
|
|
9
9
|
} from "pacc";
|
|
10
|
+
import { binop } from "./expression.mjs";
|
|
10
11
|
|
|
11
|
-
function dateOp(value, against
|
|
12
|
-
return
|
|
12
|
+
function dateOp(op, value, against) {
|
|
13
|
+
return binop(op, value.getTime(), against.getTime());
|
|
13
14
|
}
|
|
14
15
|
|
|
15
|
-
function collectionOp(value, against
|
|
16
|
+
function collectionOp(op, value, against) {
|
|
16
17
|
for (const v of value) {
|
|
17
|
-
if (allOp(v, against
|
|
18
|
+
if (allOp(op, v, against)) {
|
|
18
19
|
return true;
|
|
19
20
|
}
|
|
20
21
|
}
|
|
@@ -22,7 +23,7 @@ function collectionOp(value, against, op) {
|
|
|
22
23
|
return false;
|
|
23
24
|
}
|
|
24
25
|
|
|
25
|
-
function allOp(value, against
|
|
26
|
+
function allOp(op, value, against) {
|
|
26
27
|
switch (typeof value) {
|
|
27
28
|
case "undefined":
|
|
28
29
|
return false;
|
|
@@ -33,13 +34,13 @@ function allOp(value, against, op) {
|
|
|
33
34
|
}
|
|
34
35
|
|
|
35
36
|
if (value instanceof Map) {
|
|
36
|
-
return collectionOp(value.keys(), against
|
|
37
|
+
return collectionOp(op, value.keys(), against);
|
|
37
38
|
}
|
|
38
39
|
if (value instanceof RegExp) {
|
|
39
40
|
return value.test(against);
|
|
40
41
|
}
|
|
41
42
|
if (value[Symbol.iterator]) {
|
|
42
|
-
return collectionOp(value, against
|
|
43
|
+
return collectionOp(op, value, against);
|
|
43
44
|
}
|
|
44
45
|
|
|
45
46
|
switch (typeof against) {
|
|
@@ -50,26 +51,29 @@ function allOp(value, against, op) {
|
|
|
50
51
|
against[0] instanceof Date &&
|
|
51
52
|
against[1] instanceof Date
|
|
52
53
|
) {
|
|
53
|
-
return
|
|
54
|
+
return (
|
|
55
|
+
dateOp(GREATER_EQUAL, value, against[0]) &&
|
|
56
|
+
dateOp(LESS_EQUAL, value, against[1])
|
|
57
|
+
);
|
|
54
58
|
}
|
|
55
59
|
|
|
56
60
|
if (against instanceof Date) {
|
|
57
|
-
return dateOp(value, against
|
|
61
|
+
return dateOp(op, value, against);
|
|
58
62
|
}
|
|
59
63
|
}
|
|
60
64
|
|
|
61
65
|
if (value[Symbol.toPrimitive] && against[Symbol.toPrimitive]) {
|
|
62
|
-
return
|
|
66
|
+
return binop(
|
|
67
|
+
op,
|
|
63
68
|
value[Symbol.toPrimitive]("number"),
|
|
64
|
-
against[Symbol.toPrimitive]("number")
|
|
65
|
-
op
|
|
69
|
+
against[Symbol.toPrimitive]("number")
|
|
66
70
|
);
|
|
67
71
|
}
|
|
68
72
|
break;
|
|
69
73
|
|
|
70
74
|
case "bigint":
|
|
71
75
|
case "number":
|
|
72
|
-
return allOp(value[Symbol.toPrimitive]("number"), against
|
|
76
|
+
return allOp(op, value[Symbol.toPrimitive]("number"), against);
|
|
73
77
|
|
|
74
78
|
case "string":
|
|
75
79
|
if (against.length === 0) {
|
|
@@ -77,11 +81,11 @@ function allOp(value, against, op) {
|
|
|
77
81
|
}
|
|
78
82
|
|
|
79
83
|
if (value instanceof Date) {
|
|
80
|
-
return dateOp(value, new Date(against)
|
|
84
|
+
return dateOp(op, value, new Date(against));
|
|
81
85
|
}
|
|
82
86
|
break;
|
|
83
87
|
case "boolean":
|
|
84
|
-
return
|
|
88
|
+
return binop(op, value ? true : false, against);
|
|
85
89
|
}
|
|
86
90
|
|
|
87
91
|
if (against instanceof RegExp) {
|
|
@@ -92,7 +96,7 @@ function allOp(value, against, op) {
|
|
|
92
96
|
case "string":
|
|
93
97
|
switch (typeof against) {
|
|
94
98
|
case "boolean":
|
|
95
|
-
return
|
|
99
|
+
return binop(op, value.length !== 0, against);
|
|
96
100
|
case "string":
|
|
97
101
|
if (
|
|
98
102
|
op === EQUAL &&
|
|
@@ -106,14 +110,14 @@ function allOp(value, against, op) {
|
|
|
106
110
|
}
|
|
107
111
|
case "bigint":
|
|
108
112
|
case "number":
|
|
109
|
-
return value.length ?
|
|
113
|
+
return value.length ? binop(op, value, against) : true;
|
|
110
114
|
case "object":
|
|
111
115
|
if (value.length === 0) {
|
|
112
116
|
return false;
|
|
113
117
|
}
|
|
114
118
|
|
|
115
119
|
if (against instanceof Date) {
|
|
116
|
-
return dateOp(new Date(value), against
|
|
120
|
+
return dateOp(op, new Date(value), against);
|
|
117
121
|
}
|
|
118
122
|
|
|
119
123
|
if (against instanceof RegExp) {
|
|
@@ -122,7 +126,7 @@ function allOp(value, against, op) {
|
|
|
122
126
|
|
|
123
127
|
if (against instanceof Map) {
|
|
124
128
|
for (const [k, v] of against) {
|
|
125
|
-
if (allOp(value, k
|
|
129
|
+
if (allOp(op, value, k) || allOp(op, value, v)) {
|
|
126
130
|
return true;
|
|
127
131
|
}
|
|
128
132
|
}
|
|
@@ -130,7 +134,7 @@ function allOp(value, against, op) {
|
|
|
130
134
|
|
|
131
135
|
if (against[Symbol.iterator]) {
|
|
132
136
|
for (const i of against) {
|
|
133
|
-
if (allOp(value, i
|
|
137
|
+
if (allOp(op, value, i)) {
|
|
134
138
|
return true;
|
|
135
139
|
}
|
|
136
140
|
}
|
|
@@ -149,7 +153,7 @@ function allOp(value, against, op) {
|
|
|
149
153
|
|
|
150
154
|
if (against instanceof Map) {
|
|
151
155
|
for (const [k, v] of against) {
|
|
152
|
-
if (
|
|
156
|
+
if (binop(op, value, k) || binop(op, value, v)) {
|
|
153
157
|
return true;
|
|
154
158
|
}
|
|
155
159
|
}
|
|
@@ -158,20 +162,20 @@ function allOp(value, against, op) {
|
|
|
158
162
|
|
|
159
163
|
if (against[Symbol.iterator]) {
|
|
160
164
|
for (const i of against) {
|
|
161
|
-
if (
|
|
165
|
+
if (binop(op, value, i)) {
|
|
162
166
|
return true;
|
|
163
167
|
}
|
|
164
168
|
}
|
|
165
169
|
return false;
|
|
166
170
|
}
|
|
167
171
|
}
|
|
168
|
-
return
|
|
172
|
+
return binop(op, value, against);
|
|
169
173
|
case "boolean":
|
|
170
174
|
switch (typeof against) {
|
|
171
175
|
case "object":
|
|
172
176
|
if (against[Symbol.iterator]) {
|
|
173
177
|
for (const i of against) {
|
|
174
|
-
if (allOp(value, i
|
|
178
|
+
if (allOp(op, value, i)) {
|
|
175
179
|
return true;
|
|
176
180
|
}
|
|
177
181
|
}
|
|
@@ -185,23 +189,6 @@ function allOp(value, against, op) {
|
|
|
185
189
|
return false;
|
|
186
190
|
}
|
|
187
191
|
|
|
188
|
-
function numberOp(value, against, op) {
|
|
189
|
-
switch (op) {
|
|
190
|
-
case NOT_EQUAL:
|
|
191
|
-
return value != against;
|
|
192
|
-
case EQUAL:
|
|
193
|
-
return value == against;
|
|
194
|
-
case GREATER:
|
|
195
|
-
return value > against;
|
|
196
|
-
case LESS:
|
|
197
|
-
return value < against;
|
|
198
|
-
case GREATER_EQUAL:
|
|
199
|
-
return value >= against;
|
|
200
|
-
case LESS_EQUAL:
|
|
201
|
-
return value <= against;
|
|
202
|
-
}
|
|
203
|
-
}
|
|
204
|
-
|
|
205
192
|
/**
|
|
206
193
|
* Generate filter function.
|
|
207
194
|
* @param {Object} [filterBy]
|
|
@@ -212,7 +199,7 @@ export function filter(filterBy) {
|
|
|
212
199
|
const filters = Object.entries(filterBy).map(([key, against]) => {
|
|
213
200
|
return a => {
|
|
214
201
|
const [value, op] = getAttributeAndOperator(a, key);
|
|
215
|
-
return allOp(value, against
|
|
202
|
+
return allOp(op, value, against);
|
|
216
203
|
};
|
|
217
204
|
});
|
|
218
205
|
|
package/types/attributes.d.mts
CHANGED
package/types/expression.d.mts
CHANGED