feat: implement mergeFilters function and enhance query object merging

- Added mergeFilters function to combine filter objects with priority handling.
- Introduced comprehensive tests for mergeFilters in permissions.spec.ts.
- Created query.spec.ts to validate query structure and expression handling.
- Enhanced error messages in query.ts for better debugging and clarity.
This commit is contained in:
dswbx
2025-10-26 21:05:11 +01:00
parent 574b37abcd
commit 0b58cadbd0
4 changed files with 196 additions and 7 deletions

View File

@@ -6,6 +6,7 @@ import type { ServerEnv } from "modules/Controller";
import type { Role } from "./Role";
import { HttpStatus } from "bknd/utils";
import type { Policy, PolicySchema } from "./Policy";
import { convert, type ObjectQuery } from "core/object/query/object-query";
export type GuardUserContext = {
role?: string | null;
@@ -294,7 +295,7 @@ export class Guard {
filter,
policies,
merge: (givenFilter: object | undefined) => {
return mergeObject(givenFilter ?? {}, filter ?? {});
return mergeFilters(givenFilter ?? {}, filter ?? {});
},
matches: (subject: object | object[], opts?: { throwOnError?: boolean }) => {
const subjects = Array.isArray(subject) ? subject : [subject];
@@ -319,3 +320,22 @@ export class Guard {
};
}
}
export function mergeFilters(base: ObjectQuery, priority: ObjectQuery) {
const base_converted = convert(base);
const priority_converted = convert(priority);
const merged = mergeObject(base_converted, priority_converted);
// in case priority filter is also contained in base's $and, merge priority in
if ("$or" in base_converted && base_converted.$or) {
const $ors = base_converted.$or as ObjectQuery;
const priority_keys = Object.keys(priority_converted);
for (const key of priority_keys) {
if (key in $ors) {
merged.$or[key] = mergeObject($ors[key], priority_converted[key]);
}
}
}
return merged;
}