assign-gingerly 0.0.74 → 0.0.76
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/DX/installForwarding.js +1 -1
- package/DX/installForwarding.ts +1 -1
- package/README.md +2 -0
- package/assignFrom.js +18 -17
- package/assignFrom.ts +23 -23
- package/assignFromAsync.js +14 -13
- package/assignFromAsync.ts +15 -15
- package/assignGingerly.js +46 -42
- package/assignGingerly.ts +131 -124
- package/assignPermissions/PermissionProcessor.js +166 -0
- package/assignPermissions/PermissionProcessor.ts +210 -0
- package/assignPermissions/isAllowedImportPath.js +2 -6
- package/assignPermissions/isAllowedImportPath.ts +3 -5
- package/assignPermissions/isAllowedUrl.js +18 -0
- package/assignPermissions/isAllowedUrl.ts +15 -0
- package/assignTentatively.js +9 -11
- package/assignTentatively.ts +11 -13
- package/beVigilant.js +1 -1
- package/beVigilant.ts +1 -1
- package/buildCSSQuery.js +1 -1
- package/buildCSSQuery.ts +1 -1
- package/eachTime.js +5 -6
- package/eachTime.ts +12 -15
- package/enhanceAll.js +3 -3
- package/enhanceAll.ts +4 -4
- package/evaluatePathWithAsyncMethods.js +12 -8
- package/evaluatePathWithAsyncMethods.ts +129 -117
- package/handlers/addEventListener.js +11 -11
- package/handlers/addEventListener.ts +12 -13
- package/handlers/lazyLoad.ts +7 -7
- package/handlers/lazyLoadSwitch.ts +3 -3
- package/handlers/manageTemplateList.js +10 -10
- package/handlers/manageTemplateList.ts +12 -12
- package/handlers/rangeSelector.ts +3 -3
- package/index.js +2 -3
- package/index.ts +2 -3
- package/inferencer/types/assign-gingerly/types.d.ts +37 -23
- package/inferencer/types/el-maker/types.d.ts +33 -0
- package/inferencer/types/scratch-box/types.d.ts +3 -0
- package/inferencer/types/truth-sourcer/types.d.ts +4 -0
- package/package.json +25 -23
- package/parseWithAttrs.js +1 -1
- package/parseWithAttrs.ts +1 -1
- package/processHandlerCommands.js +5 -7
- package/processHandlerCommands.ts +12 -15
- package/{getValues.js → resolve/getValues.js} +19 -8
- package/{getValues.ts → resolve/getValues.ts} +331 -314
- package/{resolveIdRef.js → resolve/resolveIdRef.js} +1 -1
- package/{resolveIdRef.ts → resolve/resolveIdRef.ts} +1 -1
- package/{resolveValues.ts → resolve/resolveValues.ts} +1 -1
- package/types/assign-gingerly/types.d.ts +37 -8
- package/utils/findClassPrototypeInPath.js +57 -0
- package/utils/findClassPrototypeInPath.ts +62 -0
- package/utils/isAsyncSpawn.js +20 -0
- package/utils/isAsyncSpawn.ts +17 -0
- package/assignPermissions/restrictedProps.js +0 -43
- package/assignPermissions/restrictedProps.ts +0 -53
- package/resolveAndAssignFeatures.js +0 -36
- package/resolveAndAssignFeatures.ts +0 -43
- /package/{resolveTemplate.js → resolve/resolveTemplate.js} +0 -0
- /package/{resolveTemplate.ts → resolve/resolveTemplate.ts} +0 -0
- /package/{resolveValues.js → resolve/resolveValues.js} +0 -0
package/enhanceAll.ts
CHANGED
|
@@ -18,7 +18,7 @@
|
|
|
18
18
|
|
|
19
19
|
import { isAllowedImportPath } from './assignPermissions/isAllowedImportPath.js';
|
|
20
20
|
import { findClassPrototypeInPath } from './utils/findClassPrototypeInPath.js';
|
|
21
|
-
import type {
|
|
21
|
+
import type { PermissionProcessor } from './types/assign-gingerly/types.js';
|
|
22
22
|
|
|
23
23
|
/**
|
|
24
24
|
* Configuration for a single enhancement to apply in bulk.
|
|
@@ -51,15 +51,15 @@ export interface EnhanceConfig {
|
|
|
51
51
|
export async function enhanceAll(
|
|
52
52
|
target: Element,
|
|
53
53
|
configs: EnhanceConfig[],
|
|
54
|
-
|
|
54
|
+
permissionProcessor?: PermissionProcessor
|
|
55
55
|
): Promise<void> {
|
|
56
56
|
for (const config of configs) {
|
|
57
57
|
// Validate EMC path unless cross-domain imports are explicitly permitted
|
|
58
|
-
if (!
|
|
58
|
+
if (!permissionProcessor?.crossDomainImports && !isAllowedImportPath(config.emc)) {
|
|
59
59
|
throw new Error(
|
|
60
60
|
`enhanceAll: EMC path "${config.emc}" is a cross-domain URL. ` +
|
|
61
61
|
`Only same-origin paths or import-map-covered specifiers are allowed by default. ` +
|
|
62
|
-
`Pass { crossDomainImports: true } in
|
|
62
|
+
`Pass { crossDomainImports: true } in permissionProcessor to override.`
|
|
63
63
|
);
|
|
64
64
|
}
|
|
65
65
|
|
|
@@ -10,6 +10,10 @@
|
|
|
10
10
|
* NOTE: Interaction with @each and @eachTime is not yet implemented.
|
|
11
11
|
* Deferred until a compelling use case presents itself.
|
|
12
12
|
*/
|
|
13
|
+
import { isAllowedMethod } from './assignGingerly.js';
|
|
14
|
+
function isAllowedAsyncMethod(methodName, withAsyncMethods, permissionProcessor) {
|
|
15
|
+
return withAsyncMethods.has(methodName) && !permissionProcessor?.checkRestrictedMethod(methodName);
|
|
16
|
+
}
|
|
13
17
|
/**
|
|
14
18
|
* Evaluates a path with support for both sync and async method calls.
|
|
15
19
|
* Awaits the return value of any method in the withAsyncMethods set.
|
|
@@ -21,7 +25,7 @@
|
|
|
21
25
|
* @param withAsyncMethods - Set of method names that are awaited
|
|
22
26
|
* @returns Promise resolving to the evaluation result
|
|
23
27
|
*/
|
|
24
|
-
export async function evaluatePathWithAsyncMethods(target, pathParts, value, withMethods, withAsyncMethods) {
|
|
28
|
+
export async function evaluatePathWithAsyncMethods(target, pathParts, value, withMethods, withAsyncMethods, permissionProcessor) {
|
|
25
29
|
let current = target;
|
|
26
30
|
let i = 0;
|
|
27
31
|
// Process all segments except the last one
|
|
@@ -30,12 +34,12 @@ export async function evaluatePathWithAsyncMethods(target, pathParts, value, wit
|
|
|
30
34
|
const nextPart = pathParts[i + 1];
|
|
31
35
|
// A trailing | marks a zero-argument method call: 'deref|' calls deref()
|
|
32
36
|
// without consuming the next segment. Only applies to listed method names.
|
|
33
|
-
const isZeroArgSync = part.endsWith('|') &&
|
|
34
|
-
const isZeroArgAsync = part.endsWith('|') &&
|
|
37
|
+
const isZeroArgSync = part.endsWith('|') && isAllowedMethod(part.slice(0, -1), withMethods, permissionProcessor);
|
|
38
|
+
const isZeroArgAsync = part.endsWith('|') && isAllowedAsyncMethod(part.slice(0, -1), withAsyncMethods, permissionProcessor);
|
|
35
39
|
const baseName = (isZeroArgSync || isZeroArgAsync) ? part.slice(0, -1) : part;
|
|
36
40
|
const nextIsMethod = withAsyncMethods.has(nextPart) || withMethods.has(nextPart)
|
|
37
41
|
|| (nextPart.endsWith('|') && (withAsyncMethods.has(nextPart.slice(0, -1)) || withMethods.has(nextPart.slice(0, -1))));
|
|
38
|
-
if (
|
|
42
|
+
if (isAllowedAsyncMethod(part, withAsyncMethods, permissionProcessor) || isZeroArgAsync) {
|
|
39
43
|
// Async method — call and await
|
|
40
44
|
const method = current[baseName];
|
|
41
45
|
if (typeof method === 'function') {
|
|
@@ -57,7 +61,7 @@ export async function evaluatePathWithAsyncMethods(target, pathParts, value, wit
|
|
|
57
61
|
current = current[baseName];
|
|
58
62
|
}
|
|
59
63
|
}
|
|
60
|
-
else if (
|
|
64
|
+
else if (isAllowedMethod(part, withMethods, permissionProcessor) || isZeroArgSync) {
|
|
61
65
|
// Sync method — same logic as evaluatePathWithMethods
|
|
62
66
|
const method = current[baseName];
|
|
63
67
|
if (typeof method === 'function') {
|
|
@@ -91,13 +95,13 @@ export async function evaluatePathWithAsyncMethods(target, pathParts, value, wit
|
|
|
91
95
|
// otherwise it is a literal property name (e.g. an exotic key ending in |).
|
|
92
96
|
const rawLastKey = pathParts[pathParts.length - 1];
|
|
93
97
|
const isZeroArg = rawLastKey.endsWith('|')
|
|
94
|
-
&& (
|
|
98
|
+
&& (isAllowedMethod(rawLastKey.slice(0, -1), withMethods, permissionProcessor) || isAllowedAsyncMethod(rawLastKey.slice(0, -1), withAsyncMethods, permissionProcessor));
|
|
95
99
|
const lastKey = isZeroArg ? rawLastKey.slice(0, -1) : rawLastKey;
|
|
96
100
|
return {
|
|
97
101
|
target: current,
|
|
98
102
|
lastKey,
|
|
99
|
-
isMethod:
|
|
100
|
-
isAsyncMethod:
|
|
103
|
+
isMethod: isAllowedMethod(lastKey, withMethods, permissionProcessor),
|
|
104
|
+
isAsyncMethod: isAllowedAsyncMethod(lastKey, withAsyncMethods, permissionProcessor),
|
|
101
105
|
isZeroArg
|
|
102
106
|
};
|
|
103
107
|
}
|
|
@@ -1,117 +1,129 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* evaluatePathWithAsyncMethods - Async variant of evaluatePathWithMethods.
|
|
3
|
-
*
|
|
4
|
-
* Walks a path of property accesses and method calls, awaiting any methods
|
|
5
|
-
* that are in the withAsyncMethods set before continuing the chain.
|
|
6
|
-
*
|
|
7
|
-
* This module is loaded dynamically (only when withAsyncMethods is used)
|
|
8
|
-
* to avoid adding async overhead to the synchronous path.
|
|
9
|
-
*
|
|
10
|
-
* NOTE: Interaction with @each and @eachTime is not yet implemented.
|
|
11
|
-
* Deferred until a compelling use case presents itself.
|
|
12
|
-
*/
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
1
|
+
/**
|
|
2
|
+
* evaluatePathWithAsyncMethods - Async variant of evaluatePathWithMethods.
|
|
3
|
+
*
|
|
4
|
+
* Walks a path of property accesses and method calls, awaiting any methods
|
|
5
|
+
* that are in the withAsyncMethods set before continuing the chain.
|
|
6
|
+
*
|
|
7
|
+
* This module is loaded dynamically (only when withAsyncMethods is used)
|
|
8
|
+
* to avoid adding async overhead to the synchronous path.
|
|
9
|
+
*
|
|
10
|
+
* NOTE: Interaction with @each and @eachTime is not yet implemented.
|
|
11
|
+
* Deferred until a compelling use case presents itself.
|
|
12
|
+
*/
|
|
13
|
+
|
|
14
|
+
import type { PermissionProcessor } from './types/assign-gingerly/types.js';
|
|
15
|
+
import { isAllowedMethod } from './assignGingerly.js';
|
|
16
|
+
|
|
17
|
+
export interface AsyncPathResult {
|
|
18
|
+
target: any;
|
|
19
|
+
lastKey: string;
|
|
20
|
+
isMethod: boolean;
|
|
21
|
+
isAsyncMethod: boolean;
|
|
22
|
+
isZeroArg: boolean;
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
function isAllowedAsyncMethod(
|
|
26
|
+
methodName: string,
|
|
27
|
+
withAsyncMethods: Set<string>,
|
|
28
|
+
permissionProcessor?: PermissionProcessor
|
|
29
|
+
): boolean {
|
|
30
|
+
return withAsyncMethods.has(methodName) && !permissionProcessor?.checkRestrictedMethod(methodName);
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
/**
|
|
34
|
+
* Evaluates a path with support for both sync and async method calls.
|
|
35
|
+
* Awaits the return value of any method in the withAsyncMethods set.
|
|
36
|
+
*
|
|
37
|
+
* @param target - The root object to start path evaluation from
|
|
38
|
+
* @param pathParts - Array of path segments (split from '?.' notation)
|
|
39
|
+
* @param value - The value to assign or pass as argument at the end
|
|
40
|
+
* @param withMethods - Set of method names that are called synchronously
|
|
41
|
+
* @param withAsyncMethods - Set of method names that are awaited
|
|
42
|
+
* @returns Promise resolving to the evaluation result
|
|
43
|
+
*/
|
|
44
|
+
export async function evaluatePathWithAsyncMethods(
|
|
45
|
+
target: any,
|
|
46
|
+
pathParts: string[],
|
|
47
|
+
value: any,
|
|
48
|
+
withMethods: Set<string>,
|
|
49
|
+
withAsyncMethods: Set<string>,
|
|
50
|
+
permissionProcessor?: PermissionProcessor
|
|
51
|
+
): Promise<AsyncPathResult> {
|
|
52
|
+
let current = target;
|
|
53
|
+
let i = 0;
|
|
54
|
+
|
|
55
|
+
// Process all segments except the last one
|
|
56
|
+
while (i < pathParts.length - 1) {
|
|
57
|
+
const part = pathParts[i];
|
|
58
|
+
const nextPart = pathParts[i + 1];
|
|
59
|
+
|
|
60
|
+
// A trailing | marks a zero-argument method call: 'deref|' calls deref()
|
|
61
|
+
// without consuming the next segment. Only applies to listed method names.
|
|
62
|
+
const isZeroArgSync = part.endsWith('|') && isAllowedMethod(part.slice(0, -1), withMethods, permissionProcessor);
|
|
63
|
+
const isZeroArgAsync = part.endsWith('|') && isAllowedAsyncMethod(part.slice(0, -1), withAsyncMethods, permissionProcessor);
|
|
64
|
+
const baseName = (isZeroArgSync || isZeroArgAsync) ? part.slice(0, -1) : part;
|
|
65
|
+
const nextIsMethod = withAsyncMethods.has(nextPart) || withMethods.has(nextPart)
|
|
66
|
+
|| (nextPart.endsWith('|') && (withAsyncMethods.has(nextPart.slice(0, -1)) || withMethods.has(nextPart.slice(0, -1))));
|
|
67
|
+
|
|
68
|
+
if (isAllowedAsyncMethod(part, withAsyncMethods, permissionProcessor) || isZeroArgAsync) {
|
|
69
|
+
// Async method — call and await
|
|
70
|
+
const method = current[baseName];
|
|
71
|
+
if (typeof method === 'function') {
|
|
72
|
+
if (isZeroArgAsync || nextIsMethod) {
|
|
73
|
+
// Zero-arg call — next is either a method or explicitly not an argument
|
|
74
|
+
current = await method.call(current);
|
|
75
|
+
} else {
|
|
76
|
+
// Call with next part as string arg, then await
|
|
77
|
+
current = await method.call(current, nextPart);
|
|
78
|
+
i++; // Skip next part since we consumed it as argument
|
|
79
|
+
}
|
|
80
|
+
} else {
|
|
81
|
+
// Not a function — just access property
|
|
82
|
+
if (current[baseName] === undefined || current[baseName] === null) {
|
|
83
|
+
current[baseName] = {};
|
|
84
|
+
}
|
|
85
|
+
current = current[baseName];
|
|
86
|
+
}
|
|
87
|
+
} else if (isAllowedMethod(part, withMethods, permissionProcessor) || isZeroArgSync) {
|
|
88
|
+
// Sync method — same logic as evaluatePathWithMethods
|
|
89
|
+
const method = current[baseName];
|
|
90
|
+
if (typeof method === 'function') {
|
|
91
|
+
if (isZeroArgSync || nextIsMethod) {
|
|
92
|
+
// Zero-arg call — next is either a method or explicitly not an argument
|
|
93
|
+
current = method.call(current);
|
|
94
|
+
} else {
|
|
95
|
+
// Call with next part as string arg
|
|
96
|
+
current = method.call(current, nextPart);
|
|
97
|
+
i++; // Skip next part since we consumed it as argument
|
|
98
|
+
}
|
|
99
|
+
} else {
|
|
100
|
+
if (!(baseName in current) || typeof current[baseName] !== 'object' || current[baseName] === null) {
|
|
101
|
+
current[baseName] = {};
|
|
102
|
+
}
|
|
103
|
+
current = current[baseName];
|
|
104
|
+
}
|
|
105
|
+
} else {
|
|
106
|
+
// Not a method — normal property access
|
|
107
|
+
if (!(part in current) || typeof current[part] !== 'object' || current[part] === null) {
|
|
108
|
+
current[part] = {};
|
|
109
|
+
}
|
|
110
|
+
current = current[part];
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
i++;
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
// Strip a trailing | from the last segment only when it names a listed method;
|
|
117
|
+
// otherwise it is a literal property name (e.g. an exotic key ending in |).
|
|
118
|
+
const rawLastKey = pathParts[pathParts.length - 1];
|
|
119
|
+
const isZeroArg = rawLastKey.endsWith('|')
|
|
120
|
+
&& (isAllowedMethod(rawLastKey.slice(0, -1), withMethods, permissionProcessor) || isAllowedAsyncMethod(rawLastKey.slice(0, -1), withAsyncMethods, permissionProcessor));
|
|
121
|
+
const lastKey = isZeroArg ? rawLastKey.slice(0, -1) : rawLastKey;
|
|
122
|
+
return {
|
|
123
|
+
target: current,
|
|
124
|
+
lastKey,
|
|
125
|
+
isMethod: isAllowedMethod(lastKey, withMethods, permissionProcessor),
|
|
126
|
+
isAsyncMethod: isAllowedAsyncMethod(lastKey, withAsyncMethods, permissionProcessor),
|
|
127
|
+
isZeroArg
|
|
128
|
+
};
|
|
129
|
+
}
|
|
@@ -37,7 +37,7 @@ function extractShorthand(config) {
|
|
|
37
37
|
/**
|
|
38
38
|
* Process a single AssignDispatchVector — execute all toTarget/toHost/toLHS assignments.
|
|
39
39
|
*/
|
|
40
|
-
function processVector(vector, source, target, host, lhs, inheritedOptions, useAssignFrom,
|
|
40
|
+
function processVector(vector, source, target, host, lhs, inheritedOptions, useAssignFrom, permissionProcessor) {
|
|
41
41
|
const destinations = [
|
|
42
42
|
{ key: 'toTarget', dest: target },
|
|
43
43
|
{ key: 'toHost', dest: host },
|
|
@@ -50,11 +50,11 @@ function processVector(vector, source, target, host, lhs, inheritedOptions, useA
|
|
|
50
50
|
if (useAssignFrom && source != null) {
|
|
51
51
|
// Dynamic import assignFrom on demand (fire-and-forget context, already async)
|
|
52
52
|
import('../assignFrom.js').then(({ assignFrom }) => {
|
|
53
|
-
assignFrom(dest, pattern, { from: source, ...inheritedOptions, ...vector.withOptions },
|
|
53
|
+
assignFrom(dest, pattern, { from: source, ...inheritedOptions, ...vector.withOptions }, permissionProcessor);
|
|
54
54
|
});
|
|
55
55
|
}
|
|
56
56
|
else {
|
|
57
|
-
assignGingerly(dest, pattern, inheritedOptions,
|
|
57
|
+
assignGingerly(dest, pattern, inheritedOptions, permissionProcessor);
|
|
58
58
|
}
|
|
59
59
|
}
|
|
60
60
|
// Handle shorthand (implicit toHost)
|
|
@@ -62,11 +62,11 @@ function processVector(vector, source, target, host, lhs, inheritedOptions, useA
|
|
|
62
62
|
if (shorthand) {
|
|
63
63
|
if (useAssignFrom && source != null) {
|
|
64
64
|
import('../assignFrom.js').then(({ assignFrom }) => {
|
|
65
|
-
assignFrom(host, shorthand, { from: source, ...inheritedOptions, ...vector.withOptions },
|
|
65
|
+
assignFrom(host, shorthand, { from: source, ...inheritedOptions, ...vector.withOptions }, permissionProcessor);
|
|
66
66
|
});
|
|
67
67
|
}
|
|
68
68
|
else {
|
|
69
|
-
assignGingerly(host, shorthand, inheritedOptions,
|
|
69
|
+
assignGingerly(host, shorthand, inheritedOptions, permissionProcessor);
|
|
70
70
|
}
|
|
71
71
|
}
|
|
72
72
|
}
|
|
@@ -79,7 +79,7 @@ function processVector(vector, source, target, host, lhs, inheritedOptions, useA
|
|
|
79
79
|
* @param host - The options.from (source/view model)
|
|
80
80
|
* @param inheritedOptions - Parent assignFrom options (withMethods, aka, etc.)
|
|
81
81
|
*/
|
|
82
|
-
export function attachEventListener(lhs, config, target, host, inheritedOptions,
|
|
82
|
+
export function attachEventListener(lhs, config, target, host, inheritedOptions, permissionProcessor) {
|
|
83
83
|
const { on: eventName, get: getConfig, fromLHS, fromHost, fromTarget, fromEvent, dispatch } = config;
|
|
84
84
|
// Resolve get config values
|
|
85
85
|
const { abortController, key, nudge, options: listenerOptions, stopPropagation, preventDefault, dispatch: getDispatch } = getConfig ?? {};
|
|
@@ -112,22 +112,22 @@ export function attachEventListener(lhs, config, target, host, inheritedOptions,
|
|
|
112
112
|
if (preventDefault)
|
|
113
113
|
event.preventDefault();
|
|
114
114
|
// Static assignments (no from) — top-level toTarget/toHost/toLHS + shorthand
|
|
115
|
-
processVector(config, null, target, host, lhs, inheritedOptions, false,
|
|
115
|
+
processVector(config, null, target, host, lhs, inheritedOptions, false, permissionProcessor);
|
|
116
116
|
// fromLHS assignments
|
|
117
117
|
if (fromLHS) {
|
|
118
|
-
processVector(fromLHS, lhs, target, host, lhs, inheritedOptions, true,
|
|
118
|
+
processVector(fromLHS, lhs, target, host, lhs, inheritedOptions, true, permissionProcessor);
|
|
119
119
|
}
|
|
120
120
|
// fromHost assignments
|
|
121
121
|
if (fromHost) {
|
|
122
|
-
processVector(fromHost, host, target, host, lhs, inheritedOptions, true,
|
|
122
|
+
processVector(fromHost, host, target, host, lhs, inheritedOptions, true, permissionProcessor);
|
|
123
123
|
}
|
|
124
124
|
// fromTarget assignments
|
|
125
125
|
if (fromTarget) {
|
|
126
|
-
processVector(fromTarget, target, target, host, lhs, inheritedOptions, true,
|
|
126
|
+
processVector(fromTarget, target, target, host, lhs, inheritedOptions, true, permissionProcessor);
|
|
127
127
|
}
|
|
128
128
|
// fromEvent assignments
|
|
129
129
|
if (fromEvent) {
|
|
130
|
-
processVector(fromEvent, event, target, host, lhs, inheritedOptions, true,
|
|
130
|
+
processVector(fromEvent, event, target, host, lhs, inheritedOptions, true, permissionProcessor);
|
|
131
131
|
}
|
|
132
132
|
// Dispatch custom event if configured
|
|
133
133
|
const dispatchConfig = dispatch || getDispatch;
|
|
@@ -8,8 +8,7 @@
|
|
|
8
8
|
*/
|
|
9
9
|
|
|
10
10
|
import assignGingerly from '../assignGingerly.js';
|
|
11
|
-
import type { AddEventListenerConfig, AssignDispatchVector } from '../types/assign-gingerly/types.js';
|
|
12
|
-
import type { AssignPermissions } from '../types/assign-gingerly/types.js';
|
|
11
|
+
import type { AddEventListenerConfig, AssignDispatchVector, PermissionProcessor } from '../types/assign-gingerly/types.js';
|
|
13
12
|
|
|
14
13
|
/**
|
|
15
14
|
* WeakMap for dedup: Element → Map<key, AbortController>
|
|
@@ -52,7 +51,7 @@ function processVector(
|
|
|
52
51
|
lhs: Element,
|
|
53
52
|
inheritedOptions: any,
|
|
54
53
|
useAssignFrom: boolean,
|
|
55
|
-
|
|
54
|
+
permissionProcessor?: PermissionProcessor
|
|
56
55
|
): void {
|
|
57
56
|
const destinations = [
|
|
58
57
|
{ key: 'toTarget' as const, dest: target },
|
|
@@ -66,10 +65,10 @@ function processVector(
|
|
|
66
65
|
if (useAssignFrom && source != null) {
|
|
67
66
|
// Dynamic import assignFrom on demand (fire-and-forget context, already async)
|
|
68
67
|
import('../assignFrom.js').then(({ assignFrom }) => {
|
|
69
|
-
assignFrom(dest, pattern, { from: source, ...inheritedOptions, ...vector.withOptions },
|
|
68
|
+
assignFrom(dest, pattern, { from: source, ...inheritedOptions, ...vector.withOptions }, permissionProcessor);
|
|
70
69
|
});
|
|
71
70
|
} else {
|
|
72
|
-
assignGingerly(dest, pattern, inheritedOptions,
|
|
71
|
+
assignGingerly(dest, pattern, inheritedOptions, permissionProcessor);
|
|
73
72
|
}
|
|
74
73
|
}
|
|
75
74
|
|
|
@@ -78,10 +77,10 @@ function processVector(
|
|
|
78
77
|
if (shorthand) {
|
|
79
78
|
if (useAssignFrom && source != null) {
|
|
80
79
|
import('../assignFrom.js').then(({ assignFrom }) => {
|
|
81
|
-
assignFrom(host, shorthand, { from: source, ...inheritedOptions, ...vector.withOptions },
|
|
80
|
+
assignFrom(host, shorthand, { from: source, ...inheritedOptions, ...vector.withOptions }, permissionProcessor);
|
|
82
81
|
});
|
|
83
82
|
} else {
|
|
84
|
-
assignGingerly(host, shorthand, inheritedOptions,
|
|
83
|
+
assignGingerly(host, shorthand, inheritedOptions, permissionProcessor);
|
|
85
84
|
}
|
|
86
85
|
}
|
|
87
86
|
}
|
|
@@ -101,7 +100,7 @@ export function attachEventListener(
|
|
|
101
100
|
target: any,
|
|
102
101
|
host: any,
|
|
103
102
|
inheritedOptions: any,
|
|
104
|
-
|
|
103
|
+
permissionProcessor?: PermissionProcessor
|
|
105
104
|
): void {
|
|
106
105
|
const { on: eventName, get: getConfig, fromLHS, fromHost, fromTarget, fromEvent, dispatch } = config;
|
|
107
106
|
|
|
@@ -134,26 +133,26 @@ export function attachEventListener(
|
|
|
134
133
|
if (preventDefault) event.preventDefault();
|
|
135
134
|
|
|
136
135
|
// Static assignments (no from) — top-level toTarget/toHost/toLHS + shorthand
|
|
137
|
-
processVector(config, null, target, host, lhs, inheritedOptions, false,
|
|
136
|
+
processVector(config, null, target, host, lhs, inheritedOptions, false, permissionProcessor);
|
|
138
137
|
|
|
139
138
|
// fromLHS assignments
|
|
140
139
|
if (fromLHS) {
|
|
141
|
-
processVector(fromLHS, lhs, target, host, lhs, inheritedOptions, true,
|
|
140
|
+
processVector(fromLHS, lhs, target, host, lhs, inheritedOptions, true, permissionProcessor);
|
|
142
141
|
}
|
|
143
142
|
|
|
144
143
|
// fromHost assignments
|
|
145
144
|
if (fromHost) {
|
|
146
|
-
processVector(fromHost, host, target, host, lhs, inheritedOptions, true,
|
|
145
|
+
processVector(fromHost, host, target, host, lhs, inheritedOptions, true, permissionProcessor);
|
|
147
146
|
}
|
|
148
147
|
|
|
149
148
|
// fromTarget assignments
|
|
150
149
|
if (fromTarget) {
|
|
151
|
-
processVector(fromTarget, target, target, host, lhs, inheritedOptions, true,
|
|
150
|
+
processVector(fromTarget, target, target, host, lhs, inheritedOptions, true, permissionProcessor);
|
|
152
151
|
}
|
|
153
152
|
|
|
154
153
|
// fromEvent assignments
|
|
155
154
|
if (fromEvent) {
|
|
156
|
-
processVector(fromEvent, event, target, host, lhs, inheritedOptions, true,
|
|
155
|
+
processVector(fromEvent, event, target, host, lhs, inheritedOptions, true, permissionProcessor);
|
|
157
156
|
}
|
|
158
157
|
|
|
159
158
|
// Dispatch custom event if configured
|
package/handlers/lazyLoad.ts
CHANGED
|
@@ -20,11 +20,11 @@
|
|
|
20
20
|
*/
|
|
21
21
|
|
|
22
22
|
import type { AssignFromHandler } from '../assignFromAsync.js';
|
|
23
|
-
import type { LazyLoadResolvedParams, LazyLoadInstantiatedContext } from '../types/assign-gingerly/types.js';
|
|
23
|
+
import type { LazyLoadResolvedParams, LazyLoadInstantiatedContext, PermissionProcessor } from '../types/assign-gingerly/types.js';
|
|
24
24
|
import { withTransition, ensureHideStyle, DEFAULT_HIDE_CLASS } from '../transitionHelper.js';
|
|
25
25
|
import { findMarkers, createMarkers, getNodesBetweenMarkers, findMarkersSibling, createMarkersSibling, MARKER_START_PREFIX, MARKER_END } from '../markerUtils.js';
|
|
26
26
|
import { assignFrom } from '../assignFrom.js';
|
|
27
|
-
|
|
27
|
+
|
|
28
28
|
|
|
29
29
|
export type { LazyLoadResolvedParams, LazyLoadInstantiatedContext };
|
|
30
30
|
|
|
@@ -49,16 +49,16 @@ function getMarkerName(templateEl: any): string {
|
|
|
49
49
|
export class LazyLoadHandler implements AssignFromHandler {
|
|
50
50
|
config: any;
|
|
51
51
|
_options: any;
|
|
52
|
-
|
|
52
|
+
_permissionProcessor?: PermissionProcessor;
|
|
53
53
|
static #markerCounter = 0;
|
|
54
54
|
|
|
55
55
|
constructor(config: any) {
|
|
56
56
|
this.config = config;
|
|
57
57
|
}
|
|
58
58
|
|
|
59
|
-
async assign(lhsTarget: any, resolvedParams: LazyLoadResolvedParams, options?: any,
|
|
59
|
+
async assign(lhsTarget: any, resolvedParams: LazyLoadResolvedParams, options?: any, permissionProcessor?: PermissionProcessor): Promise<void> {
|
|
60
60
|
this._options = options; // Store for applyAssign access
|
|
61
|
-
this.
|
|
61
|
+
this._permissionProcessor = permissionProcessor;
|
|
62
62
|
const {
|
|
63
63
|
if: condition,
|
|
64
64
|
instantiate,
|
|
@@ -320,10 +320,10 @@ export class LazyLoadHandler implements AssignFromHandler {
|
|
|
320
320
|
const len = Math.min(elements.length, assign.configs.length);
|
|
321
321
|
for (let j = 0; j < len; j++) {
|
|
322
322
|
const cfg = assign.configs[j];
|
|
323
|
-
assignFrom(elements[j], cfg.toClone ?? {}, { from, ...cfg.withOptions }, this.
|
|
323
|
+
assignFrom(elements[j], cfg.toClone ?? {}, { from, ...cfg.withOptions }, this._permissionProcessor);
|
|
324
324
|
}
|
|
325
325
|
} else if (assign.toClone) {
|
|
326
|
-
assignFrom(elements[0], assign.toClone, { from, ...assign.withOptions }, this.
|
|
326
|
+
assignFrom(elements[0], assign.toClone, { from, ...assign.withOptions }, this._permissionProcessor);
|
|
327
327
|
}
|
|
328
328
|
}
|
|
329
329
|
|
|
@@ -21,7 +21,7 @@
|
|
|
21
21
|
*/
|
|
22
22
|
|
|
23
23
|
import { LazyLoadHandler } from './lazyLoad.js';
|
|
24
|
-
import type {
|
|
24
|
+
import type { PermissionProcessor } from '../types/assign-gingerly/types.js';
|
|
25
25
|
import type { AssignFromHandler } from '../assignFromAsync.js';
|
|
26
26
|
import type { LazyLoadSwitchResolvedParams } from '../types/assign-gingerly/types.js';
|
|
27
27
|
|
|
@@ -56,10 +56,10 @@ function evaluateOp(lhs: any, op: string, rhs: any): boolean {
|
|
|
56
56
|
*/
|
|
57
57
|
export class LazyLoadSwitchHandler extends LazyLoadHandler implements AssignFromHandler {
|
|
58
58
|
|
|
59
|
-
async assign(lhsTarget: any, resolvedParams: LazyLoadSwitchResolvedParams, options?: any,
|
|
59
|
+
async assign(lhsTarget: any, resolvedParams: LazyLoadSwitchResolvedParams, options?: any, permissionProcessor?: PermissionProcessor): Promise<void> {
|
|
60
60
|
const { lhs, op = '===', rhs, ...rest } = resolvedParams;
|
|
61
61
|
const condition = evaluateOp(lhs, op, rhs);
|
|
62
62
|
// Delegate to parent with computed condition
|
|
63
|
-
return super.assign(lhsTarget, { ...rest, if: condition }, options,
|
|
63
|
+
return super.assign(lhsTarget, { ...rest, if: condition }, options, permissionProcessor);
|
|
64
64
|
}
|
|
65
65
|
}
|
|
@@ -25,7 +25,7 @@
|
|
|
25
25
|
* }, { from: vm, withMethods: ['querySelector'], protocols: { globalThis: k => globalThis[k] } });
|
|
26
26
|
*/
|
|
27
27
|
import { findMarkers, createMarkers } from '../markerUtils.js';
|
|
28
|
-
import { resolveValue } from '../resolveValues.js';
|
|
28
|
+
import { resolveValue } from '../resolve/resolveValues.js';
|
|
29
29
|
import { assignFrom } from '../assignFrom.js';
|
|
30
30
|
import { processInferredAssignments } from '../inferredAssignments.js';
|
|
31
31
|
/**
|
|
@@ -55,7 +55,7 @@ export class ManageTemplateListHandler {
|
|
|
55
55
|
constructor(config) {
|
|
56
56
|
this.config = config;
|
|
57
57
|
}
|
|
58
|
-
async assign(lhsTarget, resolvedParams, options,
|
|
58
|
+
async assign(lhsTarget, resolvedParams, options, permissionProcessor) {
|
|
59
59
|
//return;
|
|
60
60
|
const { forEach: items, instantiate, method = 'appendChild', forget = false, markerName, yieldEvery, } = resolvedParams;
|
|
61
61
|
if (!(lhsTarget instanceof Element)) {
|
|
@@ -143,7 +143,7 @@ export class ManageTemplateListHandler {
|
|
|
143
143
|
const len = Math.min(elements.length, configs.length);
|
|
144
144
|
for (let j = 0; j < len; j++) {
|
|
145
145
|
const cfg = configs[j];
|
|
146
|
-
assignFrom(elements[j], cfg.toClone ?? {}, { from: item, ...cfg.withOptions },
|
|
146
|
+
assignFrom(elements[j], cfg.toClone ?? {}, { from: item, ...cfg.withOptions }, permissionProcessor);
|
|
147
147
|
}
|
|
148
148
|
}
|
|
149
149
|
else {
|
|
@@ -153,13 +153,13 @@ export class ManageTemplateListHandler {
|
|
|
153
153
|
processInferred(rootEl, item, inferredConfig === true ? { byItemprop: true } : inferredConfig);
|
|
154
154
|
}
|
|
155
155
|
else {
|
|
156
|
-
assignFrom(rootEl, toClone, { from: item, ...withOptions },
|
|
156
|
+
assignFrom(rootEl, toClone, { from: item, ...withOptions }, permissionProcessor);
|
|
157
157
|
}
|
|
158
158
|
if (hostToClone && options?.from) {
|
|
159
|
-
assignFrom(rootEl, hostToClone, { from: options.from, ...hostWithOptions },
|
|
159
|
+
assignFrom(rootEl, hostToClone, { from: options.from, ...hostWithOptions }, permissionProcessor);
|
|
160
160
|
}
|
|
161
161
|
if (targetToClone) {
|
|
162
|
-
assignFrom(rootEl, targetToClone, { from: lhsTarget, ...targetWithOptions },
|
|
162
|
+
assignFrom(rootEl, targetToClone, { from: lhsTarget, ...targetWithOptions }, permissionProcessor);
|
|
163
163
|
}
|
|
164
164
|
}
|
|
165
165
|
}
|
|
@@ -192,7 +192,7 @@ export class ManageTemplateListHandler {
|
|
|
192
192
|
const len = Math.min(elements.length, configs.length);
|
|
193
193
|
for (let j = 0; j < len; j++) {
|
|
194
194
|
const cfg = configs[j];
|
|
195
|
-
assignFrom(elements[j], cfg.toClone ?? {}, { from: item, ...cfg.withOptions },
|
|
195
|
+
assignFrom(elements[j], cfg.toClone ?? {}, { from: item, ...cfg.withOptions }, permissionProcessor);
|
|
196
196
|
}
|
|
197
197
|
}
|
|
198
198
|
else {
|
|
@@ -204,13 +204,13 @@ export class ManageTemplateListHandler {
|
|
|
204
204
|
processInferred(rootEl, item, inferredConfig === true ? { byItemprop: true } : inferredConfig);
|
|
205
205
|
}
|
|
206
206
|
else {
|
|
207
|
-
assignFrom(rootEl, toClone, { from: item, ...withOptions },
|
|
207
|
+
assignFrom(rootEl, toClone, { from: item, ...withOptions }, permissionProcessor);
|
|
208
208
|
}
|
|
209
209
|
if (hostToClone && options?.from) {
|
|
210
|
-
assignFrom(rootEl, hostToClone, { from: options.from, ...hostWithOptions },
|
|
210
|
+
assignFrom(rootEl, hostToClone, { from: options.from, ...hostWithOptions }, permissionProcessor);
|
|
211
211
|
}
|
|
212
212
|
if (targetToClone) {
|
|
213
|
-
assignFrom(rootEl, targetToClone, { from: lhsTarget, ...targetWithOptions },
|
|
213
|
+
assignFrom(rootEl, targetToClone, { from: lhsTarget, ...targetWithOptions }, permissionProcessor);
|
|
214
214
|
}
|
|
215
215
|
}
|
|
216
216
|
}
|