diff --git a/packages/react-native-codegen/src/parsers/flow/components/componentsUtils.js b/packages/react-native-codegen/src/parsers/flow/components/componentsUtils.js index 0ae12c7cbdc45c..0e6edc9a374f29 100644 --- a/packages/react-native-codegen/src/parsers/flow/components/componentsUtils.js +++ b/packages/react-native-codegen/src/parsers/flow/components/componentsUtils.js @@ -10,10 +10,9 @@ 'use strict'; -import type {ASTNode} from '../utils'; import type {NamedShape} from '../../../CodegenSchema.js'; const {getValueFromTypes} = require('../utils.js'); -import type {TypeDeclarationMap, PropAST} from '../../utils'; +import type {TypeDeclarationMap, PropAST, ASTNode} from '../../utils'; function getProperties( typeName: string, diff --git a/packages/react-native-codegen/src/parsers/flow/components/props.js b/packages/react-native-codegen/src/parsers/flow/components/props.js index a55b5a43025223..acf74e49bc2954 100644 --- a/packages/react-native-codegen/src/parsers/flow/components/props.js +++ b/packages/react-native-codegen/src/parsers/flow/components/props.js @@ -23,36 +23,13 @@ const { getSchemaInfo, getTypeAnnotation, } = require('./componentsUtils.js'); +const {buildPropSchema} = require('../../parsers-commons'); type ExtendsForProp = null | { type: 'ReactNativeBuiltInType', knownTypeName: 'ReactNativeCoreViewProps', }; -function buildPropSchema( - property: PropAST, - types: TypeDeclarationMap, -): ?NamedShape { - const info = getSchemaInfo(property, types); - if (info == null) { - return null; - } - const {name, optional, typeAnnotation, defaultValue, withNullDefault} = info; - - return { - name, - optional, - typeAnnotation: getTypeAnnotation( - name, - typeAnnotation, - defaultValue, - withNullDefault, - types, - buildPropSchema, - ), - }; -} - function extendsForProp( prop: PropAST, types: TypeDeclarationMap, @@ -117,7 +94,9 @@ function getProps( } { const nonExtendsProps = removeKnownExtends(typeDefinition, types, parser); const props = flattenProperties(nonExtendsProps, types) - .map(property => buildPropSchema(property, types)) + .map(property => + buildPropSchema(property, types, getSchemaInfo, getTypeAnnotation), + ) .filter(Boolean); return { diff --git a/packages/react-native-codegen/src/parsers/flow/utils.js b/packages/react-native-codegen/src/parsers/flow/utils.js index 3692cf16f89b7c..258c9258512fc0 100644 --- a/packages/react-native-codegen/src/parsers/flow/utils.js +++ b/packages/react-native-codegen/src/parsers/flow/utils.js @@ -10,10 +10,7 @@ 'use strict'; -import type {TypeResolutionStatus, TypeDeclarationMap} from '../utils'; - -// $FlowFixMe[unclear-type] there's no flowtype for ASTs -export type ASTNode = Object; +import type {TypeResolutionStatus, TypeDeclarationMap, ASTNode} from '../utils'; const invariant = require('invariant'); diff --git a/packages/react-native-codegen/src/parsers/parsers-commons.js b/packages/react-native-codegen/src/parsers/parsers-commons.js index e98581ef28bf01..c9a0cb4de51325 100644 --- a/packages/react-native-codegen/src/parsers/parsers-commons.js +++ b/packages/react-native-codegen/src/parsers/parsers-commons.js @@ -23,11 +23,17 @@ import type { SchemaType, NativeModuleEnumMap, OptionsShape, + PropTypeAnnotation, } from '../CodegenSchema.js'; import type {Parser} from './parser'; import type {ParserType} from './errors'; -import type {ParserErrorCapturer, TypeDeclarationMap, PropAST} from './utils'; +import type { + ParserErrorCapturer, + TypeDeclarationMap, + PropAST, + ASTNode, +} from './utils'; import type {ComponentSchemaBuilderConfig} from './schema.js'; const { @@ -852,6 +858,54 @@ function extendsForProp( } } +type SchemaInfo = { + name: string, + optional: boolean, + typeAnnotation: $FlowFixMe, + defaultValue: $FlowFixMe, + withNullDefault: boolean, +}; + +function buildPropSchema( + property: PropAST, + types: TypeDeclarationMap, + getSchemaInfo: (property: PropAST, types: TypeDeclarationMap) => ?SchemaInfo, + getTypeAnnotation: ( + name: string, + annotation: $FlowFixMe | ASTNode, + defaultValue: $FlowFixMe | void, + withNullDefault: boolean, + types: TypeDeclarationMap, + buildSchema: (property: PropAST, types: TypeDeclarationMap) => $FlowFixMe, + ) => $FlowFixMe, +): ?NamedShape { + const info = getSchemaInfo(property, types); + if (info == null) { + return null; + } + const {name, optional, typeAnnotation, defaultValue, withNullDefault} = info; + + const wrappedBuildSchema = ( + passedProps: PropAST, + passedTypes: TypeDeclarationMap, + ): $FlowFixMe => { + buildPropSchema(passedProps, passedTypes, getSchemaInfo, getTypeAnnotation); + }; + + return { + name, + optional, + typeAnnotation: getTypeAnnotation( + name, + typeAnnotation, + defaultValue, + withNullDefault, + types, + wrappedBuildSchema, + ), + }; +} + module.exports = { wrapModuleSchema, unwrapNullable, @@ -872,4 +926,5 @@ module.exports = { getOptions, getCommandTypeNameAndOptionsExpression, extendsForProp, + buildPropSchema, }; diff --git a/packages/react-native-codegen/src/parsers/typescript/components/componentsUtils.js b/packages/react-native-codegen/src/parsers/typescript/components/componentsUtils.js index ba8efb7ce7a5ce..a1c8a82e57c6b5 100644 --- a/packages/react-native-codegen/src/parsers/typescript/components/componentsUtils.js +++ b/packages/react-native-codegen/src/parsers/typescript/components/componentsUtils.js @@ -9,13 +9,12 @@ */ 'use strict'; -import type {ASTNode} from '../utils'; import type {NamedShape} from '../../../CodegenSchema.js'; const { parseTopLevelType, flattenIntersectionType, } = require('../parseTopLevelType'); -import type {TypeDeclarationMap, PropAST} from '../../utils'; +import type {TypeDeclarationMap, PropAST, ASTNode} from '../../utils'; function getProperties( typeName: string, @@ -370,7 +369,7 @@ function getTypeAnnotation( name: string, annotation: $FlowFixMe | ASTNode, defaultValue: $FlowFixMe | void, - withNullDefault: boolean, + withNullDefault: boolean, // Just to make `getTypeAnnotation` signature match with the one from Flow types: TypeDeclarationMap, buildSchema: (property: PropAST, types: TypeDeclarationMap) => ?NamedShape, ): $FlowFixMe { @@ -436,6 +435,7 @@ type SchemaInfo = { optional: boolean, typeAnnotation: $FlowFixMe, defaultValue: $FlowFixMe, + withNullDefault: boolean, // Just to make `getTypeAnnotation` signature match with the one from Flow }; function getSchemaInfo( @@ -461,6 +461,7 @@ function getSchemaInfo( optional: property.optional || topLevelType.optional, typeAnnotation: topLevelType.type, defaultValue: topLevelType.defaultValue, + withNullDefault: false, // Just to make `getTypeAnnotation` signature match with the one from Flow }; } diff --git a/packages/react-native-codegen/src/parsers/typescript/components/props.js b/packages/react-native-codegen/src/parsers/typescript/components/props.js index 392f7c5b0c3e7d..063805e41eab8f 100644 --- a/packages/react-native-codegen/src/parsers/typescript/components/props.js +++ b/packages/react-native-codegen/src/parsers/typescript/components/props.js @@ -19,27 +19,7 @@ import type {Parser} from '../../parser'; const {flattenProperties} = require('./componentsUtils.js'); const {parseTopLevelType} = require('../parseTopLevelType'); -const {extendsForProp} = require('../../parsers-commons'); - -function buildPropSchema( - property: PropAST, - types: TypeDeclarationMap, -): NamedShape { - const info = getSchemaInfo(property, types); - const {name, optional, typeAnnotation, defaultValue} = info; - return { - name, - optional, - typeAnnotation: getTypeAnnotation( - name, - typeAnnotation, - defaultValue, - false, // Just to make `getTypeAnnotation` signature match with the one from Flow - types, - buildPropSchema, - ), - }; -} +const {buildPropSchema, extendsForProp} = require('../../parsers-commons'); function isEvent(typeAnnotation: $FlowFixMe): boolean { if (typeAnnotation.type !== 'TSTypeReference') { @@ -102,7 +82,9 @@ function getProps( } return { - props: componentPropAsts.map(property => buildPropSchema(property, types)), + props: componentPropAsts.map(property => + buildPropSchema(property, types, getSchemaInfo, getTypeAnnotation), + ), extendsProps, }; } diff --git a/packages/react-native-codegen/src/parsers/typescript/utils.js b/packages/react-native-codegen/src/parsers/typescript/utils.js index ffb7145d620852..e555ff5fe4e2c4 100644 --- a/packages/react-native-codegen/src/parsers/typescript/utils.js +++ b/packages/react-native-codegen/src/parsers/typescript/utils.js @@ -14,9 +14,6 @@ import type {TypeResolutionStatus, TypeDeclarationMap} from '../utils'; const {parseTopLevelType} = require('./parseTopLevelType'); -// $FlowFixMe[unclear-type] Use flow-types for @babel/parser -export type ASTNode = Object; - const invariant = require('invariant'); function resolveTypeAnnotation( diff --git a/packages/react-native-codegen/src/parsers/utils.js b/packages/react-native-codegen/src/parsers/utils.js index 56d93491273252..5c904c6c80fecf 100644 --- a/packages/react-native-codegen/src/parsers/utils.js +++ b/packages/react-native-codegen/src/parsers/utils.js @@ -37,6 +37,9 @@ export type ParserErrorCapturer = (fn: () => T) => ?T; // $FlowFixMe[unclear-type] there's no flowtype for ASTs export type PropAST = Object; +// $FlowFixMe[unclear-type] there's no flowtype for ASTs +export type ASTNode = Object; + function createParserErrorCapturer(): [ Array, ParserErrorCapturer,