mirror of
https://github.com/react/react-native-devtools-frontend.git
synced 2026-10-02 18:11:04 +08:00
Signed-off-by: Victor Porof <victorporof@chromium.org> Bug: 1325812 Change-Id: I044170880d20ce0402062755787cccafd63c6a42 Reviewed-on: https://chromium-review.googlesource.com/c/devtools/devtools-frontend/+/3695370 Reviewed-by: Mathias Bynens <mathias@chromium.org>
83 lines
2.6 KiB
JavaScript
83 lines
2.6 KiB
JavaScript
/**
|
|
* @typedef {import("../productions/dictionary.js").Dictionary} Dictionary
|
|
*
|
|
* @param {*} idlType
|
|
* @param {import("../validator.js").Definitions} defs
|
|
* @param {object} [options]
|
|
* @param {boolean} [options.useNullableInner] use when the input idlType is nullable and you want to use its inner type
|
|
* @return {{ reference: *, dictionary: Dictionary }} the type reference that ultimately includes dictionary.
|
|
*/
|
|
export function idlTypeIncludesDictionary(
|
|
idlType,
|
|
defs,
|
|
{ useNullableInner } = {}
|
|
) {
|
|
if (!idlType.union) {
|
|
const def = defs.unique.get(idlType.idlType);
|
|
if (!def) {
|
|
return;
|
|
}
|
|
if (def.type === "typedef") {
|
|
const { typedefIncludesDictionary } = defs.cache;
|
|
if (typedefIncludesDictionary.has(def)) {
|
|
// Note that this also halts when it met indeterminate state
|
|
// to prevent infinite recursion
|
|
return typedefIncludesDictionary.get(def);
|
|
}
|
|
defs.cache.typedefIncludesDictionary.set(def, undefined); // indeterminate state
|
|
const result = idlTypeIncludesDictionary(def.idlType, defs);
|
|
defs.cache.typedefIncludesDictionary.set(def, result);
|
|
if (result) {
|
|
return {
|
|
reference: idlType,
|
|
dictionary: result.dictionary,
|
|
};
|
|
}
|
|
}
|
|
if (def.type === "dictionary" && (useNullableInner || !idlType.nullable)) {
|
|
return {
|
|
reference: idlType,
|
|
dictionary: def,
|
|
};
|
|
}
|
|
}
|
|
for (const subtype of idlType.subtype) {
|
|
const result = idlTypeIncludesDictionary(subtype, defs);
|
|
if (result) {
|
|
if (subtype.union) {
|
|
return result;
|
|
}
|
|
return {
|
|
reference: subtype,
|
|
dictionary: result.dictionary,
|
|
};
|
|
}
|
|
}
|
|
}
|
|
|
|
/**
|
|
* @param {*} dict dictionary type
|
|
* @param {import("../validator.js").Definitions} defs
|
|
* @return {boolean}
|
|
*/
|
|
export function dictionaryIncludesRequiredField(dict, defs) {
|
|
if (defs.cache.dictionaryIncludesRequiredField.has(dict)) {
|
|
return defs.cache.dictionaryIncludesRequiredField.get(dict);
|
|
}
|
|
// Set cached result to indeterminate to short-circuit circular definitions.
|
|
// The final result will be updated to true or false.
|
|
defs.cache.dictionaryIncludesRequiredField.set(dict, undefined);
|
|
let result = dict.members.some((field) => field.required);
|
|
if (!result && dict.inheritance) {
|
|
const superdict = defs.unique.get(dict.inheritance);
|
|
if (!superdict) {
|
|
// Assume required members in the supertype if it is unknown.
|
|
result = true;
|
|
} else if (dictionaryIncludesRequiredField(superdict, defs)) {
|
|
result = true;
|
|
}
|
|
}
|
|
defs.cache.dictionaryIncludesRequiredField.set(dict, result);
|
|
return result;
|
|
}
|