mongo-query-normalizer 0.1.0
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/LICENSE +15 -0
- package/README.md +193 -0
- package/README.zh-CN.md +194 -0
- package/dist/ast/builders.d.ts +8 -0
- package/dist/ast/builders.d.ts.map +1 -0
- package/dist/ast/builders.js +27 -0
- package/dist/ast/builders.js.map +1 -0
- package/dist/ast/contains-opaque.d.ts +3 -0
- package/dist/ast/contains-opaque.d.ts.map +1 -0
- package/dist/ast/contains-opaque.js +14 -0
- package/dist/ast/contains-opaque.js.map +1 -0
- package/dist/ast/guards.d.ts +7 -0
- package/dist/ast/guards.d.ts.map +1 -0
- package/dist/ast/guards.js +23 -0
- package/dist/ast/guards.js.map +1 -0
- package/dist/ast/hash.d.ts +4 -0
- package/dist/ast/hash.d.ts.map +1 -0
- package/dist/ast/hash.js +67 -0
- package/dist/ast/hash.js.map +1 -0
- package/dist/ast/index.d.ts +6 -0
- package/dist/ast/index.d.ts.map +1 -0
- package/dist/ast/index.js +22 -0
- package/dist/ast/index.js.map +1 -0
- package/dist/ast/types.d.ts +28 -0
- package/dist/ast/types.d.ts.map +1 -0
- package/dist/ast/types.js +3 -0
- package/dist/ast/types.js.map +1 -0
- package/dist/ast/visitor.d.ts +3 -0
- package/dist/ast/visitor.d.ts.map +1 -0
- package/dist/ast/visitor.js +12 -0
- package/dist/ast/visitor.js.map +1 -0
- package/dist/common/types.d.ts +46 -0
- package/dist/common/types.d.ts.map +1 -0
- package/dist/common/types.js +3 -0
- package/dist/common/types.js.map +1 -0
- package/dist/compile/compile.d.ts +5 -0
- package/dist/compile/compile.d.ts.map +1 -0
- package/dist/compile/compile.js +69 -0
- package/dist/compile/compile.js.map +1 -0
- package/dist/compile-selector.d.ts +9 -0
- package/dist/compile-selector.d.ts.map +1 -0
- package/dist/compile-selector.js +14 -0
- package/dist/compile-selector.js.map +1 -0
- package/dist/conflict.d.ts +18 -0
- package/dist/conflict.d.ts.map +1 -0
- package/dist/conflict.js +30 -0
- package/dist/conflict.js.map +1 -0
- package/dist/core/canonicalize.d.ts +11 -0
- package/dist/core/canonicalize.d.ts.map +1 -0
- package/dist/core/canonicalize.js +104 -0
- package/dist/core/canonicalize.js.map +1 -0
- package/dist/core/conditions.d.ts +8 -0
- package/dist/core/conditions.d.ts.map +1 -0
- package/dist/core/conditions.js +282 -0
- package/dist/core/conditions.js.map +1 -0
- package/dist/core/conflicts-and-tighten.d.ts +15 -0
- package/dist/core/conflicts-and-tighten.d.ts.map +1 -0
- package/dist/core/conflicts-and-tighten.js +26 -0
- package/dist/core/conflicts-and-tighten.js.map +1 -0
- package/dist/core/conflicts.d.ts +14 -0
- package/dist/core/conflicts.d.ts.map +1 -0
- package/dist/core/conflicts.js +157 -0
- package/dist/core/conflicts.js.map +1 -0
- package/dist/core/constraint-propagation.d.ts +15 -0
- package/dist/core/constraint-propagation.d.ts.map +1 -0
- package/dist/core/constraint-propagation.js +93 -0
- package/dist/core/constraint-propagation.js.map +1 -0
- package/dist/core/field-condition-normalize.d.ts +22 -0
- package/dist/core/field-condition-normalize.d.ts.map +1 -0
- package/dist/core/field-condition-normalize.js +225 -0
- package/dist/core/field-condition-normalize.js.map +1 -0
- package/dist/core/index.d.ts +6 -0
- package/dist/core/index.d.ts.map +1 -0
- package/dist/core/index.js +14 -0
- package/dist/core/index.js.map +1 -0
- package/dist/core/normalize.d.ts +8 -0
- package/dist/core/normalize.d.ts.map +1 -0
- package/dist/core/normalize.js +44 -0
- package/dist/core/normalize.js.map +1 -0
- package/dist/core/operators.d.ts +11 -0
- package/dist/core/operators.d.ts.map +1 -0
- package/dist/core/operators.js +26 -0
- package/dist/core/operators.js.map +1 -0
- package/dist/core/predicate-merge.d.ts +9 -0
- package/dist/core/predicate-merge.d.ts.map +1 -0
- package/dist/core/predicate-merge.js +105 -0
- package/dist/core/predicate-merge.js.map +1 -0
- package/dist/core/predicateMerge.d.ts +17 -0
- package/dist/core/predicateMerge.d.ts.map +1 -0
- package/dist/core/predicateMerge.js +57 -0
- package/dist/core/predicateMerge.js.map +1 -0
- package/dist/core/simplify.d.ts +11 -0
- package/dist/core/simplify.d.ts.map +1 -0
- package/dist/core/simplify.js +128 -0
- package/dist/core/simplify.js.map +1 -0
- package/dist/core/stable-structural-key.d.ts +7 -0
- package/dist/core/stable-structural-key.d.ts.map +1 -0
- package/dist/core/stable-structural-key.js +71 -0
- package/dist/core/stable-structural-key.js.map +1 -0
- package/dist/core/utils.d.ts +16 -0
- package/dist/core/utils.d.ts.map +1 -0
- package/dist/core/utils.js +109 -0
- package/dist/core/utils.js.map +1 -0
- package/dist/flatten/flatten.d.ts +43 -0
- package/dist/flatten/flatten.d.ts.map +1 -0
- package/dist/flatten/flatten.js +68 -0
- package/dist/flatten/flatten.js.map +1 -0
- package/dist/flatten/index.d.ts +2 -0
- package/dist/flatten/index.d.ts.map +1 -0
- package/dist/flatten/index.js +10 -0
- package/dist/flatten/index.js.map +1 -0
- package/dist/flatten.d.ts +43 -0
- package/dist/flatten.d.ts.map +1 -0
- package/dist/flatten.js +68 -0
- package/dist/flatten.js.map +1 -0
- package/dist/index.d.ts +4 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +8 -0
- package/dist/index.js.map +1 -0
- package/dist/merge-ops.d.ts +33 -0
- package/dist/merge-ops.d.ts.map +1 -0
- package/dist/merge-ops.js +52 -0
- package/dist/merge-ops.js.map +1 -0
- package/dist/normalize-context.d.ts +16 -0
- package/dist/normalize-context.d.ts.map +1 -0
- package/dist/normalize-context.js +19 -0
- package/dist/normalize-context.js.map +1 -0
- package/dist/normalize.d.ts +6 -0
- package/dist/normalize.d.ts.map +1 -0
- package/dist/normalize.js +122 -0
- package/dist/normalize.js.map +1 -0
- package/dist/observe/diff.d.ts +7 -0
- package/dist/observe/diff.d.ts.map +1 -0
- package/dist/observe/diff.js +15 -0
- package/dist/observe/diff.js.map +1 -0
- package/dist/observe/level-boundary-hints.d.ts +11 -0
- package/dist/observe/level-boundary-hints.d.ts.map +1 -0
- package/dist/observe/level-boundary-hints.js +42 -0
- package/dist/observe/level-boundary-hints.js.map +1 -0
- package/dist/observe/level-preview-warning.d.ts +11 -0
- package/dist/observe/level-preview-warning.d.ts.map +1 -0
- package/dist/observe/level-preview-warning.js +42 -0
- package/dist/observe/level-preview-warning.js.map +1 -0
- package/dist/observe/metrics.d.ts +4 -0
- package/dist/observe/metrics.d.ts.map +1 -0
- package/dist/observe/metrics.js +30 -0
- package/dist/observe/metrics.js.map +1 -0
- package/dist/observe/warnings.d.ts +6 -0
- package/dist/observe/warnings.d.ts.map +1 -0
- package/dist/observe/warnings.js +24 -0
- package/dist/observe/warnings.js.map +1 -0
- package/dist/operations/compile.d.ts +7 -0
- package/dist/operations/compile.d.ts.map +1 -0
- package/dist/operations/compile.js +70 -0
- package/dist/operations/compile.js.map +1 -0
- package/dist/operations/conflicts-and-tighten.d.ts +29 -0
- package/dist/operations/conflicts-and-tighten.d.ts.map +1 -0
- package/dist/operations/conflicts-and-tighten.js +40 -0
- package/dist/operations/conflicts-and-tighten.js.map +1 -0
- package/dist/operations/conflicts.d.ts +28 -0
- package/dist/operations/conflicts.d.ts.map +1 -0
- package/dist/operations/conflicts.js +216 -0
- package/dist/operations/conflicts.js.map +1 -0
- package/dist/operations/conflictsAndTighten.d.ts +29 -0
- package/dist/operations/conflictsAndTighten.d.ts.map +1 -0
- package/dist/operations/conflictsAndTighten.js +40 -0
- package/dist/operations/conflictsAndTighten.js.map +1 -0
- package/dist/operations/merge.d.ts +18 -0
- package/dist/operations/merge.d.ts.map +1 -0
- package/dist/operations/merge.js +266 -0
- package/dist/operations/merge.js.map +1 -0
- package/dist/operations/parse.d.ts +20 -0
- package/dist/operations/parse.d.ts.map +1 -0
- package/dist/operations/parse.js +128 -0
- package/dist/operations/parse.js.map +1 -0
- package/dist/ops/compile-selector.d.ts +9 -0
- package/dist/ops/compile-selector.d.ts.map +1 -0
- package/dist/ops/compile-selector.js +14 -0
- package/dist/ops/compile-selector.js.map +1 -0
- package/dist/ops/index.d.ts +4 -0
- package/dist/ops/index.d.ts.map +1 -0
- package/dist/ops/index.js +14 -0
- package/dist/ops/index.js.map +1 -0
- package/dist/ops/merge-ops.d.ts +33 -0
- package/dist/ops/merge-ops.d.ts.map +1 -0
- package/dist/ops/merge-ops.js +52 -0
- package/dist/ops/merge-ops.js.map +1 -0
- package/dist/ops/parse-selector.d.ts +18 -0
- package/dist/ops/parse-selector.d.ts.map +1 -0
- package/dist/ops/parse-selector.js +29 -0
- package/dist/ops/parse-selector.js.map +1 -0
- package/dist/optimize.d.ts +18 -0
- package/dist/optimize.d.ts.map +1 -0
- package/dist/optimize.js +33 -0
- package/dist/optimize.js.map +1 -0
- package/dist/options/constants.d.ts +6 -0
- package/dist/options/constants.d.ts.map +1 -0
- package/dist/options/constants.js +72 -0
- package/dist/options/constants.js.map +1 -0
- package/dist/options/resolve.d.ts +3 -0
- package/dist/options/resolve.d.ts.map +1 -0
- package/dist/options/resolve.js +35 -0
- package/dist/options/resolve.js.map +1 -0
- package/dist/options/types.d.ts +2 -0
- package/dist/options/types.d.ts.map +1 -0
- package/dist/options/types.js +3 -0
- package/dist/options/types.js.map +1 -0
- package/dist/parse/parse.d.ts +4 -0
- package/dist/parse/parse.d.ts.map +1 -0
- package/dist/parse/parse.js +114 -0
- package/dist/parse/parse.js.map +1 -0
- package/dist/parse/plain-object.d.ts +2 -0
- package/dist/parse/plain-object.d.ts.map +1 -0
- package/dist/parse/plain-object.js +7 -0
- package/dist/parse/plain-object.js.map +1 -0
- package/dist/parse-selector.d.ts +18 -0
- package/dist/parse-selector.d.ts.map +1 -0
- package/dist/parse-selector.js +29 -0
- package/dist/parse-selector.js.map +1 -0
- package/dist/passes/canonicalize.d.ts +4 -0
- package/dist/passes/canonicalize.d.ts.map +1 -0
- package/dist/passes/canonicalize.js +40 -0
- package/dist/passes/canonicalize.js.map +1 -0
- package/dist/passes/normalize-predicate.d.ts +4 -0
- package/dist/passes/normalize-predicate.d.ts.map +1 -0
- package/dist/passes/normalize-predicate.js +57 -0
- package/dist/passes/normalize-predicate.js.map +1 -0
- package/dist/passes/normalize-shape.d.ts +4 -0
- package/dist/passes/normalize-shape.d.ts.map +1 -0
- package/dist/passes/normalize-shape.js +37 -0
- package/dist/passes/normalize-shape.js.map +1 -0
- package/dist/passes/simplify.d.ts +4 -0
- package/dist/passes/simplify.d.ts.map +1 -0
- package/dist/passes/simplify.js +49 -0
- package/dist/passes/simplify.js.map +1 -0
- package/dist/prune/conflict.d.ts +18 -0
- package/dist/prune/conflict.d.ts.map +1 -0
- package/dist/prune/conflict.js +30 -0
- package/dist/prune/conflict.js.map +1 -0
- package/dist/prune/index.d.ts +3 -0
- package/dist/prune/index.d.ts.map +1 -0
- package/dist/prune/index.js +9 -0
- package/dist/prune/index.js.map +1 -0
- package/dist/prune/prune.d.ts +11 -0
- package/dist/prune/prune.d.ts.map +1 -0
- package/dist/prune/prune.js +19 -0
- package/dist/prune/prune.js.map +1 -0
- package/dist/prune.d.ts +11 -0
- package/dist/prune.d.ts.map +1 -0
- package/dist/prune.js +19 -0
- package/dist/prune.js.map +1 -0
- package/dist/rewrite.d.ts +27 -0
- package/dist/rewrite.d.ts.map +1 -0
- package/dist/rewrite.js +62 -0
- package/dist/rewrite.js.map +1 -0
- package/dist/rules/experimental/hoist-common-predicates-from-or.d.ts +5 -0
- package/dist/rules/experimental/hoist-common-predicates-from-or.d.ts.map +1 -0
- package/dist/rules/experimental/hoist-common-predicates-from-or.js +153 -0
- package/dist/rules/experimental/hoist-common-predicates-from-or.js.map +1 -0
- package/dist/rules/logical/detect-common-predicates-in-or.d.ts +5 -0
- package/dist/rules/logical/detect-common-predicates-in-or.d.ts.map +1 -0
- package/dist/rules/logical/detect-common-predicates-in-or.js +82 -0
- package/dist/rules/logical/detect-common-predicates-in-or.js.map +1 -0
- package/dist/rules/predicate/collapse-contradictions.d.ts +5 -0
- package/dist/rules/predicate/collapse-contradictions.d.ts.map +1 -0
- package/dist/rules/predicate/collapse-contradictions.js +45 -0
- package/dist/rules/predicate/collapse-contradictions.js.map +1 -0
- package/dist/rules/predicate/dedupe-same-field-predicates.d.ts +5 -0
- package/dist/rules/predicate/dedupe-same-field-predicates.d.ts.map +1 -0
- package/dist/rules/predicate/dedupe-same-field-predicates.js +33 -0
- package/dist/rules/predicate/dedupe-same-field-predicates.js.map +1 -0
- package/dist/rules/predicate/merge-comparable-predicates.d.ts +5 -0
- package/dist/rules/predicate/merge-comparable-predicates.d.ts.map +1 -0
- package/dist/rules/predicate/merge-comparable-predicates.js +30 -0
- package/dist/rules/predicate/merge-comparable-predicates.js.map +1 -0
- package/dist/rules/predicate/merge-predicates-internal.d.ts +7 -0
- package/dist/rules/predicate/merge-predicates-internal.d.ts.map +1 -0
- package/dist/rules/predicate/merge-predicates-internal.js +186 -0
- package/dist/rules/predicate/merge-predicates-internal.js.map +1 -0
- package/dist/rules/shape/collapse-single-child-logical.d.ts +5 -0
- package/dist/rules/shape/collapse-single-child-logical.d.ts.map +1 -0
- package/dist/rules/shape/collapse-single-child-logical.js +20 -0
- package/dist/rules/shape/collapse-single-child-logical.js.map +1 -0
- package/dist/rules/shape/dedupe-logical-children.d.ts +6 -0
- package/dist/rules/shape/dedupe-logical-children.d.ts.map +1 -0
- package/dist/rules/shape/dedupe-logical-children.js +37 -0
- package/dist/rules/shape/dedupe-logical-children.js.map +1 -0
- package/dist/rules/shape/flatten-logical.d.ts +6 -0
- package/dist/rules/shape/flatten-logical.d.ts.map +1 -0
- package/dist/rules/shape/flatten-logical.js +37 -0
- package/dist/rules/shape/flatten-logical.js.map +1 -0
- package/dist/rules/shape/remove-empty-logical.d.ts +5 -0
- package/dist/rules/shape/remove-empty-logical.d.ts.map +1 -0
- package/dist/rules/shape/remove-empty-logical.js +21 -0
- package/dist/rules/shape/remove-empty-logical.js.map +1 -0
- package/dist/types.d.ts +70 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +8 -0
- package/dist/types.js.map +1 -0
- package/dist/utils/compare-values.d.ts +6 -0
- package/dist/utils/compare-values.d.ts.map +1 -0
- package/dist/utils/compare-values.js +31 -0
- package/dist/utils/compare-values.js.map +1 -0
- package/dist/utils/deep-equal.d.ts +2 -0
- package/dist/utils/deep-equal.d.ts.map +1 -0
- package/dist/utils/deep-equal.js +30 -0
- package/dist/utils/deep-equal.js.map +1 -0
- package/dist/utils/is-opaque.d.ts +4 -0
- package/dist/utils/is-opaque.d.ts.map +1 -0
- package/dist/utils/is-opaque.js +42 -0
- package/dist/utils/is-opaque.js.map +1 -0
- package/dist/utils/stable-sort.d.ts +2 -0
- package/dist/utils/stable-sort.d.ts.map +1 -0
- package/dist/utils/stable-sort.js +16 -0
- package/dist/utils/stable-sort.js.map +1 -0
- package/package.json +51 -0
|
@@ -0,0 +1,128 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.simplify = simplify;
|
|
4
|
+
const builders_1 = require("../ast/builders");
|
|
5
|
+
const guards_1 = require("../ast/guards");
|
|
6
|
+
const constraint_propagation_1 = require("./constraint-propagation");
|
|
7
|
+
/**
|
|
8
|
+
* simplify(AST → AST)编排:
|
|
9
|
+
*
|
|
10
|
+
* 1. **约束传播**(`constraint-propagation`):`$and` 内 sibling context、父级与子级 FieldNode 的
|
|
11
|
+
* 冲突剪枝与 tighten;tighten 仅作用于 `conditions.ts` 中声明的支持操作符,其余条件原样保留,
|
|
12
|
+
* 不改变 Mongo 语义。
|
|
13
|
+
* 2. **逻辑化简**:true/false 传播、AND 吸收 true、OR 吸收 false、AND flatten、$nor 结构化简。
|
|
14
|
+
*/
|
|
15
|
+
function simplify(ast) {
|
|
16
|
+
const context = new Map();
|
|
17
|
+
return simplifyNode(ast, context);
|
|
18
|
+
}
|
|
19
|
+
function simplifyNode(node, context) {
|
|
20
|
+
if ((0, guards_1.isTrueNode)(node) || (0, guards_1.isFalseNode)(node)) {
|
|
21
|
+
return node;
|
|
22
|
+
}
|
|
23
|
+
if ((0, guards_1.isFieldNode)(node)) {
|
|
24
|
+
return (0, constraint_propagation_1.simplifyFieldAgainstContext)(node, context);
|
|
25
|
+
}
|
|
26
|
+
if ((0, guards_1.isLogicalNode)(node)) {
|
|
27
|
+
switch (node.op) {
|
|
28
|
+
case "$and":
|
|
29
|
+
return simplifyAnd(node, context);
|
|
30
|
+
case "$or":
|
|
31
|
+
return simplifyOr(node, context);
|
|
32
|
+
case "$nor":
|
|
33
|
+
return simplifyNor(node, context);
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
return node;
|
|
37
|
+
}
|
|
38
|
+
function simplifyAnd(node, context) {
|
|
39
|
+
const layerAll = (0, constraint_propagation_1.collectAndLayerFieldConditions)(node);
|
|
40
|
+
const resultChildren = [];
|
|
41
|
+
for (const child of node.children) {
|
|
42
|
+
const childContext = (0, guards_1.isFieldNode)(child)
|
|
43
|
+
? (0, constraint_propagation_1.buildSiblingContext)(context, layerAll, child)
|
|
44
|
+
: (0, constraint_propagation_1.buildLayerContext)(context, layerAll);
|
|
45
|
+
const simplified = simplifyNode(child, childContext);
|
|
46
|
+
if ((0, guards_1.isFalseNode)(simplified)) {
|
|
47
|
+
return builders_1.ASTNodeBuilder.falseNode();
|
|
48
|
+
}
|
|
49
|
+
if ((0, guards_1.isTrueNode)(simplified)) {
|
|
50
|
+
continue;
|
|
51
|
+
}
|
|
52
|
+
if ((0, guards_1.isFieldNode)(simplified)) {
|
|
53
|
+
resultChildren.push(simplified);
|
|
54
|
+
continue;
|
|
55
|
+
}
|
|
56
|
+
if ((0, guards_1.isLogicalNode)(simplified) && simplified.op === "$and") {
|
|
57
|
+
resultChildren.push(...simplified.children);
|
|
58
|
+
continue;
|
|
59
|
+
}
|
|
60
|
+
resultChildren.push(simplified);
|
|
61
|
+
}
|
|
62
|
+
if (resultChildren.length === 0) {
|
|
63
|
+
return builders_1.ASTNodeBuilder.trueNode();
|
|
64
|
+
}
|
|
65
|
+
if (resultChildren.length === 1) {
|
|
66
|
+
return resultChildren[0];
|
|
67
|
+
}
|
|
68
|
+
return builders_1.ASTNodeBuilder.logical("$and", resultChildren);
|
|
69
|
+
}
|
|
70
|
+
function simplifyOr(node, context) {
|
|
71
|
+
const resultChildren = [];
|
|
72
|
+
for (const child of node.children) {
|
|
73
|
+
const simplified = simplifyNode(child, context);
|
|
74
|
+
if ((0, guards_1.isTrueNode)(simplified)) {
|
|
75
|
+
return builders_1.ASTNodeBuilder.trueNode();
|
|
76
|
+
}
|
|
77
|
+
if ((0, guards_1.isFalseNode)(simplified)) {
|
|
78
|
+
continue;
|
|
79
|
+
}
|
|
80
|
+
resultChildren.push(simplified);
|
|
81
|
+
}
|
|
82
|
+
if (resultChildren.length === 0) {
|
|
83
|
+
return builders_1.ASTNodeBuilder.falseNode();
|
|
84
|
+
}
|
|
85
|
+
if (resultChildren.length === 1) {
|
|
86
|
+
return resultChildren[0];
|
|
87
|
+
}
|
|
88
|
+
return builders_1.ASTNodeBuilder.logical("$or", resultChildren);
|
|
89
|
+
}
|
|
90
|
+
/**
|
|
91
|
+
* $nor 子句:空 context 做结构化简,父 context 判断是否可剪枝;恒 true 子句使 NOR 为 false。
|
|
92
|
+
*/
|
|
93
|
+
function simplifyNorChildrenWithContext(children, context) {
|
|
94
|
+
const kept = [];
|
|
95
|
+
const emptyContext = new Map();
|
|
96
|
+
for (const child of children) {
|
|
97
|
+
const childNoCtx = simplifyNode(child, emptyContext);
|
|
98
|
+
if ((0, guards_1.isFalseNode)(childNoCtx)) {
|
|
99
|
+
continue;
|
|
100
|
+
}
|
|
101
|
+
const childWithCtx = simplifyNode(child, context);
|
|
102
|
+
if ((0, guards_1.isFalseNode)(childWithCtx)) {
|
|
103
|
+
continue;
|
|
104
|
+
}
|
|
105
|
+
// 子句在外层 $and 上下文中可化简(如与 sibling 字段矛盾)时必须保留化简结果,不能推入
|
|
106
|
+
// childNoCtx;否则首轮输出仍含冗余支,再 parse 后 sibling 顺序/合并变化会导致二轮多剪一枝,破坏幂等。
|
|
107
|
+
if ((0, guards_1.isTrueNode)(childNoCtx) || (0, guards_1.isTrueNode)(childWithCtx)) {
|
|
108
|
+
return { kept: [], hasAlwaysTrue: true };
|
|
109
|
+
}
|
|
110
|
+
kept.push(childWithCtx);
|
|
111
|
+
}
|
|
112
|
+
return { kept, hasAlwaysTrue: false };
|
|
113
|
+
}
|
|
114
|
+
function simplifyNor(node, context) {
|
|
115
|
+
const { kept, hasAlwaysTrue } = simplifyNorChildrenWithContext(node.children, context);
|
|
116
|
+
if (hasAlwaysTrue) {
|
|
117
|
+
return builders_1.ASTNodeBuilder.falseNode();
|
|
118
|
+
}
|
|
119
|
+
if (kept.length === 0) {
|
|
120
|
+
return builders_1.ASTNodeBuilder.trueNode();
|
|
121
|
+
}
|
|
122
|
+
if (kept.length === 1) {
|
|
123
|
+
return builders_1.ASTNodeBuilder.logical("$nor", [kept[0]]);
|
|
124
|
+
}
|
|
125
|
+
// 扁平 $nor 子句列表(与 $nor:[{$or:[...]}] 语义等价);标准形采用扁平形以利于一步幂等
|
|
126
|
+
return builders_1.ASTNodeBuilder.logical("$nor", kept);
|
|
127
|
+
}
|
|
128
|
+
//# sourceMappingURL=simplify.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"simplify.js","sourceRoot":"","sources":["../../src/core/simplify.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
import type { SelectorAST } from "../ast/types";
|
|
2
|
+
/**
|
|
3
|
+
* 为 canonical form 下的子节点排序生成稳定、无语义含义的字符串键(仅用于 $or / $nor 子句重排)。
|
|
4
|
+
* 不用于语义比较;同一 AST 结构应产生同一键。
|
|
5
|
+
*/
|
|
6
|
+
export declare function stableStructuralSortKey(node: SelectorAST): string;
|
|
7
|
+
//# sourceMappingURL=stable-structural-key.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"stable-structural-key.d.ts","sourceRoot":"","sources":["../../src/core/stable-structural-key.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAkB,WAAW,EAAE,MAAM,cAAc,CAAC;AAEhE;;;GAGG;AACH,wBAAgB,uBAAuB,CAAC,IAAI,EAAE,WAAW,GAAG,MAAM,CAejE"}
|
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.stableStructuralSortKey = stableStructuralSortKey;
|
|
4
|
+
/**
|
|
5
|
+
* 为 canonical form 下的子节点排序生成稳定、无语义含义的字符串键(仅用于 $or / $nor 子句重排)。
|
|
6
|
+
* 不用于语义比较;同一 AST 结构应产生同一键。
|
|
7
|
+
*/
|
|
8
|
+
function stableStructuralSortKey(node) {
|
|
9
|
+
switch (node.type) {
|
|
10
|
+
case "true":
|
|
11
|
+
return "0:true";
|
|
12
|
+
case "false":
|
|
13
|
+
return "1:false";
|
|
14
|
+
case "field":
|
|
15
|
+
return `2:field:${node.field}:${stableFieldConditionsKey(node.conditions)}`;
|
|
16
|
+
case "logical": {
|
|
17
|
+
const childKeys = node.children.map(stableStructuralSortKey).sort();
|
|
18
|
+
return `3:log:${node.op}(${childKeys.join("\u001f")})`;
|
|
19
|
+
}
|
|
20
|
+
default:
|
|
21
|
+
return "9:unknown";
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
function stableFieldConditionsKey(conditions) {
|
|
25
|
+
const parts = conditions.map((c) => {
|
|
26
|
+
const v = serializeValueForSort(c.value);
|
|
27
|
+
return `${c.op}\u0000${v}`;
|
|
28
|
+
});
|
|
29
|
+
parts.sort();
|
|
30
|
+
return parts.join("\u001f");
|
|
31
|
+
}
|
|
32
|
+
function serializeValueForSort(value) {
|
|
33
|
+
if (value === undefined) {
|
|
34
|
+
return "u";
|
|
35
|
+
}
|
|
36
|
+
if (value === null) {
|
|
37
|
+
return "n:null";
|
|
38
|
+
}
|
|
39
|
+
if (typeof value === "number") {
|
|
40
|
+
if (Object.is(value, -0)) {
|
|
41
|
+
return "num:-0";
|
|
42
|
+
}
|
|
43
|
+
if (!Number.isFinite(value)) {
|
|
44
|
+
return `num:${String(value)}`;
|
|
45
|
+
}
|
|
46
|
+
return `num:${value}`;
|
|
47
|
+
}
|
|
48
|
+
if (typeof value === "boolean") {
|
|
49
|
+
return `bool:${value}`;
|
|
50
|
+
}
|
|
51
|
+
if (typeof value === "string") {
|
|
52
|
+
return `str:${JSON.stringify(value)}`;
|
|
53
|
+
}
|
|
54
|
+
if (value instanceof Date) {
|
|
55
|
+
return `date:${value.toISOString()}`;
|
|
56
|
+
}
|
|
57
|
+
if (value instanceof RegExp) {
|
|
58
|
+
return `re:${value.source}\u0000${value.flags}`;
|
|
59
|
+
}
|
|
60
|
+
if (Array.isArray(value)) {
|
|
61
|
+
return `arr:[${value.map(serializeValueForSort).join("\u001f")}]`;
|
|
62
|
+
}
|
|
63
|
+
if (typeof value === "object") {
|
|
64
|
+
const o = value;
|
|
65
|
+
const keys = Object.keys(o).sort();
|
|
66
|
+
const inner = keys.map((k) => `${JSON.stringify(k)}:${serializeValueForSort(o[k])}`).join("\u001f");
|
|
67
|
+
return `obj:{${inner}}`;
|
|
68
|
+
}
|
|
69
|
+
return `x:${String(value)}`;
|
|
70
|
+
}
|
|
71
|
+
//# sourceMappingURL=stable-structural-key.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"stable-structural-key.js","sourceRoot":"","sources":["../../src/core/stable-structural-key.ts"],"names":[],"mappings":";;AAMA,0DAeC;AAnBD;;;GAGG;AACH,SAAgB,uBAAuB,CAAC,IAAiB;IACrD,QAAQ,IAAI,CAAC,IAAI,EAAE,CAAC;QAChB,KAAK,MAAM;YACP,OAAO,QAAQ,CAAC;QACpB,KAAK,OAAO;YACR,OAAO,SAAS,CAAC;QACrB,KAAK,OAAO;YACR,OAAO,WAAW,IAAI,CAAC,KAAK,IAAI,wBAAwB,CAAC,IAAI,CAAC,UAAU,CAAC,EAAE,CAAC;QAChF,KAAK,SAAS,CAAC,CAAC,CAAC;YACb,MAAM,SAAS,GAAG,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,uBAAuB,CAAC,CAAC,IAAI,EAAE,CAAC;YACpE,OAAO,SAAS,IAAI,CAAC,EAAE,IAAI,SAAS,CAAC,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC;QAC3D,CAAC;QACD;YACI,OAAO,WAAW,CAAC;IAC3B,CAAC;AACL,CAAC;AAED,SAAS,wBAAwB,CAAC,UAA4B;IAC1D,MAAM,KAAK,GAAG,UAAU,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE;QAC/B,MAAM,CAAC,GAAG,qBAAqB,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC;QACzC,OAAO,GAAG,CAAC,CAAC,EAAE,SAAS,CAAC,EAAE,CAAC;IAC/B,CAAC,CAAC,CAAC;IACH,KAAK,CAAC,IAAI,EAAE,CAAC;IACb,OAAO,KAAK,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;AAChC,CAAC;AAED,SAAS,qBAAqB,CAAC,KAAc;IACzC,IAAI,KAAK,KAAK,SAAS,EAAE,CAAC;QACtB,OAAO,GAAG,CAAC;IACf,CAAC;IACD,IAAI,KAAK,KAAK,IAAI,EAAE,CAAC;QACjB,OAAO,QAAQ,CAAC;IACpB,CAAC;IACD,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE,CAAC;QAC5B,IAAI,MAAM,CAAC,EAAE,CAAC,KAAK,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;YACvB,OAAO,QAAQ,CAAC;QACpB,CAAC;QACD,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,KAAK,CAAC,EAAE,CAAC;YAC1B,OAAO,OAAO,MAAM,CAAC,KAAK,CAAC,EAAE,CAAC;QAClC,CAAC;QACD,OAAO,OAAO,KAAK,EAAE,CAAC;IAC1B,CAAC;IACD,IAAI,OAAO,KAAK,KAAK,SAAS,EAAE,CAAC;QAC7B,OAAO,QAAQ,KAAK,EAAE,CAAC;IAC3B,CAAC;IACD,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE,CAAC;QAC5B,OAAO,OAAO,IAAI,CAAC,SAAS,CAAC,KAAK,CAAC,EAAE,CAAC;IAC1C,CAAC;IACD,IAAI,KAAK,YAAY,IAAI,EAAE,CAAC;QACxB,OAAO,QAAQ,KAAK,CAAC,WAAW,EAAE,EAAE,CAAC;IACzC,CAAC;IACD,IAAI,KAAK,YAAY,MAAM,EAAE,CAAC;QAC1B,OAAO,MAAM,KAAK,CAAC,MAAM,SAAS,KAAK,CAAC,KAAK,EAAE,CAAC;IACpD,CAAC;IACD,IAAI,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC;QACvB,OAAO,QAAQ,KAAK,CAAC,GAAG,CAAC,qBAAqB,CAAC,CAAC,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC;IACtE,CAAC;IACD,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE,CAAC;QAC5B,MAAM,CAAC,GAAG,KAAgC,CAAC;QAC3C,MAAM,IAAI,GAAG,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC;QACnC,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,GAAG,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC,IAAI,qBAAqB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;QACpG,OAAO,QAAQ,KAAK,GAAG,CAAC;IAC5B,CAAC;IACD,OAAO,KAAK,MAAM,CAAC,KAAK,CAAC,EAAE,CAAC;AAChC,CAAC"}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* 深度比较两个值是否相等(含 Date、ObjectId-like、数组、对象),用于去重与交集等。
|
|
3
|
+
*
|
|
4
|
+
* @param left - 任意值
|
|
5
|
+
* @param right - 任意值
|
|
6
|
+
* @returns 是否相等
|
|
7
|
+
*/
|
|
8
|
+
export declare function areValuesEqual(left: unknown, right: unknown): boolean;
|
|
9
|
+
/**
|
|
10
|
+
* 数组去重(使用 areValuesEqual 比较)。
|
|
11
|
+
*
|
|
12
|
+
* @param items - 待去重数组
|
|
13
|
+
* @returns 去重后的新数组
|
|
14
|
+
*/
|
|
15
|
+
export declare function deduplicateByValue<T>(items: T[]): T[];
|
|
16
|
+
//# sourceMappingURL=utils.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../../src/core/utils.ts"],"names":[],"mappings":"AAwCA;;;;;;GAMG;AACH,wBAAgB,cAAc,CAAC,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE,OAAO,GAAG,OAAO,CA2DrE;AAED;;;;;GAKG;AACH,wBAAgB,kBAAkB,CAAC,CAAC,EAAE,KAAK,EAAE,CAAC,EAAE,GAAG,CAAC,EAAE,CAQrD"}
|
|
@@ -0,0 +1,109 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.areValuesEqual = areValuesEqual;
|
|
4
|
+
exports.deduplicateByValue = deduplicateByValue;
|
|
5
|
+
function isPlainObject(value) {
|
|
6
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
7
|
+
}
|
|
8
|
+
function isObjectIdLike(value) {
|
|
9
|
+
if (typeof value !== "object" || value === null) {
|
|
10
|
+
return false;
|
|
11
|
+
}
|
|
12
|
+
const obj = value;
|
|
13
|
+
return obj._bsontype === "ObjectId" || typeof obj.toHexString === "function" || typeof obj.equals === "function";
|
|
14
|
+
}
|
|
15
|
+
function isEjsonObjectId(value) {
|
|
16
|
+
if (!isPlainObject(value)) {
|
|
17
|
+
return false;
|
|
18
|
+
}
|
|
19
|
+
return Object.keys(value).length === 1 && typeof value["$oid"] === "string";
|
|
20
|
+
}
|
|
21
|
+
function objectIdHex(value) {
|
|
22
|
+
if (isEjsonObjectId(value)) {
|
|
23
|
+
return value.$oid.toLowerCase();
|
|
24
|
+
}
|
|
25
|
+
if (isObjectIdLike(value) && typeof value.toHexString === "function") {
|
|
26
|
+
return value.toHexString().toLowerCase();
|
|
27
|
+
}
|
|
28
|
+
if (typeof value === "string" && /^[0-9a-f]{24}$/i.test(value)) {
|
|
29
|
+
return value.toLowerCase();
|
|
30
|
+
}
|
|
31
|
+
return undefined;
|
|
32
|
+
}
|
|
33
|
+
/**
|
|
34
|
+
* 深度比较两个值是否相等(含 Date、ObjectId-like、数组、对象),用于去重与交集等。
|
|
35
|
+
*
|
|
36
|
+
* @param left - 任意值
|
|
37
|
+
* @param right - 任意值
|
|
38
|
+
* @returns 是否相等
|
|
39
|
+
*/
|
|
40
|
+
function areValuesEqual(left, right) {
|
|
41
|
+
if (left === right) {
|
|
42
|
+
return true;
|
|
43
|
+
}
|
|
44
|
+
if (left instanceof Date && right instanceof Date) {
|
|
45
|
+
return left.getTime() === right.getTime();
|
|
46
|
+
}
|
|
47
|
+
const leftHex = objectIdHex(left);
|
|
48
|
+
const rightHex = objectIdHex(right);
|
|
49
|
+
if (leftHex !== undefined && rightHex !== undefined) {
|
|
50
|
+
return leftHex === rightHex;
|
|
51
|
+
}
|
|
52
|
+
if (isObjectIdLike(left) && isObjectIdLike(right)) {
|
|
53
|
+
if (typeof left.equals === "function") {
|
|
54
|
+
return left.equals(right);
|
|
55
|
+
}
|
|
56
|
+
if (typeof right.equals === "function") {
|
|
57
|
+
return right.equals(left);
|
|
58
|
+
}
|
|
59
|
+
if (typeof left.toHexString === "function" && typeof right.toHexString === "function") {
|
|
60
|
+
return left.toHexString() === right.toHexString();
|
|
61
|
+
}
|
|
62
|
+
return false;
|
|
63
|
+
}
|
|
64
|
+
if (Array.isArray(left) && Array.isArray(right)) {
|
|
65
|
+
if (left.length !== right.length) {
|
|
66
|
+
return false;
|
|
67
|
+
}
|
|
68
|
+
for (let i = 0; i < left.length; i += 1) {
|
|
69
|
+
if (!areValuesEqual(left[i], right[i])) {
|
|
70
|
+
return false;
|
|
71
|
+
}
|
|
72
|
+
}
|
|
73
|
+
return true;
|
|
74
|
+
}
|
|
75
|
+
if (typeof left === "object" && left !== null && typeof right === "object" && right !== null) {
|
|
76
|
+
const leftKeys = Object.keys(left).sort();
|
|
77
|
+
const rightKeys = Object.keys(right).sort();
|
|
78
|
+
if (leftKeys.length !== rightKeys.length) {
|
|
79
|
+
return false;
|
|
80
|
+
}
|
|
81
|
+
for (let i = 0; i < leftKeys.length; i += 1) {
|
|
82
|
+
if (leftKeys[i] !== rightKeys[i]) {
|
|
83
|
+
return false;
|
|
84
|
+
}
|
|
85
|
+
const key = leftKeys[i];
|
|
86
|
+
if (!areValuesEqual(left[key], right[key])) {
|
|
87
|
+
return false;
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
return true;
|
|
91
|
+
}
|
|
92
|
+
return false;
|
|
93
|
+
}
|
|
94
|
+
/**
|
|
95
|
+
* 数组去重(使用 areValuesEqual 比较)。
|
|
96
|
+
*
|
|
97
|
+
* @param items - 待去重数组
|
|
98
|
+
* @returns 去重后的新数组
|
|
99
|
+
*/
|
|
100
|
+
function deduplicateByValue(items) {
|
|
101
|
+
const result = [];
|
|
102
|
+
for (const item of items) {
|
|
103
|
+
if (!result.some((x) => areValuesEqual(x, item))) {
|
|
104
|
+
result.push(item);
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
return result;
|
|
108
|
+
}
|
|
109
|
+
//# sourceMappingURL=utils.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"utils.js","sourceRoot":"","sources":["../../src/core/utils.ts"],"names":[],"mappings":";;AA+CA,wCA2DC;AAQD,gDAQC;AAlHD,SAAS,aAAa,CAAC,KAAc;IACjC,OAAO,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,IAAI,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC;AAChF,CAAC;AAED,SAAS,cAAc,CAAC,KAAc;IAClC,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,IAAI,EAAE,CAAC;QAC9C,OAAO,KAAK,CAAC;IACjB,CAAC;IACD,MAAM,GAAG,GAAG,KAAqB,CAAC;IAClC,OAAO,GAAG,CAAC,SAAS,KAAK,UAAU,IAAI,OAAO,GAAG,CAAC,WAAW,KAAK,UAAU,IAAI,OAAO,GAAG,CAAC,MAAM,KAAK,UAAU,CAAC;AACrH,CAAC;AAED,SAAS,eAAe,CAAC,KAAc;IACnC,IAAI,CAAC,aAAa,CAAC,KAAK,CAAC,EAAE,CAAC;QACxB,OAAO,KAAK,CAAC;IACjB,CAAC;IACD,OAAO,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,MAAM,KAAK,CAAC,IAAI,OAAQ,KAAiC,CAAC,MAAM,CAAC,KAAK,QAAQ,CAAC;AAC7G,CAAC;AAED,SAAS,WAAW,CAAC,KAAc;IAC/B,IAAI,eAAe,CAAC,KAAK,CAAC,EAAE,CAAC;QACzB,OAAO,KAAK,CAAC,IAAI,CAAC,WAAW,EAAE,CAAC;IACpC,CAAC;IACD,IAAI,cAAc,CAAC,KAAK,CAAC,IAAI,OAAO,KAAK,CAAC,WAAW,KAAK,UAAU,EAAE,CAAC;QACnE,OAAO,KAAK,CAAC,WAAW,EAAE,CAAC,WAAW,EAAE,CAAC;IAC7C,CAAC;IACD,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,iBAAiB,CAAC,IAAI,CAAC,KAAK,CAAC,EAAE,CAAC;QAC7D,OAAO,KAAK,CAAC,WAAW,EAAE,CAAC;IAC/B,CAAC;IACD,OAAO,SAAS,CAAC;AACrB,CAAC;AAED;;;;;;GAMG;AACH,SAAgB,cAAc,CAAC,IAAa,EAAE,KAAc;IACxD,IAAI,IAAI,KAAK,KAAK,EAAE,CAAC;QACjB,OAAO,IAAI,CAAC;IAChB,CAAC;IAED,IAAI,IAAI,YAAY,IAAI,IAAI,KAAK,YAAY,IAAI,EAAE,CAAC;QAChD,OAAO,IAAI,CAAC,OAAO,EAAE,KAAK,KAAK,CAAC,OAAO,EAAE,CAAC;IAC9C,CAAC;IAED,MAAM,OAAO,GAAG,WAAW,CAAC,IAAI,CAAC,CAAC;IAClC,MAAM,QAAQ,GAAG,WAAW,CAAC,KAAK,CAAC,CAAC;IACpC,IAAI,OAAO,KAAK,SAAS,IAAI,QAAQ,KAAK,SAAS,EAAE,CAAC;QAClD,OAAO,OAAO,KAAK,QAAQ,CAAC;IAChC,CAAC;IAED,IAAI,cAAc,CAAC,IAAI,CAAC,IAAI,cAAc,CAAC,KAAK,CAAC,EAAE,CAAC;QAChD,IAAI,OAAO,IAAI,CAAC,MAAM,KAAK,UAAU,EAAE,CAAC;YACpC,OAAO,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;QAC9B,CAAC;QACD,IAAI,OAAO,KAAK,CAAC,MAAM,KAAK,UAAU,EAAE,CAAC;YACrC,OAAO,KAAK,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;QAC9B,CAAC;QACD,IAAI,OAAO,IAAI,CAAC,WAAW,KAAK,UAAU,IAAI,OAAO,KAAK,CAAC,WAAW,KAAK,UAAU,EAAE,CAAC;YACpF,OAAO,IAAI,CAAC,WAAW,EAAE,KAAK,KAAK,CAAC,WAAW,EAAE,CAAC;QACtD,CAAC;QACD,OAAO,KAAK,CAAC;IACjB,CAAC;IAED,IAAI,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,IAAI,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC;QAC9C,IAAI,IAAI,CAAC,MAAM,KAAK,KAAK,CAAC,MAAM,EAAE,CAAC;YAC/B,OAAO,KAAK,CAAC;QACjB,CAAC;QACD,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,IAAI,CAAC,MAAM,EAAE,CAAC,IAAI,CAAC,EAAE,CAAC;YACtC,IAAI,CAAC,cAAc,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,KAAK,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;gBACrC,OAAO,KAAK,CAAC;YACjB,CAAC;QACL,CAAC;QACD,OAAO,IAAI,CAAC;IAChB,CAAC;IAED,IAAI,OAAO,IAAI,KAAK,QAAQ,IAAI,IAAI,KAAK,IAAI,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,IAAI,EAAE,CAAC;QAC3F,MAAM,QAAQ,GAAG,MAAM,CAAC,IAAI,CAAC,IAAc,CAAC,CAAC,IAAI,EAAE,CAAC;QACpD,MAAM,SAAS,GAAG,MAAM,CAAC,IAAI,CAAC,KAAe,CAAC,CAAC,IAAI,EAAE,CAAC;QACtD,IAAI,QAAQ,CAAC,MAAM,KAAK,SAAS,CAAC,MAAM,EAAE,CAAC;YACvC,OAAO,KAAK,CAAC;QACjB,CAAC;QACD,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,QAAQ,CAAC,MAAM,EAAE,CAAC,IAAI,CAAC,EAAE,CAAC;YAC1C,IAAI,QAAQ,CAAC,CAAC,CAAC,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,CAAC;gBAC/B,OAAO,KAAK,CAAC;YACjB,CAAC;YACD,MAAM,GAAG,GAAG,QAAQ,CAAC,CAAC,CAAC,CAAC;YACxB,IAAI,CAAC,cAAc,CAAE,IAAgC,CAAC,GAAG,CAAC,EAAG,KAAiC,CAAC,GAAG,CAAC,CAAC,EAAE,CAAC;gBACnG,OAAO,KAAK,CAAC;YACjB,CAAC;QACL,CAAC;QACD,OAAO,IAAI,CAAC;IAChB,CAAC;IAED,OAAO,KAAK,CAAC;AACjB,CAAC;AAED;;;;;GAKG;AACH,SAAgB,kBAAkB,CAAI,KAAU;IAC5C,MAAM,MAAM,GAAQ,EAAE,CAAC;IACvB,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QACvB,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,cAAc,CAAC,CAAC,EAAE,IAAI,CAAC,CAAC,EAAE,CAAC;YAC/C,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACtB,CAAC;IACL,CAAC;IACD,OAAO,MAAM,CAAC;AAClB,CAAC"}
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
import type { Selector, IndexSpec } from "../common/types.js";
|
|
2
|
+
/**
|
|
3
|
+
* 阶段二:打平嵌套层级(结合律),并可选按集合索引排列条件以提升索引利用率。
|
|
4
|
+
*
|
|
5
|
+
* @param selector - 已修减的选择器(通常为 simplifySelector 的输出)
|
|
6
|
+
* @param indexSpecs - 可选,当前集合的索引列表;传入时会对 $and 等按索引键顺序排序
|
|
7
|
+
* @returns 打平后的选择器,语义不变
|
|
8
|
+
*/
|
|
9
|
+
export declare function normalizeSelector(selector: Selector, indexSpecs?: IndexSpec[]): Selector;
|
|
10
|
+
/**
|
|
11
|
+
* 对 $and 子句数组应用结合律:展平嵌套的 $and,单子节点时提升为根。
|
|
12
|
+
* 不改变语义,仅简化结构。
|
|
13
|
+
*
|
|
14
|
+
* @param andClauses - $and 子句数组(每项已递归展平)
|
|
15
|
+
* @param siblingFields - 与 $and 同层的其它字段条件(非逻辑运算符部分)
|
|
16
|
+
* @returns 合并后的选择器
|
|
17
|
+
*/
|
|
18
|
+
export declare function flattenAndClauses(andClauses: Selector[], siblingFields: Record<string, unknown>): Selector;
|
|
19
|
+
/**
|
|
20
|
+
* 对 $or 子句数组应用结合律:展平嵌套的 $or,单子节点时提升为根。
|
|
21
|
+
*
|
|
22
|
+
* @param orClauses - $or 子句数组(每项已递归展平)
|
|
23
|
+
* @param siblingFields - 与 $or 同层的其它字段条件
|
|
24
|
+
* @returns 合并后的选择器
|
|
25
|
+
*/
|
|
26
|
+
export declare function flattenOrClauses(orClauses: Selector[], siblingFields: Record<string, unknown>): Selector;
|
|
27
|
+
/**
|
|
28
|
+
* 对 $nor 子句数组应用结合律:展平嵌套的 $nor。不做「单子节点提升」以免丢失否定语义。
|
|
29
|
+
*
|
|
30
|
+
* @param norClauses - $nor 子句数组(每项已递归展平)
|
|
31
|
+
* @param siblingFields - 与 $nor 同层的其它字段条件
|
|
32
|
+
* @returns 合并后的选择器
|
|
33
|
+
*/
|
|
34
|
+
export declare function flattenNorClauses(norClauses: Selector[], siblingFields: Record<string, unknown>): Selector;
|
|
35
|
+
/**
|
|
36
|
+
* 按给定索引的键顺序排列条件(如 $and 中的字段顺序),使生成的选择器更贴近索引,利于 planner 选择。
|
|
37
|
+
*
|
|
38
|
+
* @param conditions - 扁平条件列表(如 AtomicCondition[] 或字段名列表)
|
|
39
|
+
* @param indexSpec - 可选,用于排序的索引;未传则保持原序
|
|
40
|
+
* @returns 按索引键顺序排列后的条件
|
|
41
|
+
*/
|
|
42
|
+
export declare function sortConditionsByIndexKeys<T>(conditions: T[], indexSpec?: IndexSpec): T[];
|
|
43
|
+
//# sourceMappingURL=flatten.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"flatten.d.ts","sourceRoot":"","sources":["../../src/flatten/flatten.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,QAAQ,EAAE,SAAS,EAAE,MAAM,oBAAoB,CAAC;AAE9D;;;;;;GAMG;AACH,wBAAgB,iBAAiB,CAC/B,QAAQ,EAAE,QAAQ,EAClB,UAAU,CAAC,EAAE,SAAS,EAAE,GACvB,QAAQ,CAIV;AAED;;;;;;;GAOG;AACH,wBAAgB,iBAAiB,CAC/B,UAAU,EAAE,QAAQ,EAAE,EACtB,aAAa,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GACrC,QAAQ,CAIV;AAED;;;;;;GAMG;AACH,wBAAgB,gBAAgB,CAC9B,SAAS,EAAE,QAAQ,EAAE,EACrB,aAAa,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GACrC,QAAQ,CAIV;AAED;;;;;;GAMG;AACH,wBAAgB,iBAAiB,CAC/B,UAAU,EAAE,QAAQ,EAAE,EACtB,aAAa,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GACrC,QAAQ,CAIV;AAED;;;;;;GAMG;AACH,wBAAgB,yBAAyB,CAAC,CAAC,EACzC,UAAU,EAAE,CAAC,EAAE,EACf,SAAS,CAAC,EAAE,SAAS,GACpB,CAAC,EAAE,CAGL"}
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.normalizeSelector = normalizeSelector;
|
|
4
|
+
exports.flattenAndClauses = flattenAndClauses;
|
|
5
|
+
exports.flattenOrClauses = flattenOrClauses;
|
|
6
|
+
exports.flattenNorClauses = flattenNorClauses;
|
|
7
|
+
exports.sortConditionsByIndexKeys = sortConditionsByIndexKeys;
|
|
8
|
+
/**
|
|
9
|
+
* 阶段二:打平嵌套层级(结合律),并可选按集合索引排列条件以提升索引利用率。
|
|
10
|
+
*
|
|
11
|
+
* @param selector - 已修减的选择器(通常为 simplifySelector 的输出)
|
|
12
|
+
* @param indexSpecs - 可选,当前集合的索引列表;传入时会对 $and 等按索引键顺序排序
|
|
13
|
+
* @returns 打平后的选择器,语义不变
|
|
14
|
+
*/
|
|
15
|
+
function normalizeSelector(selector, indexSpecs) {
|
|
16
|
+
void indexSpecs;
|
|
17
|
+
// TODO: 递归应用 flattenAndClauses / flattenOrClauses / flattenNorClauses,再按 indexSpecs 排序
|
|
18
|
+
return selector;
|
|
19
|
+
}
|
|
20
|
+
/**
|
|
21
|
+
* 对 $and 子句数组应用结合律:展平嵌套的 $and,单子节点时提升为根。
|
|
22
|
+
* 不改变语义,仅简化结构。
|
|
23
|
+
*
|
|
24
|
+
* @param andClauses - $and 子句数组(每项已递归展平)
|
|
25
|
+
* @param siblingFields - 与 $and 同层的其它字段条件(非逻辑运算符部分)
|
|
26
|
+
* @returns 合并后的选择器
|
|
27
|
+
*/
|
|
28
|
+
function flattenAndClauses(andClauses, siblingFields) {
|
|
29
|
+
void andClauses;
|
|
30
|
+
void siblingFields;
|
|
31
|
+
return {};
|
|
32
|
+
}
|
|
33
|
+
/**
|
|
34
|
+
* 对 $or 子句数组应用结合律:展平嵌套的 $or,单子节点时提升为根。
|
|
35
|
+
*
|
|
36
|
+
* @param orClauses - $or 子句数组(每项已递归展平)
|
|
37
|
+
* @param siblingFields - 与 $or 同层的其它字段条件
|
|
38
|
+
* @returns 合并后的选择器
|
|
39
|
+
*/
|
|
40
|
+
function flattenOrClauses(orClauses, siblingFields) {
|
|
41
|
+
void orClauses;
|
|
42
|
+
void siblingFields;
|
|
43
|
+
return {};
|
|
44
|
+
}
|
|
45
|
+
/**
|
|
46
|
+
* 对 $nor 子句数组应用结合律:展平嵌套的 $nor。不做「单子节点提升」以免丢失否定语义。
|
|
47
|
+
*
|
|
48
|
+
* @param norClauses - $nor 子句数组(每项已递归展平)
|
|
49
|
+
* @param siblingFields - 与 $nor 同层的其它字段条件
|
|
50
|
+
* @returns 合并后的选择器
|
|
51
|
+
*/
|
|
52
|
+
function flattenNorClauses(norClauses, siblingFields) {
|
|
53
|
+
void norClauses;
|
|
54
|
+
void siblingFields;
|
|
55
|
+
return {};
|
|
56
|
+
}
|
|
57
|
+
/**
|
|
58
|
+
* 按给定索引的键顺序排列条件(如 $and 中的字段顺序),使生成的选择器更贴近索引,利于 planner 选择。
|
|
59
|
+
*
|
|
60
|
+
* @param conditions - 扁平条件列表(如 AtomicCondition[] 或字段名列表)
|
|
61
|
+
* @param indexSpec - 可选,用于排序的索引;未传则保持原序
|
|
62
|
+
* @returns 按索引键顺序排列后的条件
|
|
63
|
+
*/
|
|
64
|
+
function sortConditionsByIndexKeys(conditions, indexSpec) {
|
|
65
|
+
void indexSpec;
|
|
66
|
+
return conditions;
|
|
67
|
+
}
|
|
68
|
+
//# sourceMappingURL=flatten.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"flatten.js","sourceRoot":"","sources":["../../src/flatten/flatten.ts"],"names":[],"mappings":";;AASA,8CAOC;AAUD,8CAOC;AASD,4CAOC;AASD,8CAOC;AASD,8DAMC;AA9ED;;;;;;GAMG;AACH,SAAgB,iBAAiB,CAC/B,QAAkB,EAClB,UAAwB;IAExB,KAAK,UAAU,CAAC;IAChB,uFAAuF;IACvF,OAAO,QAAQ,CAAC;AAClB,CAAC;AAED;;;;;;;GAOG;AACH,SAAgB,iBAAiB,CAC/B,UAAsB,EACtB,aAAsC;IAEtC,KAAK,UAAU,CAAC;IAChB,KAAK,aAAa,CAAC;IACnB,OAAO,EAAE,CAAC;AACZ,CAAC;AAED;;;;;;GAMG;AACH,SAAgB,gBAAgB,CAC9B,SAAqB,EACrB,aAAsC;IAEtC,KAAK,SAAS,CAAC;IACf,KAAK,aAAa,CAAC;IACnB,OAAO,EAAE,CAAC;AACZ,CAAC;AAED;;;;;;GAMG;AACH,SAAgB,iBAAiB,CAC/B,UAAsB,EACtB,aAAsC;IAEtC,KAAK,UAAU,CAAC;IAChB,KAAK,aAAa,CAAC;IACnB,OAAO,EAAE,CAAC;AACZ,CAAC;AAED;;;;;;GAMG;AACH,SAAgB,yBAAyB,CACvC,UAAe,EACf,SAAqB;IAErB,KAAK,SAAS,CAAC;IACf,OAAO,UAAU,CAAC;AACpB,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/flatten/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,iBAAiB,EACjB,iBAAiB,EACjB,gBAAgB,EAChB,iBAAiB,EACjB,yBAAyB,GAC1B,MAAM,cAAc,CAAC"}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.sortConditionsByIndexKeys = exports.flattenNorClauses = exports.flattenOrClauses = exports.flattenAndClauses = exports.normalizeSelector = void 0;
|
|
4
|
+
var flatten_js_1 = require("./flatten.js");
|
|
5
|
+
Object.defineProperty(exports, "normalizeSelector", { enumerable: true, get: function () { return flatten_js_1.normalizeSelector; } });
|
|
6
|
+
Object.defineProperty(exports, "flattenAndClauses", { enumerable: true, get: function () { return flatten_js_1.flattenAndClauses; } });
|
|
7
|
+
Object.defineProperty(exports, "flattenOrClauses", { enumerable: true, get: function () { return flatten_js_1.flattenOrClauses; } });
|
|
8
|
+
Object.defineProperty(exports, "flattenNorClauses", { enumerable: true, get: function () { return flatten_js_1.flattenNorClauses; } });
|
|
9
|
+
Object.defineProperty(exports, "sortConditionsByIndexKeys", { enumerable: true, get: function () { return flatten_js_1.sortConditionsByIndexKeys; } });
|
|
10
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/flatten/index.ts"],"names":[],"mappings":";;;AAAA,2CAMsB;AALpB,+GAAA,iBAAiB,OAAA;AACjB,+GAAA,iBAAiB,OAAA;AACjB,8GAAA,gBAAgB,OAAA;AAChB,+GAAA,iBAAiB,OAAA;AACjB,uHAAA,yBAAyB,OAAA"}
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
import type { FilterQuery, IndexSpec } from "./types";
|
|
2
|
+
/**
|
|
3
|
+
* 阶段二:打平嵌套层级(结合律),并可选按集合索引排列条件以提升索引利用率。
|
|
4
|
+
*
|
|
5
|
+
* @param query - 已修减的查询(通常为 pruneSelector 的输出)
|
|
6
|
+
* @param indexSpecs - 可选,当前集合的索引列表;传入时会对 $and 等按索引键顺序排序
|
|
7
|
+
* @returns 打平后的查询,语义不变
|
|
8
|
+
*/
|
|
9
|
+
export declare function flattenSelector(query: FilterQuery, indexSpecs?: IndexSpec[]): FilterQuery;
|
|
10
|
+
/**
|
|
11
|
+
* 对 $and 数组应用结合律:展平嵌套的 $and,单子节点时提升为根。
|
|
12
|
+
* 不改变语义,仅简化结构。
|
|
13
|
+
*
|
|
14
|
+
* @param andClauses - $and 子句数组(每项已递归 flatten)
|
|
15
|
+
* @param baseSelector - 与 $and 同层的其它字段条件
|
|
16
|
+
* @returns 合并后的 selector
|
|
17
|
+
*/
|
|
18
|
+
export declare function reduceAnd(andClauses: FilterQuery[], baseSelector: Record<string, unknown>): FilterQuery;
|
|
19
|
+
/**
|
|
20
|
+
* 对 $or 数组应用结合律:展平嵌套的 $or,单子节点时提升为根。
|
|
21
|
+
*
|
|
22
|
+
* @param orClauses - $or 子句数组(每项已递归 flatten)
|
|
23
|
+
* @param baseSelector - 与 $or 同层的其它字段条件
|
|
24
|
+
* @returns 合并后的 selector
|
|
25
|
+
*/
|
|
26
|
+
export declare function reduceOr(orClauses: FilterQuery[], baseSelector: Record<string, unknown>): FilterQuery;
|
|
27
|
+
/**
|
|
28
|
+
* 对 $nor 数组应用结合律:展平嵌套的 $nor。不做「单子节点提升」以免丢失否定语义。
|
|
29
|
+
*
|
|
30
|
+
* @param norClauses - $nor 子句数组(每项已递归 flatten)
|
|
31
|
+
* @param baseSelector - 与 $nor 同层的其它字段条件
|
|
32
|
+
* @returns 合并后的 selector
|
|
33
|
+
*/
|
|
34
|
+
export declare function reduceNor(norClauses: FilterQuery[], baseSelector: Record<string, unknown>): FilterQuery;
|
|
35
|
+
/**
|
|
36
|
+
* 按给定索引的键顺序排列条件(如 $and 中的字段顺序),使生成的 selector 更贴近索引,利于 planner 选择。
|
|
37
|
+
*
|
|
38
|
+
* @param conditions - 扁平条件列表(如 ParsedOp[] 或字段名列表)
|
|
39
|
+
* @param indexSpec - 可选,用于排序的索引;未传则保持原序
|
|
40
|
+
* @returns 按索引键顺序排列后的条件
|
|
41
|
+
*/
|
|
42
|
+
export declare function orderConditionsByIndex<T>(conditions: T[], indexSpec?: IndexSpec): T[];
|
|
43
|
+
//# sourceMappingURL=flatten.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"flatten.d.ts","sourceRoot":"","sources":["../src/flatten.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,SAAS,EAAE,MAAM,SAAS,CAAC;AAEtD;;;;;;GAMG;AACH,wBAAgB,eAAe,CAC7B,KAAK,EAAE,WAAW,EAClB,UAAU,CAAC,EAAE,SAAS,EAAE,GACvB,WAAW,CAIb;AAED;;;;;;;GAOG;AACH,wBAAgB,SAAS,CACvB,UAAU,EAAE,WAAW,EAAE,EACzB,YAAY,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GACpC,WAAW,CAIb;AAED;;;;;;GAMG;AACH,wBAAgB,QAAQ,CACtB,SAAS,EAAE,WAAW,EAAE,EACxB,YAAY,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GACpC,WAAW,CAIb;AAED;;;;;;GAMG;AACH,wBAAgB,SAAS,CACvB,UAAU,EAAE,WAAW,EAAE,EACzB,YAAY,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GACpC,WAAW,CAIb;AAED;;;;;;GAMG;AACH,wBAAgB,sBAAsB,CAAC,CAAC,EACtC,UAAU,EAAE,CAAC,EAAE,EACf,SAAS,CAAC,EAAE,SAAS,GACpB,CAAC,EAAE,CAGL"}
|
package/dist/flatten.js
ADDED
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.flattenSelector = flattenSelector;
|
|
4
|
+
exports.reduceAnd = reduceAnd;
|
|
5
|
+
exports.reduceOr = reduceOr;
|
|
6
|
+
exports.reduceNor = reduceNor;
|
|
7
|
+
exports.orderConditionsByIndex = orderConditionsByIndex;
|
|
8
|
+
/**
|
|
9
|
+
* 阶段二:打平嵌套层级(结合律),并可选按集合索引排列条件以提升索引利用率。
|
|
10
|
+
*
|
|
11
|
+
* @param query - 已修减的查询(通常为 pruneSelector 的输出)
|
|
12
|
+
* @param indexSpecs - 可选,当前集合的索引列表;传入时会对 $and 等按索引键顺序排序
|
|
13
|
+
* @returns 打平后的查询,语义不变
|
|
14
|
+
*/
|
|
15
|
+
function flattenSelector(query, indexSpecs) {
|
|
16
|
+
void indexSpecs;
|
|
17
|
+
// TODO: 递归应用 reduceAnd / reduceOr / reduceNor,再按 indexSpecs 排序
|
|
18
|
+
return query;
|
|
19
|
+
}
|
|
20
|
+
/**
|
|
21
|
+
* 对 $and 数组应用结合律:展平嵌套的 $and,单子节点时提升为根。
|
|
22
|
+
* 不改变语义,仅简化结构。
|
|
23
|
+
*
|
|
24
|
+
* @param andClauses - $and 子句数组(每项已递归 flatten)
|
|
25
|
+
* @param baseSelector - 与 $and 同层的其它字段条件
|
|
26
|
+
* @returns 合并后的 selector
|
|
27
|
+
*/
|
|
28
|
+
function reduceAnd(andClauses, baseSelector) {
|
|
29
|
+
void andClauses;
|
|
30
|
+
void baseSelector;
|
|
31
|
+
return {};
|
|
32
|
+
}
|
|
33
|
+
/**
|
|
34
|
+
* 对 $or 数组应用结合律:展平嵌套的 $or,单子节点时提升为根。
|
|
35
|
+
*
|
|
36
|
+
* @param orClauses - $or 子句数组(每项已递归 flatten)
|
|
37
|
+
* @param baseSelector - 与 $or 同层的其它字段条件
|
|
38
|
+
* @returns 合并后的 selector
|
|
39
|
+
*/
|
|
40
|
+
function reduceOr(orClauses, baseSelector) {
|
|
41
|
+
void orClauses;
|
|
42
|
+
void baseSelector;
|
|
43
|
+
return {};
|
|
44
|
+
}
|
|
45
|
+
/**
|
|
46
|
+
* 对 $nor 数组应用结合律:展平嵌套的 $nor。不做「单子节点提升」以免丢失否定语义。
|
|
47
|
+
*
|
|
48
|
+
* @param norClauses - $nor 子句数组(每项已递归 flatten)
|
|
49
|
+
* @param baseSelector - 与 $nor 同层的其它字段条件
|
|
50
|
+
* @returns 合并后的 selector
|
|
51
|
+
*/
|
|
52
|
+
function reduceNor(norClauses, baseSelector) {
|
|
53
|
+
void norClauses;
|
|
54
|
+
void baseSelector;
|
|
55
|
+
return {};
|
|
56
|
+
}
|
|
57
|
+
/**
|
|
58
|
+
* 按给定索引的键顺序排列条件(如 $and 中的字段顺序),使生成的 selector 更贴近索引,利于 planner 选择。
|
|
59
|
+
*
|
|
60
|
+
* @param conditions - 扁平条件列表(如 ParsedOp[] 或字段名列表)
|
|
61
|
+
* @param indexSpec - 可选,用于排序的索引;未传则保持原序
|
|
62
|
+
* @returns 按索引键顺序排列后的条件
|
|
63
|
+
*/
|
|
64
|
+
function orderConditionsByIndex(conditions, indexSpec) {
|
|
65
|
+
void indexSpec;
|
|
66
|
+
return conditions;
|
|
67
|
+
}
|
|
68
|
+
//# sourceMappingURL=flatten.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"flatten.js","sourceRoot":"","sources":["../src/flatten.ts"],"names":[],"mappings":";;AASA,0CAOC;AAUD,8BAOC;AASD,4BAOC;AASD,8BAOC;AASD,wDAMC;AA9ED;;;;;;GAMG;AACH,SAAgB,eAAe,CAC7B,KAAkB,EAClB,UAAwB;IAExB,KAAK,UAAU,CAAC;IAChB,+DAA+D;IAC/D,OAAO,KAAK,CAAC;AACf,CAAC;AAED;;;;;;;GAOG;AACH,SAAgB,SAAS,CACvB,UAAyB,EACzB,YAAqC;IAErC,KAAK,UAAU,CAAC;IAChB,KAAK,YAAY,CAAC;IAClB,OAAO,EAAE,CAAC;AACZ,CAAC;AAED;;;;;;GAMG;AACH,SAAgB,QAAQ,CACtB,SAAwB,EACxB,YAAqC;IAErC,KAAK,SAAS,CAAC;IACf,KAAK,YAAY,CAAC;IAClB,OAAO,EAAE,CAAC;AACZ,CAAC;AAED;;;;;;GAMG;AACH,SAAgB,SAAS,CACvB,UAAyB,EACzB,YAAqC;IAErC,KAAK,UAAU,CAAC;IAChB,KAAK,YAAY,CAAC;IAClB,OAAO,EAAE,CAAC;AACZ,CAAC;AAED;;;;;;GAMG;AACH,SAAgB,sBAAsB,CACpC,UAAe,EACf,SAAqB;IAErB,KAAK,SAAS,CAAC;IACf,OAAO,UAAU,CAAC;AACpB,CAAC"}
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
export { normalizeQuery } from "./normalize";
|
|
2
|
+
export { resolveNormalizeOptions } from "./options/resolve";
|
|
3
|
+
export type { NormalizeLevel, NormalizeObserve, NormalizeOptions, NormalizeResult, NormalizeRules, NormalizeSafety, NormalizeStats, ResolvedNormalizeOptions, } from "./options/types";
|
|
4
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,cAAc,EAAE,MAAM,aAAa,CAAC;AAC7C,OAAO,EAAE,uBAAuB,EAAE,MAAM,mBAAmB,CAAC;AAC5D,YAAY,EACR,cAAc,EACd,gBAAgB,EAChB,gBAAgB,EAChB,eAAe,EACf,cAAc,EACd,eAAe,EACf,cAAc,EACd,wBAAwB,GAC3B,MAAM,iBAAiB,CAAC"}
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.resolveNormalizeOptions = exports.normalizeQuery = void 0;
|
|
4
|
+
var normalize_1 = require("./normalize");
|
|
5
|
+
Object.defineProperty(exports, "normalizeQuery", { enumerable: true, get: function () { return normalize_1.normalizeQuery; } });
|
|
6
|
+
var resolve_1 = require("./options/resolve");
|
|
7
|
+
Object.defineProperty(exports, "resolveNormalizeOptions", { enumerable: true, get: function () { return resolve_1.resolveNormalizeOptions; } });
|
|
8
|
+
//# sourceMappingURL=index.js.map
|