@salesforce/lds-adapters-uiapi 1.453.0 → 1.455.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/dist/es/es2018/types/src/generated/types/RecordLayoutSaveOptionRepresentation.d.ts +3 -3
- package/dist/es/es2018/types/src/util/language.d.ts +2 -2
- package/dist/es/es2018/uiapi-records-service.js +48 -3
- package/package.json +8 -8
- package/sfdc/graphqlAdapters.js +2 -2
- package/sfdc/index.js +25 -4
- package/sfdc/uiapi-static-functions.js +27 -2
- package/src/raml/api.raml +1 -1
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { IngestPath as $64$luvio_engine_IngestPath, Luvio as $64$luvio_engine_Luvio, Store as $64$luvio_engine_Store, FragmentSelection as $64$luvio_engine_FragmentSelection, ResourceIngest as $64$luvio_engine_ResourceIngest, DurableStoreKeyMetadataMap as $64$luvio_engine_DurableStoreKeyMetadataMap, NormalizedKeyMetadata as $64$luvio_engine_NormalizedKeyMetadata } from '@luvio/engine';
|
|
2
|
-
export declare const VERSION = "
|
|
2
|
+
export declare const VERSION = "0cf134254ce2ee7273137106534e73a3";
|
|
3
3
|
export declare function validate(obj: any, path?: string): TypeError | null;
|
|
4
4
|
export declare const RepresentationType: string;
|
|
5
5
|
export declare function normalize(input: RecordLayoutSaveOptionRepresentation, existing: RecordLayoutSaveOptionRepresentationNormalized, path: $64$luvio_engine_IngestPath, luvio: $64$luvio_engine_Luvio, store: $64$luvio_engine_Store, timestamp: number): RecordLayoutSaveOptionRepresentationNormalized;
|
|
@@ -23,7 +23,7 @@ export interface RecordLayoutSaveOptionRepresentationNormalized {
|
|
|
23
23
|
/** Name of the save option. */
|
|
24
24
|
name: string;
|
|
25
25
|
/** Rest Header Name of the save option. */
|
|
26
|
-
restHeaderName: string;
|
|
26
|
+
restHeaderName: string | null;
|
|
27
27
|
/** Soap Header Name of the save option. */
|
|
28
28
|
soapHeaderName: string;
|
|
29
29
|
}
|
|
@@ -38,6 +38,6 @@ export interface RecordLayoutSaveOptionRepresentation {
|
|
|
38
38
|
isDisplayed: boolean;
|
|
39
39
|
label: string;
|
|
40
40
|
name: string;
|
|
41
|
-
restHeaderName: string;
|
|
41
|
+
restHeaderName: string | null;
|
|
42
42
|
soapHeaderName: string;
|
|
43
43
|
}
|
|
@@ -12,7 +12,7 @@ declare const assign: {
|
|
|
12
12
|
[idx: string]: object | U | null | undefined;
|
|
13
13
|
}, U extends string | number | bigint | boolean | symbol>(o: T_1): Readonly<T_1>;
|
|
14
14
|
<T_2>(o: T_2): Readonly<T_2>;
|
|
15
|
-
}, isFrozen: (o: any) => boolean, keys: {
|
|
15
|
+
}, getPrototypeOf: (o: any) => any, isFrozen: (o: any) => boolean, keys: {
|
|
16
16
|
(o: object): string[];
|
|
17
17
|
(o: {}): string[];
|
|
18
18
|
};
|
|
@@ -39,4 +39,4 @@ declare const parse: (text: string, reviver?: ((this: any, key: string, value: a
|
|
|
39
39
|
(value: any, replacer?: ((this: any, key: string, value: any) => any) | undefined, space?: string | number | undefined): string;
|
|
40
40
|
(value: any, replacer?: (string | number)[] | null | undefined, space?: string | number | undefined): string;
|
|
41
41
|
};
|
|
42
|
-
export { assign as ObjectAssign, create as ObjectCreate, freeze as ObjectFreeze, isFrozen as ObjectIsFrozen, keys as ObjectKeys, hasOwnProperty as ObjectPrototypeHasOwnProperty, isArray as ArrayIsArray, concat as ArrayPrototypeConcat, filter as ArrayPrototypeFilter, includes as ArrayPrototypeIncludes, push as ArrayPrototypePush, reduce as ArrayPrototypeReduce, split as StringPrototypeSplit, endsWith as StringPrototypeEndsWith, parse as JSONParse, stringify as JSONStringify, };
|
|
42
|
+
export { assign as ObjectAssign, create as ObjectCreate, freeze as ObjectFreeze, getPrototypeOf as ObjectGetPrototypeOf, isFrozen as ObjectIsFrozen, keys as ObjectKeys, hasOwnProperty as ObjectPrototypeHasOwnProperty, isArray as ArrayIsArray, concat as ArrayPrototypeConcat, filter as ArrayPrototypeFilter, includes as ArrayPrototypeIncludes, push as ArrayPrototypePush, reduce as ArrayPrototypeReduce, split as StringPrototypeSplit, endsWith as StringPrototypeEndsWith, parse as JSONParse, stringify as JSONStringify, };
|
|
@@ -435,7 +435,7 @@ function buildAdapterValidationConfig(displayName, paramsMeta) {
|
|
|
435
435
|
}
|
|
436
436
|
const keyPrefix = 'UiApi';
|
|
437
437
|
|
|
438
|
-
const { assign, create, freeze, isFrozen, keys } = Object;
|
|
438
|
+
const { assign, create, freeze, getPrototypeOf, isFrozen, keys } = Object;
|
|
439
439
|
const { hasOwnProperty } = Object.prototype;
|
|
440
440
|
const { split, endsWith } = String.prototype;
|
|
441
441
|
const { isArray } = Array;
|
|
@@ -3711,6 +3711,24 @@ function isFieldValueRepresentation(unknown) {
|
|
|
3711
3711
|
}
|
|
3712
3712
|
return 'value' in unknown && 'displayValue' in unknown;
|
|
3713
3713
|
}
|
|
3714
|
+
/**
|
|
3715
|
+
* Whether `value` is a plain data object safe to index into as a record's
|
|
3716
|
+
* `fields` map. getField runs as trusted (system-mode) code walking a caller-
|
|
3717
|
+
* supplied dot-path, so indexing into a host/exotic object (e.g. `window`) or
|
|
3718
|
+
* reading a prototype-chain property (e.g. `__proto__`) would let it read host
|
|
3719
|
+
* state on the caller's behalf -- the same class of confused-deputy sandbox
|
|
3720
|
+
* escape fixed for `getSObjectValue` (W-23862210). Record field maps are
|
|
3721
|
+
* JSON-derived plain objects, so we accept only a prototype chain that ends
|
|
3722
|
+
* immediately at an `Object.prototype` (or `null`), which also keeps
|
|
3723
|
+
* cross-realm/membrane records (LWS) valid.
|
|
3724
|
+
*/
|
|
3725
|
+
function isTraversableFieldsMap(value) {
|
|
3726
|
+
if (typeof value !== 'object' || value === null) {
|
|
3727
|
+
return false;
|
|
3728
|
+
}
|
|
3729
|
+
const proto = getPrototypeOf(value);
|
|
3730
|
+
return proto === null || getPrototypeOf(proto) === null;
|
|
3731
|
+
}
|
|
3714
3732
|
function getField(record, field) {
|
|
3715
3733
|
const fieldApiName = getFieldApiName(field);
|
|
3716
3734
|
if (fieldApiName === undefined) {
|
|
@@ -3720,7 +3738,13 @@ function getField(record, field) {
|
|
|
3720
3738
|
const fields = unqualifiedField.split('.');
|
|
3721
3739
|
let r = record;
|
|
3722
3740
|
while (r && r.fields) {
|
|
3741
|
+
if (isTraversableFieldsMap(r.fields) === false) {
|
|
3742
|
+
return undefined;
|
|
3743
|
+
}
|
|
3723
3744
|
const f = fields.shift();
|
|
3745
|
+
if (!hasOwnProperty.call(r.fields, f)) {
|
|
3746
|
+
return undefined;
|
|
3747
|
+
}
|
|
3724
3748
|
const fvr = r.fields[f];
|
|
3725
3749
|
if (fvr === undefined) {
|
|
3726
3750
|
return undefined;
|
|
@@ -10336,8 +10360,29 @@ function validate$1N(obj, path = 'RecordLayoutSaveOptionRepresentation') {
|
|
|
10336
10360
|
}
|
|
10337
10361
|
const obj_restHeaderName = obj.restHeaderName;
|
|
10338
10362
|
const path_restHeaderName = path + '.restHeaderName';
|
|
10339
|
-
|
|
10340
|
-
|
|
10363
|
+
let obj_restHeaderName_union0 = null;
|
|
10364
|
+
const obj_restHeaderName_union0_error = (() => {
|
|
10365
|
+
if (typeof obj_restHeaderName !== 'string') {
|
|
10366
|
+
return new TypeError('Expected "string" but received "' + typeof obj_restHeaderName + '" (at "' + path_restHeaderName + '")');
|
|
10367
|
+
}
|
|
10368
|
+
})();
|
|
10369
|
+
if (obj_restHeaderName_union0_error != null) {
|
|
10370
|
+
obj_restHeaderName_union0 = obj_restHeaderName_union0_error.message;
|
|
10371
|
+
}
|
|
10372
|
+
let obj_restHeaderName_union1 = null;
|
|
10373
|
+
const obj_restHeaderName_union1_error = (() => {
|
|
10374
|
+
if (obj_restHeaderName !== null) {
|
|
10375
|
+
return new TypeError('Expected "null" but received "' + typeof obj_restHeaderName + '" (at "' + path_restHeaderName + '")');
|
|
10376
|
+
}
|
|
10377
|
+
})();
|
|
10378
|
+
if (obj_restHeaderName_union1_error != null) {
|
|
10379
|
+
obj_restHeaderName_union1 = obj_restHeaderName_union1_error.message;
|
|
10380
|
+
}
|
|
10381
|
+
if (obj_restHeaderName_union0 && obj_restHeaderName_union1) {
|
|
10382
|
+
let message = 'Object doesn\'t match union (at "' + path_restHeaderName + '")';
|
|
10383
|
+
message += '\n' + obj_restHeaderName_union0.split('\n').map((line) => '\t' + line).join('\n');
|
|
10384
|
+
message += '\n' + obj_restHeaderName_union1.split('\n').map((line) => '\t' + line).join('\n');
|
|
10385
|
+
return new TypeError(message);
|
|
10341
10386
|
}
|
|
10342
10387
|
const obj_soapHeaderName = obj.soapHeaderName;
|
|
10343
10388
|
const path_soapHeaderName = path + '.soapHeaderName';
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@salesforce/lds-adapters-uiapi",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.455.0",
|
|
4
4
|
"license": "SEE LICENSE IN LICENSE.txt",
|
|
5
5
|
"description": "Wire adapters for record related UI API endpoints",
|
|
6
6
|
"type": "module",
|
|
@@ -62,15 +62,15 @@
|
|
|
62
62
|
}
|
|
63
63
|
},
|
|
64
64
|
"dependencies": {
|
|
65
|
-
"@luvio/graphql-parser": "0.161.
|
|
66
|
-
"@salesforce/lds-bindings": "^1.
|
|
67
|
-
"@salesforce/lds-default-luvio": "^1.
|
|
65
|
+
"@luvio/graphql-parser": "0.161.2",
|
|
66
|
+
"@salesforce/lds-bindings": "^1.455.0",
|
|
67
|
+
"@salesforce/lds-default-luvio": "^1.455.0"
|
|
68
68
|
},
|
|
69
69
|
"devDependencies": {
|
|
70
|
-
"@salesforce/lds-adapters-onestore-graphql": "^1.
|
|
71
|
-
"@salesforce/lds-compiler-plugins": "^1.
|
|
72
|
-
"@salesforce/lds-jest": "^1.
|
|
73
|
-
"@salesforce/lds-store-binary": "^1.
|
|
70
|
+
"@salesforce/lds-adapters-onestore-graphql": "^1.455.0",
|
|
71
|
+
"@salesforce/lds-compiler-plugins": "^1.455.0",
|
|
72
|
+
"@salesforce/lds-jest": "^1.455.0",
|
|
73
|
+
"@salesforce/lds-store-binary": "^1.455.0"
|
|
74
74
|
},
|
|
75
75
|
"luvioBundlesize": [
|
|
76
76
|
{
|
package/sfdc/graphqlAdapters.js
CHANGED
|
@@ -16264,7 +16264,7 @@ function keyBuilderFromType(luvio, object) {
|
|
|
16264
16264
|
return keyBuilder$z(luvio, keyParams);
|
|
16265
16265
|
}
|
|
16266
16266
|
|
|
16267
|
-
const { assign, create, freeze, isFrozen, keys } = Object;
|
|
16267
|
+
const { assign, create, freeze, getPrototypeOf, isFrozen, keys } = Object;
|
|
16268
16268
|
const { isArray } = Array;
|
|
16269
16269
|
const { concat, filter, includes, push, reduce } = Array.prototype;
|
|
16270
16270
|
|
|
@@ -28845,4 +28845,4 @@ register({
|
|
|
28845
28845
|
});
|
|
28846
28846
|
|
|
28847
28847
|
export { configurationForGraphQLAdapters as configuration, graphql, factory$1 as graphqlAdapterFactory, graphqlBatch, graphqlBatch_imperative, graphql_deprecated, graphql_imperative, graphql_imperative_deprecated, graphql_imperative_onestore, graphql_onestore, graphql_state_manager, refreshGraphQL, refreshGraphQL_deprecated };
|
|
28848
|
-
// version: 1.
|
|
28848
|
+
// version: 1.455.0-96e9b41a18
|
package/sfdc/index.js
CHANGED
|
@@ -492,7 +492,7 @@ function buildAdapterValidationConfig(displayName, paramsMeta) {
|
|
|
492
492
|
}
|
|
493
493
|
const keyPrefix = 'UiApi';
|
|
494
494
|
|
|
495
|
-
const { assign, create, freeze, isFrozen, keys } = Object;
|
|
495
|
+
const { assign, create, freeze, getPrototypeOf, isFrozen, keys } = Object;
|
|
496
496
|
const { hasOwnProperty } = Object.prototype;
|
|
497
497
|
const { split, endsWith } = String.prototype;
|
|
498
498
|
const { isArray } = Array;
|
|
@@ -9971,8 +9971,29 @@ function validate$1J(obj, path = 'RecordLayoutSaveOptionRepresentation') {
|
|
|
9971
9971
|
}
|
|
9972
9972
|
const obj_restHeaderName = obj.restHeaderName;
|
|
9973
9973
|
const path_restHeaderName = path + '.restHeaderName';
|
|
9974
|
-
|
|
9975
|
-
|
|
9974
|
+
let obj_restHeaderName_union0 = null;
|
|
9975
|
+
const obj_restHeaderName_union0_error = (() => {
|
|
9976
|
+
if (typeof obj_restHeaderName !== 'string') {
|
|
9977
|
+
return new TypeError('Expected "string" but received "' + typeof obj_restHeaderName + '" (at "' + path_restHeaderName + '")');
|
|
9978
|
+
}
|
|
9979
|
+
})();
|
|
9980
|
+
if (obj_restHeaderName_union0_error != null) {
|
|
9981
|
+
obj_restHeaderName_union0 = obj_restHeaderName_union0_error.message;
|
|
9982
|
+
}
|
|
9983
|
+
let obj_restHeaderName_union1 = null;
|
|
9984
|
+
const obj_restHeaderName_union1_error = (() => {
|
|
9985
|
+
if (obj_restHeaderName !== null) {
|
|
9986
|
+
return new TypeError('Expected "null" but received "' + typeof obj_restHeaderName + '" (at "' + path_restHeaderName + '")');
|
|
9987
|
+
}
|
|
9988
|
+
})();
|
|
9989
|
+
if (obj_restHeaderName_union1_error != null) {
|
|
9990
|
+
obj_restHeaderName_union1 = obj_restHeaderName_union1_error.message;
|
|
9991
|
+
}
|
|
9992
|
+
if (obj_restHeaderName_union0 && obj_restHeaderName_union1) {
|
|
9993
|
+
let message = 'Object doesn\'t match union (at "' + path_restHeaderName + '")';
|
|
9994
|
+
message += '\n' + obj_restHeaderName_union0.split('\n').map((line) => '\t' + line).join('\n');
|
|
9995
|
+
message += '\n' + obj_restHeaderName_union1.split('\n').map((line) => '\t' + line).join('\n');
|
|
9996
|
+
return new TypeError(message);
|
|
9976
9997
|
}
|
|
9977
9998
|
const obj_soapHeaderName = obj.soapHeaderName;
|
|
9978
9999
|
const path_soapHeaderName = path + '.soapHeaderName';
|
|
@@ -37501,4 +37522,4 @@ withDefaultLuvio((luvio) => {
|
|
|
37501
37522
|
});
|
|
37502
37523
|
|
|
37503
37524
|
export { API_NAMESPACE, VERSION$1i as FieldValueRepresentationVersion, InMemoryRecordRepresentationQueryEvaluator, MRU, RepresentationType$J as ObjectInfoDirectoryEntryRepresentationType, RepresentationType$O as ObjectInfoRepresentationType, RECORD_FIELDS_KEY_JUNCTION, RECORD_ID_PREFIX, RECORD_REPRESENTATION_NAME, RECORD_VIEW_ENTITY_ID_PREFIX, RECORD_VIEW_ENTITY_REPRESENTATION_NAME, RepresentationType$V as RecordRepresentationRepresentationType, TTL$z as RecordRepresentationTTL, RepresentationType$V as RecordRepresentationType, VERSION$1g as RecordRepresentationVersion, keyPrefix as UiApiNamespace, buildRecordRepKeyFromId, getFieldApiNamesArray as coerceFieldIdArray, coerceLayoutModeArray, getLayoutTypeArray as coerceLayoutTypeArray, getObjectApiName$1 as coerceObjectId, getObjectApiNamesArray as coerceObjectIdArray, configurationForRestAdapters as configuration, createContentDocumentAndVersion, createContentVersion, createIngestRecordWithFields, createLDSAdapterWithPrediction, createListInfo, createRecord, deleteListInfo, deleteRecord, executeBatchRecordOperations, extractRecordIdFromStoreKey, getActionOverrides, getActionOverrides_imperative, getAllApps, getAllApps_imperative, getAppDetails, getAppDetails_imperative, getDuplicateConfiguration, getDuplicateConfiguration_imperative, getDuplicates, getDuplicates_imperative, getFlexipageFormulaOverrides, getFlexipageFormulaOverrides_imperative, getGlobalActions, getGlobalActions_imperative, getKeywordSearchResults, getKeywordSearchResults_imperative, getLayout, getLayoutUserState, getLayoutUserState_imperative, getLayout_imperative, getListInfoByName, getListInfoByNameAdapterFactory, getListInfoByName_imperative, getListInfosByName, getListInfosByName_imperative, getListInfosByObjectName, getListInfosByObjectNameAdapterFactory, getListInfosByObjectName_imperative, getListObjectInfo, getListObjectInfoAdapterFactory, getListObjectInfo_imperative, getListPreferences, getListPreferences_imperative, getListRecordsByName, factory$a as getListRecordsByNameAdapterFactory, getListRecordsByName_imperative, getListUi, getListUi_imperative, getLookupActions, getLookupActions_imperative, getLookupMetadata, getLookupMetadata_imperative, getLookupRecords, getLookupRecords_imperative, getNavItems, getNavItems_imperative, getObjectCreateActions, getObjectCreateActions_imperative, getObjectInfo, getObjectInfoAdapterFactory, getObjectInfoDirectoryAdapterFactory, getObjectInfo_imperative, getObjectInfos, getObjectInfosAdapterFactory, getObjectInfos_imperative, getPathLayout, getPathLayout_imperative, getPicklistValues, getPicklistValuesByRecordType, getPicklistValuesByRecordType_imperative, getPicklistValues_imperative, getQuickActionDefaults, getQuickActionDefaults_imperative, getQuickActionInfo, getQuickActionInfo_imperative, getQuickActionLayout, getQuickActionLayout_imperative, getRecord, getRecordActions, getRecordActionsAdapterFactory, getRecordActions_imperative, factory$f as getRecordAdapterFactory, getRecordAvatars, getRecordAvatarsAdapterFactory, getRecordAvatars_imperative, getRecordCreateDefaults, getRecordCreateDefaults_imperative, getRecordEditActions, getRecordEditActions_imperative, getRecordId18, getRecordId18Array, getRecordIngestionOverride, getRecordNotifyChange, getRecordTemplateClone, getRecordTemplateClone_imperative, getRecordTemplateCreate, getRecordTemplateCreate_imperative, getRecordUi, getRecordUi_imperative, getRecord_imperative, getRecords, getRecordsAdapterFactory, getRecords_imperative, getRelatedListActions, getRelatedListActionsAdapterFactory, getRelatedListActions_imperative, getRelatedListCount, getRelatedListCount_imperative, getRelatedListInfo, getRelatedListInfoAdapterFactory, getRelatedListInfoBatch, getRelatedListInfoBatchAdapterFactory, getRelatedListInfoBatch_imperative, getRelatedListInfo_imperative, getRelatedListPreferences, getRelatedListPreferencesBatch, getRelatedListPreferencesBatch_imperative, getRelatedListPreferences_imperative, getRelatedListRecordActions, getRelatedListRecordActions_imperative, getRelatedListRecords, getRelatedListRecordsAdapterFactory, getRelatedListRecordsBatch, getRelatedListRecordsBatchAdapterFactory, getRelatedListRecordsBatch_imperative, getRelatedListRecords_imperative, getRelatedListsActions, getRelatedListsActionsAdapterFactory, getRelatedListsActions_imperative, getRelatedListsCount, getRelatedListsCount_imperative, getRelatedListsInfo, getRelatedListsInfoAdapterFactory, getRelatedListsInfo_imperative, getResponseCacheKeys as getResponseCacheKeysContentDocumentCompositeRepresentation, getSearchFilterMetadata, getSearchFilterMetadata_imperative, getSearchFilterOptions, getSearchFilterOptions_imperative, getSearchResults, getSearchResults_imperative, getTypeCacheKeys$X as getTypeCacheKeysRecord, ingest as ingestContentDocumentCompositeRepresentation, ingest$H as ingestObjectInfo, ingest$B as ingestQuickActionExecutionRepresentation, ingest$O as ingestRecord, instrument, isStoreKeyRecordViewEntity, keyBuilder as keyBuilderContentDocumentCompositeRepresentation, keyBuilderFromType as keyBuilderFromTypeContentDocumentCompositeRepresentation, keyBuilderFromType$E as keyBuilderFromTypeRecordRepresentation, keyBuilder$1Y as keyBuilderObjectInfo, keyBuilder$1R as keyBuilderQuickActionExecutionRepresentation, keyBuilder$29 as keyBuilderRecord, notifyAllListInfoSummaryUpdateAvailable, notifyAllListRecordUpdateAvailable, notifyListInfoSummaryUpdateAvailable, notifyListInfoUpdateAvailable, notifyListRecordCollectionUpdateAvailable, notifyListViewSummaryUpdateAvailable, notifyQuickActionDefaultsUpdateAvailable, notifyRecordUpdateAvailable, performQuickAction, performUpdateRecordQuickAction, refresh, registerPrefetcher, updateLayoutUserState, updateListInfoByName, updateListPreferences, updateRecord, updateRecordAvatar, updateRelatedListInfo, updateRelatedListPreferences };
|
|
37504
|
-
// version: 1.
|
|
37525
|
+
// version: 1.455.0-96e9b41a18
|
|
@@ -99,11 +99,12 @@ var TypeCheckShapes;
|
|
|
99
99
|
TypeCheckShapes[TypeCheckShapes["Integer"] = 3] = "Integer";
|
|
100
100
|
TypeCheckShapes[TypeCheckShapes["Unsupported"] = 4] = "Unsupported";
|
|
101
101
|
})(TypeCheckShapes || (TypeCheckShapes = {}));
|
|
102
|
-
// engine version: 0.161.
|
|
102
|
+
// engine version: 0.161.2-bd1bd38a
|
|
103
103
|
|
|
104
104
|
const { keys: ObjectKeys, create: ObjectCreate } = Object;
|
|
105
105
|
|
|
106
|
-
const { assign, create, freeze, isFrozen, keys } = Object;
|
|
106
|
+
const { assign, create, freeze, getPrototypeOf, isFrozen, keys } = Object;
|
|
107
|
+
const { hasOwnProperty } = Object.prototype;
|
|
107
108
|
|
|
108
109
|
function isString(value) {
|
|
109
110
|
return typeof value === 'string';
|
|
@@ -508,6 +509,24 @@ function isFieldValueRepresentation(unknown) {
|
|
|
508
509
|
}
|
|
509
510
|
return 'value' in unknown && 'displayValue' in unknown;
|
|
510
511
|
}
|
|
512
|
+
/**
|
|
513
|
+
* Whether `value` is a plain data object safe to index into as a record's
|
|
514
|
+
* `fields` map. getField runs as trusted (system-mode) code walking a caller-
|
|
515
|
+
* supplied dot-path, so indexing into a host/exotic object (e.g. `window`) or
|
|
516
|
+
* reading a prototype-chain property (e.g. `__proto__`) would let it read host
|
|
517
|
+
* state on the caller's behalf -- the same class of confused-deputy sandbox
|
|
518
|
+
* escape fixed for `getSObjectValue` (W-23862210). Record field maps are
|
|
519
|
+
* JSON-derived plain objects, so we accept only a prototype chain that ends
|
|
520
|
+
* immediately at an `Object.prototype` (or `null`), which also keeps
|
|
521
|
+
* cross-realm/membrane records (LWS) valid.
|
|
522
|
+
*/
|
|
523
|
+
function isTraversableFieldsMap(value) {
|
|
524
|
+
if (typeof value !== 'object' || value === null) {
|
|
525
|
+
return false;
|
|
526
|
+
}
|
|
527
|
+
const proto = getPrototypeOf(value);
|
|
528
|
+
return proto === null || getPrototypeOf(proto) === null;
|
|
529
|
+
}
|
|
511
530
|
function getField(record, field) {
|
|
512
531
|
const fieldApiName = getFieldApiName(field);
|
|
513
532
|
if (fieldApiName === undefined) {
|
|
@@ -517,7 +536,13 @@ function getField(record, field) {
|
|
|
517
536
|
const fields = unqualifiedField.split('.');
|
|
518
537
|
let r = record;
|
|
519
538
|
while (r && r.fields) {
|
|
539
|
+
if (isTraversableFieldsMap(r.fields) === false) {
|
|
540
|
+
return undefined;
|
|
541
|
+
}
|
|
520
542
|
const f = fields.shift();
|
|
543
|
+
if (!hasOwnProperty.call(r.fields, f)) {
|
|
544
|
+
return undefined;
|
|
545
|
+
}
|
|
521
546
|
const fvr = r.fields[f];
|
|
522
547
|
if (fvr === undefined) {
|
|
523
548
|
return undefined;
|
package/src/raml/api.raml
CHANGED