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
|
@@ -28,10 +28,10 @@
|
|
|
28
28
|
import type { AssignFromHandler } from '../assignFromAsync.js';
|
|
29
29
|
import type { ManageTemplateListResolvedParams } from '../types/assign-gingerly/types.js';
|
|
30
30
|
import { findMarkers, createMarkers, getNodesBetweenMarkers, MARKER_START_PREFIX, MARKER_END } from '../markerUtils.js';
|
|
31
|
-
import { resolveValue } from '../resolveValues.js';
|
|
31
|
+
import { resolveValue } from '../resolve/resolveValues.js';
|
|
32
32
|
import { assignFrom } from '../assignFrom.js';
|
|
33
|
-
import { processInferredAssignments } from '../inferredAssignments.js';
|
|
34
|
-
import type {
|
|
33
|
+
import { processInferredAssignments } from '../inferredAssignments.js';
|
|
34
|
+
import type { PermissionProcessor } from '../types/assign-gingerly/types.js';
|
|
35
35
|
|
|
36
36
|
/**
|
|
37
37
|
* Reserved keys in fromEachItem config — not treated as shorthand patterns.
|
|
@@ -75,7 +75,7 @@ export class ManageTemplateListHandler implements AssignFromHandler {
|
|
|
75
75
|
this.config = config;
|
|
76
76
|
}
|
|
77
77
|
|
|
78
|
-
async assign(lhsTarget: any, resolvedParams: ManageTemplateListResolvedParams, options?: any,
|
|
78
|
+
async assign(lhsTarget: any, resolvedParams: ManageTemplateListResolvedParams, options?: any, permissionProcessor?: PermissionProcessor): Promise<void> {
|
|
79
79
|
//return;
|
|
80
80
|
const {
|
|
81
81
|
forEach: items,
|
|
@@ -184,7 +184,7 @@ export class ManageTemplateListHandler implements AssignFromHandler {
|
|
|
184
184
|
const len = Math.min(elements.length, configs.length);
|
|
185
185
|
for (let j = 0; j < len; j++) {
|
|
186
186
|
const cfg = configs[j];
|
|
187
|
-
assignFrom(elements[j], cfg.toClone ?? {}, { from: item, ...cfg.withOptions },
|
|
187
|
+
assignFrom(elements[j], cfg.toClone ?? {}, { from: item, ...cfg.withOptions }, permissionProcessor);
|
|
188
188
|
}
|
|
189
189
|
} else {
|
|
190
190
|
const rootEl = existingNodes.find(n => n instanceof Element) as Element | undefined;
|
|
@@ -192,13 +192,13 @@ export class ManageTemplateListHandler implements AssignFromHandler {
|
|
|
192
192
|
if (processInferred) {
|
|
193
193
|
processInferred(rootEl, item, inferredConfig === true ? { byItemprop: true } : inferredConfig);
|
|
194
194
|
} else {
|
|
195
|
-
assignFrom(rootEl, toClone, { from: item, ...withOptions },
|
|
195
|
+
assignFrom(rootEl, toClone, { from: item, ...withOptions }, permissionProcessor);
|
|
196
196
|
}
|
|
197
197
|
if (hostToClone && options?.from) {
|
|
198
|
-
assignFrom(rootEl, hostToClone, { from: options.from, ...hostWithOptions },
|
|
198
|
+
assignFrom(rootEl, hostToClone, { from: options.from, ...hostWithOptions }, permissionProcessor);
|
|
199
199
|
}
|
|
200
200
|
if (targetToClone) {
|
|
201
|
-
assignFrom(rootEl, targetToClone, { from: lhsTarget, ...targetWithOptions },
|
|
201
|
+
assignFrom(rootEl, targetToClone, { from: lhsTarget, ...targetWithOptions }, permissionProcessor);
|
|
202
202
|
}
|
|
203
203
|
}
|
|
204
204
|
}
|
|
@@ -229,7 +229,7 @@ export class ManageTemplateListHandler implements AssignFromHandler {
|
|
|
229
229
|
const len = Math.min(elements.length, configs.length);
|
|
230
230
|
for (let j = 0; j < len; j++) {
|
|
231
231
|
const cfg = configs[j];
|
|
232
|
-
assignFrom(elements[j], cfg.toClone ?? {}, { from: item, ...cfg.withOptions },
|
|
232
|
+
assignFrom(elements[j], cfg.toClone ?? {}, { from: item, ...cfg.withOptions }, permissionProcessor);
|
|
233
233
|
}
|
|
234
234
|
} else {
|
|
235
235
|
const rootEl = clonedNodes.find(n => n instanceof Element) as Element | undefined;
|
|
@@ -240,14 +240,14 @@ export class ManageTemplateListHandler implements AssignFromHandler {
|
|
|
240
240
|
if (processInferred) {
|
|
241
241
|
processInferred(rootEl, item, inferredConfig === true ? { byItemprop: true } : inferredConfig);
|
|
242
242
|
} else {
|
|
243
|
-
assignFrom(rootEl, toClone, { from: item, ...withOptions },
|
|
243
|
+
assignFrom(rootEl, toClone, { from: item, ...withOptions }, permissionProcessor);
|
|
244
244
|
}
|
|
245
245
|
|
|
246
246
|
if (hostToClone && options?.from) {
|
|
247
|
-
assignFrom(rootEl, hostToClone, { from: options.from, ...hostWithOptions },
|
|
247
|
+
assignFrom(rootEl, hostToClone, { from: options.from, ...hostWithOptions }, permissionProcessor);
|
|
248
248
|
}
|
|
249
249
|
if (targetToClone) {
|
|
250
|
-
assignFrom(rootEl, targetToClone, { from: lhsTarget, ...targetWithOptions },
|
|
250
|
+
assignFrom(rootEl, targetToClone, { from: lhsTarget, ...targetWithOptions }, permissionProcessor);
|
|
251
251
|
}
|
|
252
252
|
}
|
|
253
253
|
}
|
|
@@ -23,7 +23,7 @@
|
|
|
23
23
|
|
|
24
24
|
import type { AssignFromHandler } from '../assignFromAsync.js';
|
|
25
25
|
import assignGingerly from '../assignGingerly.js';
|
|
26
|
-
import type {
|
|
26
|
+
import type { PermissionProcessor } from '../types/assign-gingerly/types.js';
|
|
27
27
|
|
|
28
28
|
/**
|
|
29
29
|
* Operator keys recognized in case objects.
|
|
@@ -73,7 +73,7 @@ export class RangeSelectorHandler implements AssignFromHandler {
|
|
|
73
73
|
this.config = config;
|
|
74
74
|
}
|
|
75
75
|
|
|
76
|
-
async assign(lhsTarget: any, resolvedParams: any, _options?: any,
|
|
76
|
+
async assign(lhsTarget: any, resolvedParams: any, _options?: any, permissionProcessor?: PermissionProcessor): Promise<void> {
|
|
77
77
|
const { value, when } = resolvedParams;
|
|
78
78
|
|
|
79
79
|
if (!Array.isArray(when)) return;
|
|
@@ -82,7 +82,7 @@ export class RangeSelectorHandler implements AssignFromHandler {
|
|
|
82
82
|
for (const caseObj of when) {
|
|
83
83
|
if (caseMatches(value, caseObj)) {
|
|
84
84
|
if (caseObj.merge && typeof caseObj.merge === 'object') {
|
|
85
|
-
assignGingerly(lhsTarget, caseObj.merge, undefined,
|
|
85
|
+
assignGingerly(lhsTarget, caseObj.merge, undefined, permissionProcessor);
|
|
86
86
|
}
|
|
87
87
|
return; // First match wins
|
|
88
88
|
}
|
package/index.js
CHANGED
|
@@ -5,15 +5,14 @@ export { waitForEvent } from './waitForEvent.js';
|
|
|
5
5
|
export { ParserRegistry, globalParserRegistry } from './parserRegistry.js';
|
|
6
6
|
export { parseWithAttrs } from './parseWithAttrs.js';
|
|
7
7
|
export { buildCSSQuery } from './buildCSSQuery.js';
|
|
8
|
-
export { resolveTemplate } from './resolveTemplate.js';
|
|
8
|
+
export { resolveTemplate } from './resolve/resolveTemplate.js';
|
|
9
9
|
export { getHost } from './getHost.js';
|
|
10
|
-
export { resolveValues, resolveValue } from './resolveValues.js';
|
|
10
|
+
export { resolveValues, resolveValue } from './resolve/resolveValues.js';
|
|
11
11
|
export { assignFromAsync } from './assignFromAsync.js';
|
|
12
12
|
export { assignFrom } from './assignFrom.js';
|
|
13
13
|
export { assignFeatures, FeaturesRegistry, captureFeatureInitVals, PropertyBag, suggestFeatureInfo, getFeatureInfoSuggestions } from './assignFeatures.js';
|
|
14
14
|
export { installForwarding } from './DX/installForwarding.js';
|
|
15
15
|
export { defineWithFeatures } from './defineWithFeatures.js';
|
|
16
|
-
export { resolveAndAssignFeatures } from './resolveAndAssignFeatures.js';
|
|
17
16
|
export { nudge } from './handlers/nudge.js';
|
|
18
17
|
export { arr } from './handlers/arr.js';
|
|
19
18
|
import './object-extension.js';
|
package/index.ts
CHANGED
|
@@ -5,15 +5,14 @@ export {waitForEvent} from './waitForEvent.js';
|
|
|
5
5
|
export {ParserRegistry, globalParserRegistry} from './parserRegistry.js';
|
|
6
6
|
export {parseWithAttrs} from './parseWithAttrs.js';
|
|
7
7
|
export {buildCSSQuery} from './buildCSSQuery.js';
|
|
8
|
-
export {resolveTemplate} from './resolveTemplate.js';
|
|
8
|
+
export {resolveTemplate} from './resolve/resolveTemplate.js';
|
|
9
9
|
export {getHost} from './getHost.js';
|
|
10
|
-
export {resolveValues, resolveValue} from './resolveValues.js';
|
|
10
|
+
export {resolveValues, resolveValue} from './resolve/resolveValues.js';
|
|
11
11
|
export {assignFromAsync} from './assignFromAsync.js';
|
|
12
12
|
export {assignFrom} from './assignFrom.js';
|
|
13
13
|
export {assignFeatures, FeaturesRegistry, captureFeatureInitVals, PropertyBag, suggestFeatureInfo, getFeatureInfoSuggestions} from './assignFeatures.js';
|
|
14
14
|
export {installForwarding} from './DX/installForwarding.js';
|
|
15
15
|
export {defineWithFeatures} from './defineWithFeatures.js';
|
|
16
|
-
export {resolveAndAssignFeatures} from './resolveAndAssignFeatures.js';
|
|
17
16
|
export {nudge} from './handlers/nudge.js';
|
|
18
17
|
export {arr} from './handlers/arr.js';
|
|
19
18
|
export {} from './handlers/manageTemplateList.js';
|
|
@@ -424,6 +424,11 @@ export interface GetValuesOptions extends IAssignGingerlyOptions {
|
|
|
424
424
|
*/
|
|
425
425
|
root?: any;
|
|
426
426
|
|
|
427
|
+
/**
|
|
428
|
+
* Optional permission processor for guarding method calls during RHS resolution.
|
|
429
|
+
*/
|
|
430
|
+
permissionProcessor?: PermissionProcessor;
|
|
431
|
+
|
|
427
432
|
/**
|
|
428
433
|
* Synchronous protocol handlers for resolving protocol-prefixed values.
|
|
429
434
|
* Each handler receives the key portion and MUST return synchronously.
|
|
@@ -449,6 +454,11 @@ export interface ResolveValuesOptions extends IAssignGingerlyOptions {
|
|
|
449
454
|
*/
|
|
450
455
|
root?: any;
|
|
451
456
|
|
|
457
|
+
/**
|
|
458
|
+
* Optional permission processor for guarding method calls during RHS resolution.
|
|
459
|
+
*/
|
|
460
|
+
permissionProcessor?: PermissionProcessor;
|
|
461
|
+
|
|
452
462
|
/**
|
|
453
463
|
* Protocol handlers for resolving protocol-prefixed values (e.g., 'globalThis://key').
|
|
454
464
|
* Each handler receives the key portion and returns the resolved value (sync or async).
|
|
@@ -591,21 +601,6 @@ export interface SupportedFeatureConfig {
|
|
|
591
601
|
callbackForwarding?: string[];
|
|
592
602
|
}
|
|
593
603
|
|
|
594
|
-
/**
|
|
595
|
-
* Class-level configuration for the features system.
|
|
596
|
-
* Declared as `static featuresConfig` on the class.
|
|
597
|
-
*/
|
|
598
|
-
export interface FeaturesClassConfig {
|
|
599
|
-
/**
|
|
600
|
-
* Lifecycle method configuration.
|
|
601
|
-
* true = install 'whenFeatureReady' method.
|
|
602
|
-
* Object = custom method name.
|
|
603
|
-
*/
|
|
604
|
-
lifecycleKeys?: true | {
|
|
605
|
-
whenFeatureReady?: string;
|
|
606
|
-
};
|
|
607
|
-
}
|
|
608
|
-
|
|
609
604
|
/**
|
|
610
605
|
* Configuration for a feature passed to assignFeatures.
|
|
611
606
|
*/
|
|
@@ -710,7 +705,7 @@ export interface HandlerConfig {
|
|
|
710
705
|
* Handlers are invoked when a LHS key ends with ' =>'.
|
|
711
706
|
*/
|
|
712
707
|
export interface AssignFromHandler {
|
|
713
|
-
assign(lhsTarget: any, resolvedParams: Record<string, any>, options: any,
|
|
708
|
+
assign(lhsTarget: any, resolvedParams: Record<string, any>, options: any, permissionProcessor?: PermissionProcessor): Promise<void> | void;
|
|
714
709
|
}
|
|
715
710
|
|
|
716
711
|
/**
|
|
@@ -888,7 +883,7 @@ export interface LazyLoadInstantiatedContext {
|
|
|
888
883
|
export declare class LazyLoadHandler implements AssignFromHandler {
|
|
889
884
|
config: any;
|
|
890
885
|
constructor(config: any);
|
|
891
|
-
assign(lhsTarget: any, resolvedParams: Record<string, any>, options?: any,
|
|
886
|
+
assign(lhsTarget: any, resolvedParams: Record<string, any>, options?: any, permissionProcessor?: PermissionProcessor): Promise<void>;
|
|
892
887
|
protected onCloneInserted(nodes: Node[], lhsTarget: Element, resolvedParams: Record<string, any>): Promise<void>;
|
|
893
888
|
}
|
|
894
889
|
|
|
@@ -946,11 +941,11 @@ export interface AddEventListenerConfig extends AssignDispatchVector {
|
|
|
946
941
|
* Phase II+: object form for a restricted property setting.
|
|
947
942
|
*/
|
|
948
943
|
export interface RestrictedPropSetting {
|
|
949
|
-
|
|
950
|
-
useMethod?: string;
|
|
951
|
-
attr?: string;
|
|
952
|
-
|
|
953
|
-
allowCrossDomain?: boolean;
|
|
944
|
+
props: string | string[];
|
|
945
|
+
useMethod?: string; // Phase II: redirect to a safe method
|
|
946
|
+
attr?: boolean | string | string[]; // Phase III: also watch setAttribute for these attrs
|
|
947
|
+
allowFromSameDomain?: boolean; // Phase III: allow same-origin URLs
|
|
948
|
+
allowCrossDomain?: boolean; // Phase III: allow any URL
|
|
954
949
|
}
|
|
955
950
|
|
|
956
951
|
/**
|
|
@@ -973,7 +968,8 @@ export interface AssignPermissions {
|
|
|
973
968
|
* Restricted property settings.
|
|
974
969
|
* Phase I: string entries are property names that cannot be assigned.
|
|
975
970
|
* Phase II: an object with useMethod redirects ordinary assignment to that
|
|
976
|
-
* method; command operations remain blocked. Phase III+ adds attr
|
|
971
|
+
* method; command operations remain blocked. Phase III+ adds props, attr,
|
|
972
|
+
* allowFromSameDomain, and allowCrossDomain support.
|
|
977
973
|
*
|
|
978
974
|
* NOTE: This is a property-assignment guard only. Method calls (setAttribute, etc.)
|
|
979
975
|
* are not blocked — see Phase III+. Event listeners can still be registered, but
|
|
@@ -987,3 +983,21 @@ export interface AssignPermissions {
|
|
|
987
983
|
/** Restricted method settings (Phase IV+) */
|
|
988
984
|
restrictedMethodSettings?: Array<string | RestrictedMethodConfig>;
|
|
989
985
|
}
|
|
986
|
+
|
|
987
|
+
//#region Permissions
|
|
988
|
+
export interface RestrictedPropSettingsMap {
|
|
989
|
+
props: Map<string, RestrictedPropSetting | undefined>;
|
|
990
|
+
attrs: Map<string, RestrictedPropSetting | undefined>;
|
|
991
|
+
}
|
|
992
|
+
|
|
993
|
+
export declare class PermissionProcessor {
|
|
994
|
+
constructor(permissions: AssignPermissions | undefined);
|
|
995
|
+
get crossDomainImports(): boolean;
|
|
996
|
+
get hasProps(): boolean;
|
|
997
|
+
get hasAttrs(): boolean;
|
|
998
|
+
checkRestrictedProp(key: string): boolean;
|
|
999
|
+
checkRestrictedMethod(methodName: string): boolean;
|
|
1000
|
+
redirectRestrictedProp(target: any, key: string, value: any): boolean;
|
|
1001
|
+
checkRestrictedAttributeCall(methodName: string, args: any[]): { blocked: boolean; attrName?: string };
|
|
1002
|
+
}
|
|
1003
|
+
//#endregion
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import {RAConfig} from '../roundabout/types.js';
|
|
2
|
+
import {FontFaceFeatureConfig} from '../font-face-feature/types.js';
|
|
3
|
+
import {CustomData as TSCD} from '../truth-sourcer/types.js';
|
|
4
|
+
import {CustomData as FUCD} from '../face-up/types.js';
|
|
5
|
+
|
|
6
|
+
export interface ElMakerConfig<AllProps = any, TActions = AllProps> {
|
|
7
|
+
assignFeatures: {
|
|
8
|
+
roundabout?: {
|
|
9
|
+
spawn?: string,
|
|
10
|
+
customData: {
|
|
11
|
+
raConfig: RAConfig<AllProps, TActions, TActions>
|
|
12
|
+
}
|
|
13
|
+
},
|
|
14
|
+
fontMgr?: {
|
|
15
|
+
spawn?: string,
|
|
16
|
+
customData: {
|
|
17
|
+
fontFaceFeatureConfig: FontFaceFeatureConfig
|
|
18
|
+
}
|
|
19
|
+
},
|
|
20
|
+
templateMaker?: {
|
|
21
|
+
spawn?: string,
|
|
22
|
+
customData?: any
|
|
23
|
+
},
|
|
24
|
+
faceUp?: {
|
|
25
|
+
spawn?: string,
|
|
26
|
+
customData?: FUCD
|
|
27
|
+
},
|
|
28
|
+
truthSourcer?: {
|
|
29
|
+
spawn?: string,
|
|
30
|
+
customData?: TSCD
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "assign-gingerly",
|
|
3
|
-
"version": "0.0.
|
|
3
|
+
"version": "0.0.76",
|
|
4
4
|
"description": "This package provides a utility function for carefully merging one object into another.",
|
|
5
5
|
"homepage": "https://github.com/bahrus/assign-gingerly#readme",
|
|
6
6
|
"bugs": {
|
|
@@ -21,6 +21,8 @@
|
|
|
21
21
|
"assignPermissions/**",
|
|
22
22
|
"handlers/**",
|
|
23
23
|
"inferencer/**",
|
|
24
|
+
"resolve/**",
|
|
25
|
+
"utils/**",
|
|
24
26
|
"README.md",
|
|
25
27
|
"LICENSE",
|
|
26
28
|
"types/assign-gingerly/types.d.ts"
|
|
@@ -38,8 +40,13 @@
|
|
|
38
40
|
"default": "./assignTentatively.js",
|
|
39
41
|
"types": "./assignTentatively.ts"
|
|
40
42
|
},
|
|
41
|
-
"./
|
|
42
|
-
"default": "./
|
|
43
|
+
"./buildCSSQuery.js": {
|
|
44
|
+
"default": "./buildCSSQuery.js",
|
|
45
|
+
"types": "./buildCSSQuery.ts"
|
|
46
|
+
},
|
|
47
|
+
"./object-extension.js": {
|
|
48
|
+
"default": "./object-extension.js",
|
|
49
|
+
"types": "./object-extension.ts"
|
|
43
50
|
},
|
|
44
51
|
"./parserRegistry.js": {
|
|
45
52
|
"default": "./parserRegistry.js"
|
|
@@ -48,29 +55,25 @@
|
|
|
48
55
|
"default": "./parseWithAttrs.js",
|
|
49
56
|
"types": "./parseWithAttrs.ts"
|
|
50
57
|
},
|
|
51
|
-
"./
|
|
52
|
-
"default": "./
|
|
53
|
-
"types": "./
|
|
54
|
-
},
|
|
55
|
-
"./resolveTemplate.js": {
|
|
56
|
-
"default": "./resolveTemplate.js",
|
|
57
|
-
"types": "./resolveTemplate.ts"
|
|
58
|
+
"./resolve/resolveTemplate.js": {
|
|
59
|
+
"default": "./resolve/resolveTemplate.js",
|
|
60
|
+
"types": "./resolve/resolveTemplate.ts"
|
|
58
61
|
},
|
|
59
62
|
"./getHost.js": {
|
|
60
63
|
"default": "./getHost.js",
|
|
61
64
|
"types": "./getHost.ts"
|
|
62
65
|
},
|
|
63
|
-
"./resolveValues.js": {
|
|
64
|
-
"default": "./resolveValues.js",
|
|
65
|
-
"types": "./resolveValues.ts"
|
|
66
|
+
"./resolve/resolveValues.js": {
|
|
67
|
+
"default": "./resolve/resolveValues.js",
|
|
68
|
+
"types": "./resolve/resolveValues.ts"
|
|
66
69
|
},
|
|
67
|
-
"./getValues.js": {
|
|
68
|
-
"default": "./getValues.js",
|
|
69
|
-
"types": "./getValues.ts"
|
|
70
|
+
"./resolve/getValues.js": {
|
|
71
|
+
"default": "./resolve/getValues.js",
|
|
72
|
+
"types": "./resolve/getValues.ts"
|
|
70
73
|
},
|
|
71
|
-
"./resolveIdRef.js": {
|
|
72
|
-
"default": "./resolveIdRef.js",
|
|
73
|
-
"types": "./resolveIdRef.ts"
|
|
74
|
+
"./resolve/resolveIdRef.js": {
|
|
75
|
+
"default": "./resolve/resolveIdRef.js",
|
|
76
|
+
"types": "./resolve/resolveIdRef.ts"
|
|
74
77
|
},
|
|
75
78
|
"./transitionHelper.js": {
|
|
76
79
|
"default": "./transitionHelper.js",
|
|
@@ -84,10 +87,6 @@
|
|
|
84
87
|
"default": "./defineWithFeatures.js",
|
|
85
88
|
"types": "./defineWithFeatures.ts"
|
|
86
89
|
},
|
|
87
|
-
"./resolveAndAssignFeatures.js": {
|
|
88
|
-
"default": "./resolveAndAssignFeatures.js",
|
|
89
|
-
"types": "./resolveAndAssignFeatures.ts"
|
|
90
|
-
},
|
|
91
90
|
"./handlers/addEventListener.js": {
|
|
92
91
|
"default": "./handlers/addEventListener.js",
|
|
93
92
|
"types": "./handlers/addEventListener.ts"
|
|
@@ -199,6 +198,9 @@
|
|
|
199
198
|
"./evaluatePathWithAsyncMethods.js": {
|
|
200
199
|
"default": "./evaluatePathWithAsyncMethods.js",
|
|
201
200
|
"types": "./evaluatePathWithAsyncMethods.ts"
|
|
201
|
+
},
|
|
202
|
+
"./waitForEvent.js": {
|
|
203
|
+
"default": "./waitForEvent.js"
|
|
202
204
|
}
|
|
203
205
|
},
|
|
204
206
|
"main": "index.js",
|
package/parseWithAttrs.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { globalParserRegistry, getParserRegistry } from './parserRegistry.js';
|
|
2
|
-
import { resolveTemplate } from './resolveTemplate.js';
|
|
2
|
+
import { resolveTemplate } from './resolve/resolveTemplate.js';
|
|
3
3
|
// Module-level cache for parsed attribute values
|
|
4
4
|
// Structure: Map<configKey, Map<attrValue, parsedValue>>
|
|
5
5
|
const parseCache = new Map();
|
package/parseWithAttrs.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { AttrPatterns, AttrConfig, ParserFunction, ParserContext, SpawnContext } from './types/assign-gingerly/types';
|
|
2
2
|
import { globalParserRegistry, getParserRegistry } from './parserRegistry.js';
|
|
3
|
-
import { resolveTemplate } from './resolveTemplate.js';
|
|
3
|
+
import { resolveTemplate } from './resolve/resolveTemplate.js';
|
|
4
4
|
|
|
5
5
|
// Module-level cache for parsed attribute values
|
|
6
6
|
// Structure: Map<configKey, Map<attrValue, parsedValue>>
|
|
@@ -3,11 +3,10 @@
|
|
|
3
3
|
*
|
|
4
4
|
* Dynamically imported only when ` =>` keys are detected in the pattern.
|
|
5
5
|
*/
|
|
6
|
-
import { resolveValues } from './resolveValues.js';
|
|
7
|
-
import { getValues } from './getValues.js';
|
|
6
|
+
import { resolveValues } from './resolve/resolveValues.js';
|
|
7
|
+
import { getValues } from './resolve/getValues.js';
|
|
8
8
|
import { evaluatePathWithMethods } from './assignGingerly.js';
|
|
9
9
|
import { findClassPrototypeInPath } from './utils/findClassPrototypeInPath.js';
|
|
10
|
-
import { buildRestrictedPropSet, redirectRestrictedProp } from './assignPermissions/restrictedProps.js';
|
|
11
10
|
/**
|
|
12
11
|
* Map of built-in handler names to their module paths.
|
|
13
12
|
* These are auto-loaded on demand — no explicit import required.
|
|
@@ -79,8 +78,7 @@ async function resolveFromHandlers(name, handlers) {
|
|
|
79
78
|
* @param options - The assignFrom options
|
|
80
79
|
* @param handlerRegistry - The registry of handler classes
|
|
81
80
|
*/
|
|
82
|
-
export async function processHandlerCommands(target, handlerKeys, pattern, options,
|
|
83
|
-
const restrictedPropSet = buildRestrictedPropSet(permissions);
|
|
81
|
+
export async function processHandlerCommands(target, handlerKeys, pattern, options, permissionProcessor) {
|
|
84
82
|
for (const key of handlerKeys) {
|
|
85
83
|
const lhsPath = key.substring(0, key.length - 3); // Remove ' =>'
|
|
86
84
|
const rhs = pattern[key];
|
|
@@ -190,12 +188,12 @@ export async function processHandlerCommands(target, handlerKeys, pattern, optio
|
|
|
190
188
|
// Instantiate and invoke the handler
|
|
191
189
|
const handler = new HandlerClass(config);
|
|
192
190
|
//return; //1.5ms
|
|
193
|
-
const result = await handler.assign(lhsTarget, resolvedParams, options,
|
|
191
|
+
const result = await handler.assign(lhsTarget, resolvedParams, options, permissionProcessor);
|
|
194
192
|
//return; //1.5ms
|
|
195
193
|
// Return-value protocol: if handler returns a non-undefined value,
|
|
196
194
|
// assign it back to the LHS path
|
|
197
195
|
if (result !== undefined && lhsParent != null && lhsKey != null
|
|
198
|
-
&& !redirectRestrictedProp(
|
|
196
|
+
&& !permissionProcessor?.redirectRestrictedProp(lhsParent, lhsKey, result)) {
|
|
199
197
|
lhsParent[lhsKey] = result;
|
|
200
198
|
}
|
|
201
199
|
}
|
|
@@ -4,12 +4,11 @@
|
|
|
4
4
|
* Dynamically imported only when ` =>` keys are detected in the pattern.
|
|
5
5
|
*/
|
|
6
6
|
|
|
7
|
-
import { resolveValues } from './resolveValues.js';
|
|
8
|
-
import { getValues } from './getValues.js';
|
|
7
|
+
import { resolveValues } from './resolve/resolveValues.js';
|
|
8
|
+
import { getValues } from './resolve/getValues.js';
|
|
9
9
|
import { evaluatePathWithMethods } from './assignGingerly.js';
|
|
10
|
-
import { findClassPrototypeInPath } from './utils/findClassPrototypeInPath.js';
|
|
11
|
-
import {
|
|
12
|
-
import type { AssignPermissions } from './types/assign-gingerly/types.js';
|
|
10
|
+
import { findClassPrototypeInPath } from './utils/findClassPrototypeInPath.js';
|
|
11
|
+
import type { PermissionProcessor } from './types/assign-gingerly/types.js';
|
|
13
12
|
import type { AssignFromOptions, AssignFromHandlerConstructor } from './assignFromAsync.js';
|
|
14
13
|
|
|
15
14
|
/**
|
|
@@ -98,10 +97,8 @@ export async function processHandlerCommands(
|
|
|
98
97
|
handlerKeys: string[],
|
|
99
98
|
pattern: Record<string, any>,
|
|
100
99
|
options: AssignFromOptions,
|
|
101
|
-
|
|
102
|
-
): Promise<void> {
|
|
103
|
-
const restrictedPropSet = buildRestrictedPropSet(permissions);
|
|
104
|
-
|
|
100
|
+
permissionProcessor?: PermissionProcessor
|
|
101
|
+
): Promise<void> {
|
|
105
102
|
for (const key of handlerKeys) {
|
|
106
103
|
const lhsPath = key.substring(0, key.length - 3); // Remove ' =>'
|
|
107
104
|
const rhs = pattern[key];
|
|
@@ -213,13 +210,13 @@ export async function processHandlerCommands(
|
|
|
213
210
|
// Instantiate and invoke the handler
|
|
214
211
|
const handler = new HandlerClass(config);
|
|
215
212
|
//return; //1.5ms
|
|
216
|
-
const result = await handler.assign(lhsTarget, resolvedParams, options,
|
|
213
|
+
const result = await handler.assign(lhsTarget, resolvedParams, options, permissionProcessor);
|
|
217
214
|
//return; //1.5ms
|
|
218
|
-
// Return-value protocol: if handler returns a non-undefined value,
|
|
219
|
-
// assign it back to the LHS path
|
|
220
|
-
if (result !== undefined && lhsParent != null && lhsKey != null
|
|
221
|
-
&& !redirectRestrictedProp(
|
|
222
|
-
lhsParent[lhsKey] = result;
|
|
215
|
+
// Return-value protocol: if handler returns a non-undefined value,
|
|
216
|
+
// assign it back to the LHS path
|
|
217
|
+
if (result !== undefined && lhsParent != null && lhsKey != null
|
|
218
|
+
&& !permissionProcessor?.redirectRestrictedProp(lhsParent, lhsKey, result)) {
|
|
219
|
+
lhsParent[lhsKey] = result;
|
|
223
220
|
}
|
|
224
221
|
}
|
|
225
222
|
}
|
|
@@ -48,6 +48,14 @@ export function normalizeAliasOptions(options) {
|
|
|
48
48
|
}
|
|
49
49
|
return { aliasMap, withMethods };
|
|
50
50
|
}
|
|
51
|
+
/**
|
|
52
|
+
* Check whether a method name is listed in withMethods and is not restricted
|
|
53
|
+
* by the permission processor. Restricted methods are treated as non-method
|
|
54
|
+
* property names so they fall through to normal access.
|
|
55
|
+
*/
|
|
56
|
+
function isAllowedMethod(methodName, withMethods, permissionProcessor) {
|
|
57
|
+
return !!withMethods && withMethods.has(methodName) && !permissionProcessor?.checkRestrictedMethod(methodName);
|
|
58
|
+
}
|
|
51
59
|
/**
|
|
52
60
|
* Apply alias substitutions to a path string.
|
|
53
61
|
* Replaces complete tokens between `?.` delimiters with their aliased values.
|
|
@@ -90,18 +98,18 @@ function parseCachedPath(path) {
|
|
|
90
98
|
* Navigate a path against a source object, optionally calling methods.
|
|
91
99
|
* Returns the resolved value at the end of the path.
|
|
92
100
|
*/
|
|
93
|
-
function navigatePath(source, parts, withMethods) {
|
|
101
|
+
function navigatePath(source, parts, withMethods, permissionProcessor) {
|
|
94
102
|
let current = source;
|
|
95
103
|
let i = 0;
|
|
96
104
|
while (i < parts.length) {
|
|
97
105
|
if (current == null)
|
|
98
106
|
return current;
|
|
99
107
|
const part = parts[i];
|
|
100
|
-
if (withMethods
|
|
108
|
+
if (isAllowedMethod(part, withMethods, permissionProcessor)) {
|
|
101
109
|
const method = current[part];
|
|
102
110
|
if (typeof method === 'function') {
|
|
103
111
|
const nextPart = parts[i + 1];
|
|
104
|
-
if (nextPart !== undefined && !(withMethods
|
|
112
|
+
if (nextPart !== undefined && !isAllowedMethod(nextPart, withMethods, permissionProcessor)) {
|
|
105
113
|
current = method.call(current, nextPart);
|
|
106
114
|
i += 2;
|
|
107
115
|
}
|
|
@@ -152,12 +160,13 @@ function getProtocolValue(value, protocols, options) {
|
|
|
152
160
|
* Recurses into nested arrays and plain objects.
|
|
153
161
|
*/
|
|
154
162
|
function getArray(arr, source, aliasMap, withMethods, protocols, options) {
|
|
163
|
+
const permissionProcessor = options?.permissionProcessor;
|
|
155
164
|
const result = [];
|
|
156
165
|
for (const item of arr) {
|
|
157
166
|
if (typeof item === 'string' && item.startsWith('?.')) {
|
|
158
167
|
const aliased = applyAliases(item, aliasMap);
|
|
159
168
|
const parts = parseCachedPath(aliased);
|
|
160
|
-
result.push(parts.length === 0 ? source : navigatePath(source, parts, withMethods));
|
|
169
|
+
result.push(parts.length === 0 ? source : navigatePath(source, parts, withMethods, permissionProcessor));
|
|
161
170
|
}
|
|
162
171
|
else if (typeof item === 'string' && item.startsWith('$0')) {
|
|
163
172
|
const rootRef = resolveRootReference(item, source, options?.root);
|
|
@@ -168,7 +177,7 @@ function getArray(arr, source, aliasMap, withMethods, protocols, options) {
|
|
|
168
177
|
const aliased = applyAliases(rootRef.path, aliasMap);
|
|
169
178
|
const normalizedPath = aliased.startsWith('?.') ? aliased : (aliased ? `?.${aliased}` : '?.');
|
|
170
179
|
const parts = parseCachedPath(normalizedPath);
|
|
171
|
-
result.push(parts.length === 0 ? rootRef.source : navigatePath(rootRef.source, parts, withMethods));
|
|
180
|
+
result.push(parts.length === 0 ? rootRef.source : navigatePath(rootRef.source, parts, withMethods, permissionProcessor));
|
|
172
181
|
}
|
|
173
182
|
}
|
|
174
183
|
else if (typeof item === 'string' && protocols && hasProtocol(item)) {
|
|
@@ -207,12 +216,13 @@ function getArray(arr, source, aliasMap, withMethods, protocols, options) {
|
|
|
207
216
|
export function getValues(pattern, source, options) {
|
|
208
217
|
const { aliasMap, withMethods } = normalizeAliasOptions(options);
|
|
209
218
|
const protocols = options?.protocols;
|
|
219
|
+
const permissionProcessor = options?.permissionProcessor;
|
|
210
220
|
const result = {};
|
|
211
221
|
for (const [key, value] of Object.entries(pattern)) {
|
|
212
222
|
if (typeof value === 'string' && value.startsWith('?.')) {
|
|
213
223
|
const aliased = applyAliases(value, aliasMap);
|
|
214
224
|
const parts = parseCachedPath(aliased);
|
|
215
|
-
result[key] = parts.length === 0 ? source : navigatePath(source, parts, withMethods);
|
|
225
|
+
result[key] = parts.length === 0 ? source : navigatePath(source, parts, withMethods, permissionProcessor);
|
|
216
226
|
}
|
|
217
227
|
else if (typeof value === 'string' && value.startsWith('$0')) {
|
|
218
228
|
const rootRef = resolveRootReference(value, source, options?.root);
|
|
@@ -223,7 +233,7 @@ export function getValues(pattern, source, options) {
|
|
|
223
233
|
const aliased = applyAliases(rootRef.path, aliasMap);
|
|
224
234
|
const normalizedPath = aliased.startsWith('?.') ? aliased : (aliased ? `?.${aliased}` : '?.');
|
|
225
235
|
const parts = parseCachedPath(normalizedPath);
|
|
226
|
-
result[key] = parts.length === 0 ? rootRef.source : navigatePath(rootRef.source, parts, withMethods);
|
|
236
|
+
result[key] = parts.length === 0 ? rootRef.source : navigatePath(rootRef.source, parts, withMethods, permissionProcessor);
|
|
227
237
|
}
|
|
228
238
|
}
|
|
229
239
|
else if (typeof value === 'string' && protocols && hasProtocol(value)) {
|
|
@@ -274,5 +284,6 @@ export function getValue(path, source, options) {
|
|
|
274
284
|
if (parts.length === 0)
|
|
275
285
|
return source;
|
|
276
286
|
const { withMethods } = normalizeAliasOptions(options);
|
|
277
|
-
|
|
287
|
+
const permissionProcessor = options?.permissionProcessor;
|
|
288
|
+
return navigatePath(source, parts, withMethods, permissionProcessor);
|
|
278
289
|
}
|