diff --git a/packages/react-native-codegen/src/parsers/errors.js b/packages/react-native-codegen/src/parsers/errors.js index 41fc7f8ca4e..dee4483ea63 100644 --- a/packages/react-native-codegen/src/parsers/errors.js +++ b/packages/react-native-codegen/src/parsers/errors.js @@ -10,14 +10,18 @@ 'use strict'; +const invariant = require('invariant'); + +type ParserType = 'Flow' | 'TypeScript'; + class ParserError extends Error { nodes: $ReadOnlyArray<$FlowFixMe>; constructor( - hasteModuleName: string, + nativeModuleName: string, astNodeOrNodes: $FlowFixMe, message: string, ) { - super(`Module ${hasteModuleName}: ${message}`); + super(`Module ${nativeModuleName}: ${message}`); this.nodes = Array.isArray(astNodeOrNodes) ? astNodeOrNodes @@ -31,6 +35,413 @@ class ParserError extends Error { } } +class MisnamedModuleInterfaceParserError extends ParserError { + constructor(nativeModuleName: string, id: $FlowFixMe, language: ParserType) { + super( + nativeModuleName, + id, + `All ${language} interfaces extending TurboModule must be called 'Spec'. Please rename ${language} interface '${id.name}' to 'Spec'.`, + ); + } +} + +class ModuleInterfaceNotFoundParserError extends ParserError { + constructor(nativeModuleName: string, ast: $FlowFixMe, language: ParserType) { + super( + nativeModuleName, + ast, + `No ${language} interfaces extending TurboModule were detected in this NativeModule spec.`, + ); + } +} + +class MoreThanOneModuleInterfaceParserError extends ParserError { + constructor( + nativeModuleName: string, + flowModuleInterfaces: $ReadOnlyArray<$FlowFixMe>, + names: $ReadOnlyArray, + language: ParserType, + ) { + const finalName = names[names.length - 1]; + const allButLastName = names.slice(0, -1); + const quote = (x: string) => `'${x}'`; + + const nameStr = + allButLastName.map(quote).join(', ') + ', and ' + quote(finalName); + + super( + nativeModuleName, + flowModuleInterfaces, + `Every NativeModule spec file must declare exactly one NativeModule ${language} interface. This file declares ${names.length}: ${nameStr}. Please remove the extraneous ${language} interface declarations.`, + ); + } +} + +class UnsupportedModulePropertyParserError extends ParserError { + constructor( + nativeModuleName: string, + propertyValue: $FlowFixMe, + propertyName: string, + invalidPropertyValueType: string, + language: ParserType, + ) { + super( + nativeModuleName, + propertyValue, + `${language} interfaces extending TurboModule must only contain 'FunctionTypeAnnotation's. Property '${propertyName}' refers to a '${invalidPropertyValueType}'.`, + ); + } +} + +class UnsupportedTypeAnnotationParserError extends ParserError { + +typeAnnotationType: string; + constructor( + nativeModuleName: string, + typeAnnotation: $FlowFixMe, + language: ParserType, + ) { + super( + nativeModuleName, + typeAnnotation, + `${language} type annotation '${typeAnnotation.type}' is unsupported in NativeModule specs.`, + ); + + this.typeAnnotationType = typeAnnotation.type; + } +} + +class UnsupportedGenericParserError extends ParserError { + +genericName: string; + constructor( + nativeModuleName: string, + genericTypeAnnotation: $FlowFixMe, + language: ParserType, + ) { + const genericName = + language === 'TypeScript' + ? genericTypeAnnotation.typeName.name + : genericTypeAnnotation.id.name; + super( + nativeModuleName, + genericTypeAnnotation, + `Unrecognized generic type '${genericName}' in NativeModule spec.`, + ); + + this.genericName = genericName; + } +} + +class IncorrectlyParameterizedGenericParserError extends ParserError { + +genericName: string; + +numTypeParameters: number; + + // $FlowFixMe[missing-local-annot] + constructor( + nativeModuleName: string, + genericTypeAnnotation: $FlowFixMe, + language: ParserType, + ) { + const genericName = + language === 'TypeScript' + ? genericTypeAnnotation.typeName.name + : genericTypeAnnotation.id.name; + if (genericTypeAnnotation.typeParameters == null) { + super( + nativeModuleName, + genericTypeAnnotation, + `Generic '${genericName}' must have type parameters.`, + ); + return; + } + + if ( + genericTypeAnnotation.typeParameters.type === + 'TypeParameterInstantiation' && + genericTypeAnnotation.typeParameters.params.length !== 1 + ) { + super( + nativeModuleName, + genericTypeAnnotation.typeParameters, + `Generic '${genericName}' must have exactly one type parameter.`, + ); + return; + } + + invariant( + false, + "Couldn't create IncorrectlyParameterizedGenericParserError", + ); + } +} + +/** + * Array parsing errors + */ + +class UnsupportedArrayElementTypeAnnotationParserError extends ParserError { + constructor( + nativeModuleName: string, + arrayElementTypeAST: $FlowFixMe, + arrayType: 'Array' | '$ReadOnlyArray' | 'ReadonlyArray', + invalidArrayElementType: string, + language: ParserType, + ) { + super( + nativeModuleName, + arrayElementTypeAST, + `${arrayType} element types cannot be '${invalidArrayElementType}'.`, + ); + } +} + +/** + * Object parsing errors + */ + +class UnsupportedObjectPropertyTypeAnnotationParserError extends ParserError { + constructor( + nativeModuleName: string, + propertyAST: $FlowFixMe, + invalidPropertyType: string, + language: ParserType, + ) { + let message = `'ObjectTypeAnnotation' cannot contain '${invalidPropertyType}'.`; + + if ( + invalidPropertyType === 'ObjectTypeSpreadProperty' && + language !== 'TypeScript' + ) { + message = "Object spread isn't supported in 'ObjectTypeAnnotation's."; + } + + super(nativeModuleName, propertyAST, message); + } +} + +class UnsupportedObjectPropertyValueTypeAnnotationParserError extends ParserError { + constructor( + nativeModuleName: string, + propertyValueAST: $FlowFixMe, + propertyName: string, + invalidPropertyValueType: string, + language: ParserType, + ) { + super( + nativeModuleName, + propertyValueAST, + `Object property '${propertyName}' cannot have type '${invalidPropertyValueType}'.`, + ); + } +} + +/** + * Function parsing errors + */ + +class UnnamedFunctionParamParserError extends ParserError { + constructor( + functionParam: $FlowFixMe, + nativeModuleName: string, + language: ParserType, + ) { + super( + nativeModuleName, + functionParam, + 'All function parameters must be named.', + ); + } +} + +class UnsupportedFunctionParamTypeAnnotationParserError extends ParserError { + constructor( + nativeModuleName: string, + flowParamTypeAnnotation: $FlowFixMe, + paramName: string, + invalidParamType: string, + language: ParserType, + ) { + super( + nativeModuleName, + flowParamTypeAnnotation, + `Function parameter '${paramName}' cannot have type '${invalidParamType}'.`, + ); + } +} + +class UnsupportedFunctionReturnTypeAnnotationParserError extends ParserError { + constructor( + nativeModuleName: string, + flowReturnTypeAnnotation: $FlowFixMe, + invalidReturnType: string, + language: ParserType, + ) { + super( + nativeModuleName, + flowReturnTypeAnnotation, + `Function return cannot have type '${invalidReturnType}'.`, + ); + } +} + +/** + * Enum parsing errors + */ + +class UnsupportedEnumDeclarationParserError extends ParserError { + constructor( + nativeModuleName: string, + arrayElementTypeAST: $FlowFixMe, + memberType: string, + language: ParserType, + ) { + super( + nativeModuleName, + arrayElementTypeAST, + `Unexpected enum member type ${memberType}. Only string and number enum members are supported`, + ); + } +} + +/** + * Union parsing errors + */ + +class UnsupportedUnionTypeAnnotationParserError extends ParserError { + constructor( + nativeModuleName: string, + arrayElementTypeAST: $FlowFixMe, + types: string[], + language: ParserType, + ) { + super( + nativeModuleName, + arrayElementTypeAST, + `Union members must be of the same type, but multiple types were found ${types.join( + ', ', + )}'.`, + ); + } +} + +/** + * Module parsing errors + */ + +class UnusedModuleInterfaceParserError extends ParserError { + constructor( + nativeModuleName: string, + flowInterface: $FlowFixMe, + language: ParserType, + ) { + super( + nativeModuleName, + flowInterface, + "Unused NativeModule spec. Please load the NativeModule by calling TurboModuleRegistry.get('').", + ); + } +} + +class MoreThanOneModuleRegistryCallsParserError extends ParserError { + constructor( + nativeModuleName: string, + flowCallExpressions: $FlowFixMe, + numCalls: number, + language: ParserType, + ) { + super( + nativeModuleName, + flowCallExpressions, + `Every NativeModule spec file must contain exactly one NativeModule load. This file contains ${numCalls}. Please simplify this spec file, splitting it as necessary, to remove the extraneous loads.`, + ); + } +} + +class UntypedModuleRegistryCallParserError extends ParserError { + constructor( + nativeModuleName: string, + flowCallExpression: $FlowFixMe, + methodName: string, + moduleName: string, + language: ParserType, + ) { + super( + nativeModuleName, + flowCallExpression, + `Please type this NativeModule load: TurboModuleRegistry.${methodName}('${moduleName}').`, + ); + } +} + +class IncorrectModuleRegistryCallTypeParameterParserError extends ParserError { + constructor( + nativeModuleName: string, + flowTypeArguments: $FlowFixMe, + methodName: string, + moduleName: string, + language: ParserType, + ) { + super( + nativeModuleName, + flowTypeArguments, + `Please change these type arguments to reflect TurboModuleRegistry.${methodName}('${moduleName}').`, + ); + } +} + +class IncorrectModuleRegistryCallArityParserError extends ParserError { + constructor( + nativeModuleName: string, + flowCallExpression: $FlowFixMe, + methodName: string, + incorrectArity: number, + language: ParserType, + ) { + super( + nativeModuleName, + flowCallExpression, + `Please call TurboModuleRegistry.${methodName}() with exactly one argument. Detected ${incorrectArity}.`, + ); + } +} + +class IncorrectModuleRegistryCallArgumentTypeParserError extends ParserError { + constructor( + nativeModuleName: string, + flowArgument: $FlowFixMe, + methodName: string, + type: string, + language: ParserType, + ) { + const a = /[aeiouy]/.test(type.toLowerCase()) ? 'an' : 'a'; + super( + nativeModuleName, + flowArgument, + `Please call TurboModuleRegistry.${methodName}() with a string literal. Detected ${a} '${type}'`, + ); + } +} + module.exports = { ParserError, + IncorrectlyParameterizedGenericParserError, + MisnamedModuleInterfaceParserError, + ModuleInterfaceNotFoundParserError, + MoreThanOneModuleInterfaceParserError, + UnnamedFunctionParamParserError, + UnsupportedArrayElementTypeAnnotationParserError, + UnsupportedGenericParserError, + UnsupportedTypeAnnotationParserError, + UnsupportedFunctionParamTypeAnnotationParserError, + UnsupportedFunctionReturnTypeAnnotationParserError, + UnsupportedEnumDeclarationParserError, + UnsupportedUnionTypeAnnotationParserError, + UnsupportedModulePropertyParserError, + UnsupportedObjectPropertyTypeAnnotationParserError, + UnsupportedObjectPropertyValueTypeAnnotationParserError, + UnusedModuleInterfaceParserError, + MoreThanOneModuleRegistryCallsParserError, + UntypedModuleRegistryCallParserError, + IncorrectModuleRegistryCallTypeParameterParserError, + IncorrectModuleRegistryCallArityParserError, + IncorrectModuleRegistryCallArgumentTypeParserError, }; diff --git a/packages/react-native-codegen/src/parsers/flow/modules/__tests__/module-parser-e2e-test.js b/packages/react-native-codegen/src/parsers/flow/modules/__tests__/module-parser-e2e-test.js index c40bbf8ecac..f4eb8f4a852 100644 --- a/packages/react-native-codegen/src/parsers/flow/modules/__tests__/module-parser-e2e-test.js +++ b/packages/react-native-codegen/src/parsers/flow/modules/__tests__/module-parser-e2e-test.js @@ -18,11 +18,11 @@ import type { const {parseString} = require('../../index.js'); const {unwrapNullable} = require('../../../parsers-commons'); const { - UnsupportedFlowGenericParserError, - UnsupportedFlowTypeAnnotationParserError, + UnsupportedGenericParserError, + UnsupportedTypeAnnotationParserError, UnnamedFunctionParamParserError, - IncorrectlyParameterizedFlowGenericParserError, -} = require('../errors'); + IncorrectlyParameterizedGenericParserError, +} = require('../../../errors'); const invariant = require('invariant'); type PrimitiveTypeAnnotationType = @@ -87,7 +87,7 @@ describe('Flow Module Parser', () => { export default TurboModuleRegistry.get('Foo'); `); - expect(parser).toThrow(UnsupportedFlowTypeAnnotationParserError); + expect(parser).toThrow(UnsupportedTypeAnnotationParserError); }); it('should fail parsing when a function param type is unamed', () => { @@ -173,7 +173,7 @@ describe('Flow Module Parser', () => { () => { it(`should not parse methods that have ${PARAM_TYPE_DESCRIPTION} parameter of type 'Function'`, () => { expect(() => parseParamType('arg', 'Function')).toThrow( - UnsupportedFlowGenericParserError, + UnsupportedGenericParserError, ); }); @@ -212,7 +212,7 @@ describe('Flow Module Parser', () => { describe('Array Types', () => { it(`should not parse methods that have ${PARAM_TYPE_DESCRIPTION} parameter of type 'Array'`, () => { expect(() => parseParamType('arg', 'Array')).toThrow( - IncorrectlyParameterizedFlowGenericParserError, + IncorrectlyParameterizedGenericParserError, ); }); @@ -510,7 +510,7 @@ describe('Flow Module Parser', () => { it(`should not parse methods that have ${PARAM_TYPE_DESCRIPTION} parameter type of an object literal with ${PROP_TYPE_DESCRIPTION} prop of type 'Array`, () => { expect(() => parseParamTypeObjectLiteralProp('prop', 'Array'), - ).toThrow(IncorrectlyParameterizedFlowGenericParserError); + ).toThrow(IncorrectlyParameterizedGenericParserError); }); function parseArrayElementType( @@ -782,7 +782,7 @@ describe('Flow Module Parser', () => { describe('Array Types', () => { it(`should not parse methods that have ${RETURN_TYPE_DESCRIPTION} return of type 'Array'`, () => { expect(() => parseReturnType('Array')).toThrow( - IncorrectlyParameterizedFlowGenericParserError, + IncorrectlyParameterizedGenericParserError, ); }); @@ -884,7 +884,7 @@ describe('Flow Module Parser', () => { it(`should not parse methods that have ${RETURN_TYPE_DESCRIPTION} return of type 'Function'`, () => { expect(() => parseReturnType('Function')).toThrow( - UnsupportedFlowGenericParserError, + UnsupportedGenericParserError, ); }); @@ -1050,7 +1050,7 @@ describe('Flow Module Parser', () => { it(`should not parse methods that have ${RETURN_TYPE_DESCRIPTION} return type of an object literal with ${PROP_TYPE_DESCRIPTION} prop of type 'Array`, () => { expect(() => parseObjectLiteralReturnTypeProp('prop', 'Array'), - ).toThrow(IncorrectlyParameterizedFlowGenericParserError); + ).toThrow(IncorrectlyParameterizedGenericParserError); }); function parseArrayElementType( diff --git a/packages/react-native-codegen/src/parsers/flow/modules/errors.js b/packages/react-native-codegen/src/parsers/flow/modules/errors.js deleted file mode 100644 index d0929f36896..00000000000 --- a/packages/react-native-codegen/src/parsers/flow/modules/errors.js +++ /dev/null @@ -1,380 +0,0 @@ -/** - * Copyright (c) Meta Platforms, Inc. and affiliates. - * - * This source code is licensed under the MIT license found in the - * LICENSE file in the root directory of this source tree. - * - * @flow strict-local - * @format - */ - -'use strict'; - -const invariant = require('invariant'); -const {ParserError} = require('../../errors'); - -class MisnamedModuleFlowInterfaceParserError extends ParserError { - constructor(hasteModuleName: string, id: $FlowFixMe) { - super( - hasteModuleName, - id, - `All Flow interfaces extending TurboModule must be called 'Spec'. Please rename Flow interface '${id.name}' to 'Spec'.`, - ); - } -} - -class ModuleFlowInterfaceNotFoundParserError extends ParserError { - constructor(hasteModuleName: string, ast: $FlowFixMe) { - super( - hasteModuleName, - ast, - 'No Flow interfaces extending TurboModule were detected in this NativeModule spec.', - ); - } -} - -class MoreThanOneModuleFlowInterfaceParserError extends ParserError { - constructor( - hasteModuleName: string, - flowModuleInterfaces: $ReadOnlyArray<$FlowFixMe>, - names: $ReadOnlyArray, - ) { - const finalName = names[names.length - 1]; - const allButLastName = names.slice(0, -1); - const quote = (x: string) => `'${x}'`; - - const nameStr = - allButLastName.map(quote).join(', ') + ', and ' + quote(finalName); - - super( - hasteModuleName, - flowModuleInterfaces, - `Every NativeModule spec file must declare exactly one NativeModule Flow interface. This file declares ${names.length}: ${nameStr}. Please remove the extraneous Flow interface declarations.`, - ); - } -} - -class UnsupportedModulePropertyParserError extends ParserError { - constructor( - hasteModuleName: string, - propertyValue: $FlowFixMe, - propertyName: string, - invalidPropertyValueType: string, - ) { - super( - hasteModuleName, - propertyValue, - `Flow interfaces extending TurboModule must only contain 'FunctionTypeAnnotation's. Property '${propertyName}' refers to a '${invalidPropertyValueType}'.`, - ); - } -} - -class UnsupportedFlowTypeAnnotationParserError extends ParserError { - +typeAnnotationType: string; - constructor(hasteModuleName: string, typeAnnotation: $FlowFixMe) { - super( - hasteModuleName, - typeAnnotation, - `Flow type annotation '${typeAnnotation.type}' is unsupported in NativeModule specs.`, - ); - - this.typeAnnotationType = typeAnnotation.type; - } -} - -class UnsupportedFlowGenericParserError extends ParserError { - +genericName: string; - constructor(hasteModuleName: string, genericTypeAnnotation: $FlowFixMe) { - const genericName = genericTypeAnnotation.id.name; - super( - hasteModuleName, - genericTypeAnnotation, - `Unrecognized generic type '${genericName}' in NativeModule spec.`, - ); - - this.genericName = genericName; - } -} - -class IncorrectlyParameterizedFlowGenericParserError extends ParserError { - +genericName: string; - +numTypeParameters: number; - - // $FlowFixMe[missing-local-annot] - constructor(hasteModuleName: string, genericTypeAnnotation: $FlowFixMe) { - if (genericTypeAnnotation.typeParameters == null) { - super( - hasteModuleName, - genericTypeAnnotation, - `Generic '${genericTypeAnnotation.id.name}' must have type parameters.`, - ); - return; - } - - if ( - genericTypeAnnotation.typeParameters.type === - 'TypeParameterInstantiation' && - genericTypeAnnotation.typeParameters.params.length !== 1 - ) { - super( - hasteModuleName, - genericTypeAnnotation.typeParameters, - `Generic '${genericTypeAnnotation.id.name}' must have exactly one type parameter.`, - ); - return; - } - - invariant( - false, - "Couldn't create IncorrectlyParameterizedFlowGenericParserError", - ); - } -} - -/** - * Array parsing errors - */ - -class UnsupportedArrayElementTypeAnnotationParserError extends ParserError { - constructor( - hasteModuleName: string, - arrayElementTypeAST: $FlowFixMe, - arrayType: 'Array' | '$ReadOnlyArray', - invalidArrayElementType: string, - ) { - super( - hasteModuleName, - arrayElementTypeAST, - `${arrayType} element types cannot be '${invalidArrayElementType}'.`, - ); - } -} - -/** - * Object parsing errors - */ - -class UnsupportedObjectPropertyTypeAnnotationParserError extends ParserError { - constructor( - hasteModuleName: string, - propertyAST: $FlowFixMe, - invalidPropertyType: string, - ) { - let message = `'ObjectTypeAnnotation' cannot contain '${invalidPropertyType}'.`; - - if (invalidPropertyType === 'ObjectTypeSpreadProperty') { - message = "Object spread isn't supported in 'ObjectTypeAnnotation's."; - } - - super(hasteModuleName, propertyAST, message); - } -} - -class UnsupportedObjectPropertyValueTypeAnnotationParserError extends ParserError { - constructor( - hasteModuleName: string, - propertyValueAST: $FlowFixMe, - propertyName: string, - invalidPropertyValueType: string, - ) { - super( - hasteModuleName, - propertyValueAST, - `Object property '${propertyName}' cannot have type '${invalidPropertyValueType}'.`, - ); - } -} - -/** - * Function parsing errors - */ - -class UnnamedFunctionParamParserError extends ParserError { - constructor(functionParam: $FlowFixMe, hasteModuleName: string) { - super( - hasteModuleName, - functionParam, - 'All function parameters must be named.', - ); - } -} - -class UnsupportedFunctionParamTypeAnnotationParserError extends ParserError { - constructor( - hasteModuleName: string, - flowParamTypeAnnotation: $FlowFixMe, - paramName: string, - invalidParamType: string, - ) { - super( - hasteModuleName, - flowParamTypeAnnotation, - `Function parameter '${paramName}' cannot have type '${invalidParamType}'.`, - ); - } -} - -class UnsupportedFunctionReturnTypeAnnotationParserError extends ParserError { - constructor( - hasteModuleName: string, - flowReturnTypeAnnotation: $FlowFixMe, - invalidReturnType: string, - ) { - super( - hasteModuleName, - flowReturnTypeAnnotation, - `Function return cannot have type '${invalidReturnType}'.`, - ); - } -} - -/** - * Enum parsing errors - */ - -class UnsupportedEnumDeclarationParserError extends ParserError { - constructor( - hasteModuleName: string, - arrayElementTypeAST: $FlowFixMe, - memberType: string, - ) { - super( - hasteModuleName, - arrayElementTypeAST, - `Unexpected enum member type ${memberType}. Only string and number enum members are supported`, - ); - } -} - -/** - * Union parsing errors - */ - -class UnsupportedUnionTypeAnnotationParserError extends ParserError { - constructor( - hasteModuleName: string, - arrayElementTypeAST: $FlowFixMe, - types: string[], - ) { - super( - hasteModuleName, - arrayElementTypeAST, - `Union members must be of the same type, but multiple types were found ${types.join( - ', ', - )}'.`, - ); - } -} - -/** - * Module parsing errors - */ - -class UnusedModuleFlowInterfaceParserError extends ParserError { - constructor(hasteModuleName: string, flowInterface: $FlowFixMe) { - super( - hasteModuleName, - flowInterface, - "Unused NativeModule spec. Please load the NativeModule by calling TurboModuleRegistry.get('').", - ); - } -} - -class MoreThanOneModuleRegistryCallsParserError extends ParserError { - constructor( - hasteModuleName: string, - flowCallExpressions: $FlowFixMe, - numCalls: number, - ) { - super( - hasteModuleName, - flowCallExpressions, - `Every NativeModule spec file must contain exactly one NativeModule load. This file contains ${numCalls}. Please simplify this spec file, splitting it as necessary, to remove the extraneous loads.`, - ); - } -} - -class UntypedModuleRegistryCallParserError extends ParserError { - constructor( - hasteModuleName: string, - flowCallExpression: $FlowFixMe, - methodName: string, - moduleName: string, - ) { - super( - hasteModuleName, - flowCallExpression, - `Please type this NativeModule load: TurboModuleRegistry.${methodName}('${moduleName}').`, - ); - } -} - -class IncorrectModuleRegistryCallTypeParameterParserError extends ParserError { - constructor( - hasteModuleName: string, - flowTypeArguments: $FlowFixMe, - methodName: string, - moduleName: string, - ) { - super( - hasteModuleName, - flowTypeArguments, - `Please change these type arguments to reflect TurboModuleRegistry.${methodName}('${moduleName}').`, - ); - } -} - -class IncorrectModuleRegistryCallArityParserError extends ParserError { - constructor( - hasteModuleName: string, - flowCallExpression: $FlowFixMe, - methodName: string, - incorrectArity: number, - ) { - super( - hasteModuleName, - flowCallExpression, - `Please call TurboModuleRegistry.${methodName}() with exactly one argument. Detected ${incorrectArity}.`, - ); - } -} - -class IncorrectModuleRegistryCallArgumentTypeParserError extends ParserError { - constructor( - hasteModuleName: string, - flowArgument: $FlowFixMe, - methodName: string, - type: string, - ) { - const a = /[aeiouy]/.test(type.toLowerCase()) ? 'an' : 'a'; - super( - hasteModuleName, - flowArgument, - `Please call TurboModuleRegistry.${methodName}() with a string literal. Detected ${a} '${type}'`, - ); - } -} - -module.exports = { - IncorrectlyParameterizedFlowGenericParserError, - MisnamedModuleFlowInterfaceParserError, - ModuleFlowInterfaceNotFoundParserError, - MoreThanOneModuleFlowInterfaceParserError, - UnnamedFunctionParamParserError, - UnsupportedArrayElementTypeAnnotationParserError, - UnsupportedFlowGenericParserError, - UnsupportedFlowTypeAnnotationParserError, - UnsupportedFunctionParamTypeAnnotationParserError, - UnsupportedFunctionReturnTypeAnnotationParserError, - UnsupportedEnumDeclarationParserError, - UnsupportedUnionTypeAnnotationParserError, - UnsupportedModulePropertyParserError, - UnsupportedObjectPropertyTypeAnnotationParserError, - UnsupportedObjectPropertyValueTypeAnnotationParserError, - UnusedModuleFlowInterfaceParserError, - MoreThanOneModuleRegistryCallsParserError, - UntypedModuleRegistryCallParserError, - IncorrectModuleRegistryCallTypeParameterParserError, - IncorrectModuleRegistryCallArityParserError, - IncorrectModuleRegistryCallArgumentTypeParserError, -}; diff --git a/packages/react-native-codegen/src/parsers/flow/modules/index.js b/packages/react-native-codegen/src/parsers/flow/modules/index.js index 7864ef87dd6..b9a7e99f196 100644 --- a/packages/react-native-codegen/src/parsers/flow/modules/index.js +++ b/packages/react-native-codegen/src/parsers/flow/modules/index.js @@ -39,14 +39,14 @@ const { emitInt32, } = require('../../parsers-primitives'); const { - IncorrectlyParameterizedFlowGenericParserError, - MisnamedModuleFlowInterfaceParserError, - ModuleFlowInterfaceNotFoundParserError, - MoreThanOneModuleFlowInterfaceParserError, + IncorrectlyParameterizedGenericParserError, + MisnamedModuleInterfaceParserError, + ModuleInterfaceNotFoundParserError, + MoreThanOneModuleInterfaceParserError, UnnamedFunctionParamParserError, UnsupportedArrayElementTypeAnnotationParserError, - UnsupportedFlowGenericParserError, - UnsupportedFlowTypeAnnotationParserError, + UnsupportedGenericParserError, + UnsupportedTypeAnnotationParserError, UnsupportedFunctionParamTypeAnnotationParserError, UnsupportedFunctionReturnTypeAnnotationParserError, UnsupportedEnumDeclarationParserError, @@ -54,15 +54,16 @@ const { UnsupportedModulePropertyParserError, UnsupportedObjectPropertyTypeAnnotationParserError, UnsupportedObjectPropertyValueTypeAnnotationParserError, - UnusedModuleFlowInterfaceParserError, + UnusedModuleInterfaceParserError, MoreThanOneModuleRegistryCallsParserError, UntypedModuleRegistryCallParserError, IncorrectModuleRegistryCallTypeParameterParserError, IncorrectModuleRegistryCallArityParserError, IncorrectModuleRegistryCallArgumentTypeParserError, -} = require('./errors.js'); +} = require('../../errors.js'); const invariant = require('invariant'); +const language = 'Flow'; function nullGuard(fn: () => T): ?T { return fn(); @@ -139,6 +140,7 @@ function translateTypeAnnotation( typeAnnotation.typeParameters.params[0], typeAnnotation.type, 'void', + language, ); } @@ -148,6 +150,7 @@ function translateTypeAnnotation( typeAnnotation.typeParameters.params[0], typeAnnotation.type, 'Promise', + language, ); } @@ -157,6 +160,7 @@ function translateTypeAnnotation( typeAnnotation.typeParameters.params[0], typeAnnotation.type, 'FunctionTypeAnnotation', + language, ); } @@ -240,12 +244,14 @@ function translateTypeAnnotation( hasteModuleName, typeAnnotation, memberType, + language, ); } } - throw new UnsupportedFlowGenericParserError( + throw new UnsupportedGenericParserError( hasteModuleName, typeAnnotation, + language, ); } } @@ -263,6 +269,7 @@ function translateTypeAnnotation( hasteModuleName, property, property.type, + language, ); } @@ -286,6 +293,7 @@ function translateTypeAnnotation( property.value, property.key, propertyTypeAnnotation.type, + language, ); } @@ -295,6 +303,7 @@ function translateTypeAnnotation( property.value, property.key, 'void', + language, ); } @@ -304,6 +313,7 @@ function translateTypeAnnotation( property.value, property.key, 'Promise', + language, ); } @@ -411,6 +421,7 @@ function translateTypeAnnotation( hasteModuleName, typeAnnotation, unionTypes, + language, ); } return wrapNullable(nullable, { @@ -429,9 +440,10 @@ function translateTypeAnnotation( // Fallthrough } default: { - throw new UnsupportedFlowTypeAnnotationParserError( + throw new UnsupportedTypeAnnotationParserError( hasteModuleName, typeAnnotation, + language, ); } } @@ -445,9 +457,10 @@ function assertGenericTypeAnnotationHasExactlyOneTypeParameter( typeAnnotation: $FlowFixMe, ) { if (typeAnnotation.typeParameters == null) { - throw new IncorrectlyParameterizedFlowGenericParserError( + throw new IncorrectlyParameterizedGenericParserError( moduleName, typeAnnotation, + language, ); } @@ -457,9 +470,10 @@ function assertGenericTypeAnnotationHasExactlyOneTypeParameter( ); if (typeAnnotation.typeParameters.params.length !== 1) { - throw new IncorrectlyParameterizedFlowGenericParserError( + throw new IncorrectlyParameterizedGenericParserError( moduleName, typeAnnotation, + language, ); } } @@ -479,7 +493,11 @@ function translateFunctionTypeAnnotation( for (const flowParam of (flowFunctionTypeAnnotation.params: $ReadOnlyArray<$FlowFixMe>)) { const parsedParam = tryParse(() => { if (flowParam.name == null) { - throw new UnnamedFunctionParamParserError(flowParam, hasteModuleName); + throw new UnnamedFunctionParamParserError( + flowParam, + hasteModuleName, + language, + ); } const paramName = flowParam.name.name; @@ -501,6 +519,7 @@ function translateFunctionTypeAnnotation( flowParam.typeAnnotation, paramName, 'void', + language, ); } @@ -510,6 +529,7 @@ function translateFunctionTypeAnnotation( flowParam.typeAnnotation, paramName, 'Promise', + language, ); } @@ -544,6 +564,7 @@ function translateFunctionTypeAnnotation( hasteModuleName, flowFunctionTypeAnnotation.returnType, 'FunctionTypeAnnotation', + language, ); } @@ -582,6 +603,7 @@ function buildPropertySchema( property.value, property.key.name, value.type, + language, ); } @@ -625,23 +647,29 @@ function buildModuleSchema( ); if (moduleSpecs.length === 0) { - throw new ModuleFlowInterfaceNotFoundParserError(hasteModuleName, ast); + throw new ModuleInterfaceNotFoundParserError( + hasteModuleName, + ast, + language, + ); } if (moduleSpecs.length > 1) { - throw new MoreThanOneModuleFlowInterfaceParserError( + throw new MoreThanOneModuleInterfaceParserError( hasteModuleName, moduleSpecs, moduleSpecs.map(node => node.id.name), + language, ); } const [moduleSpec] = moduleSpecs; if (moduleSpec.id.name !== 'Spec') { - throw new MisnamedModuleFlowInterfaceParserError( + throw new MisnamedModuleInterfaceParserError( hasteModuleName, moduleSpec.id, + language, ); } @@ -657,9 +685,10 @@ function buildModuleSchema( }); if (callExpressions.length === 0) { - throw new UnusedModuleFlowInterfaceParserError( + throw new UnusedModuleInterfaceParserError( hasteModuleName, moduleSpec, + language, ); } @@ -668,6 +697,7 @@ function buildModuleSchema( hasteModuleName, callExpressions, callExpressions.length, + language, ); } @@ -681,6 +711,7 @@ function buildModuleSchema( callExpression, methodName, callExpression.arguments.length, + language, ); } @@ -691,6 +722,7 @@ function buildModuleSchema( callExpression.arguments[0], methodName, type, + language, ); } @@ -702,6 +734,7 @@ function buildModuleSchema( callExpression, methodName, $moduleName, + language, ); } @@ -716,6 +749,7 @@ function buildModuleSchema( typeArguments, methodName, $moduleName, + language, ); } diff --git a/packages/react-native-codegen/src/parsers/typescript/modules/__tests__/typescript-module-parser-e2e-test.js b/packages/react-native-codegen/src/parsers/typescript/modules/__tests__/typescript-module-parser-e2e-test.js index 17aa2b1dbc6..1128a1bc837 100644 --- a/packages/react-native-codegen/src/parsers/typescript/modules/__tests__/typescript-module-parser-e2e-test.js +++ b/packages/react-native-codegen/src/parsers/typescript/modules/__tests__/typescript-module-parser-e2e-test.js @@ -18,11 +18,11 @@ import type { const {parseString} = require('../../index.js'); const {unwrapNullable} = require('../../../parsers-commons'); const { - UnsupportedTypeScriptGenericParserError, - UnsupportedTypeScriptTypeAnnotationParserError, + UnsupportedGenericParserError, + UnsupportedTypeAnnotationParserError, UnnamedFunctionParamParserError, - IncorrectlyParameterizedTypeScriptGenericParserError, -} = require('../errors'); + IncorrectlyParameterizedGenericParserError, +} = require('../../../errors'); const invariant = require('invariant'); type PrimitiveTypeAnnotationType = @@ -87,7 +87,7 @@ describe('TypeScript Module Parser', () => { export default TurboModuleRegistry.get('Foo'); `); - expect(parser).toThrow(UnsupportedTypeScriptTypeAnnotationParserError); + expect(parser).toThrow(UnsupportedTypeAnnotationParserError); }); it('should fail parsing when a function param type is unamed', () => { @@ -173,7 +173,7 @@ describe('TypeScript Module Parser', () => { () => { it(`should not parse methods that have ${PARAM_TYPE_DESCRIPTION} parameter of type 'Function'`, () => { expect(() => parseParamType('arg', 'Function')).toThrow( - UnsupportedTypeScriptGenericParserError, + UnsupportedGenericParserError, ); }); @@ -212,7 +212,7 @@ describe('TypeScript Module Parser', () => { describe('Array Types', () => { it(`should not parse methods that have ${PARAM_TYPE_DESCRIPTION} parameter of type 'Array'`, () => { expect(() => parseParamType('arg', 'Array')).toThrow( - IncorrectlyParameterizedTypeScriptGenericParserError, + IncorrectlyParameterizedGenericParserError, ); }); @@ -510,9 +510,7 @@ describe('TypeScript Module Parser', () => { it(`should not parse methods that have ${PARAM_TYPE_DESCRIPTION} parameter type of an object literal with ${PROP_TYPE_DESCRIPTION} prop of type 'Array`, () => { expect(() => parseParamTypeObjectLiteralProp('prop', 'Array'), - ).toThrow( - IncorrectlyParameterizedTypeScriptGenericParserError, - ); + ).toThrow(IncorrectlyParameterizedGenericParserError); }); function parseArrayElementType( @@ -782,7 +780,7 @@ describe('TypeScript Module Parser', () => { describe('Array Types', () => { it(`should not parse methods that have ${RETURN_TYPE_DESCRIPTION} return of type 'Array'`, () => { expect(() => parseReturnType('Array')).toThrow( - IncorrectlyParameterizedTypeScriptGenericParserError, + IncorrectlyParameterizedGenericParserError, ); }); @@ -885,7 +883,7 @@ describe('TypeScript Module Parser', () => { it(`should not parse methods that have ${RETURN_TYPE_DESCRIPTION} return of type 'Function'`, () => { expect(() => parseReturnType('Function')).toThrow( - UnsupportedTypeScriptGenericParserError, + UnsupportedGenericParserError, ); }); @@ -1051,9 +1049,7 @@ describe('TypeScript Module Parser', () => { it(`should not parse methods that have ${RETURN_TYPE_DESCRIPTION} return type of an object literal with ${PROP_TYPE_DESCRIPTION} prop of type 'Array`, () => { expect(() => parseObjectLiteralReturnTypeProp('prop', 'Array'), - ).toThrow( - IncorrectlyParameterizedTypeScriptGenericParserError, - ); + ).toThrow(IncorrectlyParameterizedGenericParserError); }); function parseArrayElementType( diff --git a/packages/react-native-codegen/src/parsers/typescript/modules/errors.js b/packages/react-native-codegen/src/parsers/typescript/modules/errors.js deleted file mode 100644 index a6de07a8640..00000000000 --- a/packages/react-native-codegen/src/parsers/typescript/modules/errors.js +++ /dev/null @@ -1,376 +0,0 @@ -/** - * Copyright (c) Meta Platforms, Inc. and affiliates. - * - * This source code is licensed under the MIT license found in the - * LICENSE file in the root directory of this source tree. - * - * @flow strict-local - * @format - */ - -'use strict'; - -const invariant = require('invariant'); -const {ParserError} = require('../../errors'); - -class MisnamedModuleTypeScriptInterfaceParserError extends ParserError { - constructor(hasteModuleName: string, id: $FlowFixMe) { - super( - hasteModuleName, - id, - `All TypeScript interfaces extending TurboModule must be called 'Spec'. Please rename TypeScript interface '${id.name}' to 'Spec'.`, - ); - } -} - -class ModuleTypeScriptInterfaceNotFoundParserError extends ParserError { - constructor(hasteModuleName: string, ast: $FlowFixMe) { - super( - hasteModuleName, - ast, - 'No TypeScript interfaces extending TurboModule were detected in this NativeModule spec.', - ); - } -} - -class MoreThanOneModuleTypeScriptInterfaceParserError extends ParserError { - constructor( - hasteModuleName: string, - flowModuleInterfaces: $ReadOnlyArray<$FlowFixMe>, - names: $ReadOnlyArray, - ) { - const finalName = names[names.length - 1]; - const allButLastName = names.slice(0, -1); - const quote = (x: string) => `'${x}'`; - - const nameStr = - allButLastName.map(quote).join(', ') + ', and ' + quote(finalName); - - super( - hasteModuleName, - flowModuleInterfaces, - `Every NativeModule spec file must declare exactly one NativeModule TypeScript interface. This file declares ${names.length}: ${nameStr}. Please remove the extraneous TypeScript interface declarations.`, - ); - } -} - -class UnsupportedModulePropertyParserError extends ParserError { - constructor( - hasteModuleName: string, - propertyValue: $FlowFixMe, - propertyName: string, - invalidPropertyValueType: string, - ) { - super( - hasteModuleName, - propertyValue, - `TypeScript interfaces extending TurboModule must only contain 'FunctionTypeAnnotation's. Property '${propertyName}' refers to a '${invalidPropertyValueType}'.`, - ); - } -} - -class UnsupportedTypeScriptTypeAnnotationParserError extends ParserError { - +typeAnnotationType: string; - constructor(hasteModuleName: string, typeAnnotation: $FlowFixMe) { - super( - hasteModuleName, - typeAnnotation, - `TypeScript type annotation '${typeAnnotation.type}' is unsupported in NativeModule specs.`, - ); - - this.typeAnnotationType = typeAnnotation.type; - } -} - -class UnsupportedTypeScriptGenericParserError extends ParserError { - +genericName: string; - constructor(hasteModuleName: string, genericTypeAnnotation: $FlowFixMe) { - const genericName = genericTypeAnnotation.typeName.name; - super( - hasteModuleName, - genericTypeAnnotation, - `Unrecognized generic type '${genericName}' in NativeModule spec.`, - ); - - this.genericName = genericName; - } -} - -class IncorrectlyParameterizedTypeScriptGenericParserError extends ParserError { - +genericName: string; - +numTypeParameters: number; - - // $FlowFixMe[missing-local-annot] - constructor(hasteModuleName: string, genericTypeAnnotation: $FlowFixMe) { - if (genericTypeAnnotation.typeParameters == null) { - super( - hasteModuleName, - genericTypeAnnotation, - `Generic '${genericTypeAnnotation.typeName.name}' must have type parameters.`, - ); - return; - } - - if ( - genericTypeAnnotation.typeParameters.type === - 'TypeParameterInstantiation' && - genericTypeAnnotation.typeParameters.params.length !== 1 - ) { - super( - hasteModuleName, - genericTypeAnnotation.typeParameters, - `Generic '${genericTypeAnnotation.typeName.name}' must have exactly one type parameter.`, - ); - return; - } - - invariant( - false, - "Couldn't create IncorrectlyParameterizedFlowGenericParserError", - ); - } -} - -/** - * Array parsing errors - */ - -class UnsupportedArrayElementTypeAnnotationParserError extends ParserError { - constructor( - hasteModuleName: string, - arrayElementTypeAST: $FlowFixMe, - arrayType: 'Array' | 'ReadonlyArray', - invalidArrayElementType: string, - ) { - super( - hasteModuleName, - arrayElementTypeAST, - `${arrayType} element types cannot be '${invalidArrayElementType}'.`, - ); - } -} - -/** - * Object parsing errors - */ - -class UnsupportedObjectPropertyTypeAnnotationParserError extends ParserError { - constructor( - hasteModuleName: string, - propertyAST: $FlowFixMe, - invalidPropertyType: string, - ) { - let message = `'ObjectTypeAnnotation' cannot contain '${invalidPropertyType}'.`; - - super(hasteModuleName, propertyAST, message); - } -} - -class UnsupportedObjectPropertyValueTypeAnnotationParserError extends ParserError { - constructor( - hasteModuleName: string, - propertyValueAST: $FlowFixMe, - propertyName: string, - invalidPropertyValueType: string, - ) { - super( - hasteModuleName, - propertyValueAST, - `Object property '${propertyName}' cannot have type '${invalidPropertyValueType}'.`, - ); - } -} - -/** - * Function parsing errors - */ - -class UnnamedFunctionParamParserError extends ParserError { - constructor(functionParam: $FlowFixMe, hasteModuleName: string) { - super( - hasteModuleName, - functionParam, - 'All function parameters must be named.', - ); - } -} - -class UnsupportedFunctionParamTypeAnnotationParserError extends ParserError { - constructor( - hasteModuleName: string, - flowParamTypeAnnotation: $FlowFixMe, - paramName: string, - invalidParamType: string, - ) { - super( - hasteModuleName, - flowParamTypeAnnotation, - `Function parameter '${paramName}' cannot have type '${invalidParamType}'.`, - ); - } -} - -class UnsupportedFunctionReturnTypeAnnotationParserError extends ParserError { - constructor( - hasteModuleName: string, - flowReturnTypeAnnotation: $FlowFixMe, - invalidReturnType: string, - ) { - super( - hasteModuleName, - flowReturnTypeAnnotation, - `Function return cannot have type '${invalidReturnType}'.`, - ); - } -} - -/** - * Enum parsing errors - */ - -class UnsupportedTypeScriptEnumDeclarationParserError extends ParserError { - constructor( - hasteModuleName: string, - arrayElementTypeAST: $FlowFixMe, - memberType: string, - ) { - super( - hasteModuleName, - arrayElementTypeAST, - `Unexpected enum member type ${memberType}. Only string and number enum members are supported`, - ); - } -} - -/** - * Union parsing errors - */ - -class UnsupportedTypeScriptUnionTypeAnnotationParserError extends ParserError { - constructor( - hasteModuleName: string, - arrayElementTypeAST: $FlowFixMe, - types: string[], - ) { - super( - hasteModuleName, - arrayElementTypeAST, - `Union members must be of the same type, but multiple types were found ${types.join( - ', ', - )}'.`, - ); - } -} - -/** - * Module parsing errors - */ - -class UnusedModuleTypeScriptInterfaceParserError extends ParserError { - constructor(hasteModuleName: string, flowInterface: $FlowFixMe) { - super( - hasteModuleName, - flowInterface, - "Unused NativeModule spec. Please load the NativeModule by calling TurboModuleRegistry.get('').", - ); - } -} - -class MoreThanOneModuleRegistryCallsParserError extends ParserError { - constructor( - hasteModuleName: string, - flowCallExpressions: $FlowFixMe, - numCalls: number, - ) { - super( - hasteModuleName, - flowCallExpressions, - `Every NativeModule spec file must contain exactly one NativeModule load. This file contains ${numCalls}. Please simplify this spec file, splitting it as necessary, to remove the extraneous loads.`, - ); - } -} - -class UntypedModuleRegistryCallParserError extends ParserError { - constructor( - hasteModuleName: string, - flowCallExpression: $FlowFixMe, - methodName: string, - moduleName: string, - ) { - super( - hasteModuleName, - flowCallExpression, - `Please type this NativeModule load: TurboModuleRegistry.${methodName}('${moduleName}').`, - ); - } -} - -class IncorrectModuleRegistryCallTypeParameterParserError extends ParserError { - constructor( - hasteModuleName: string, - flowTypeArguments: $FlowFixMe, - methodName: string, - moduleName: string, - ) { - super( - hasteModuleName, - flowTypeArguments, - `Please change these type arguments to reflect TurboModuleRegistry.${methodName}('${moduleName}').`, - ); - } -} - -class IncorrectModuleRegistryCallArityParserError extends ParserError { - constructor( - hasteModuleName: string, - flowCallExpression: $FlowFixMe, - methodName: string, - incorrectArity: number, - ) { - super( - hasteModuleName, - flowCallExpression, - `Please call TurboModuleRegistry.${methodName}() with exactly one argument. Detected ${incorrectArity}.`, - ); - } -} - -class IncorrectModuleRegistryCallArgumentTypeParserError extends ParserError { - constructor( - hasteModuleName: string, - flowArgument: $FlowFixMe, - methodName: string, - type: string, - ) { - const a = /[aeiouy]/.test(type.toLowerCase()) ? 'an' : 'a'; - super( - hasteModuleName, - flowArgument, - `Please call TurboModuleRegistry.${methodName}() with a string literal. Detected ${a} '${type}'`, - ); - } -} - -module.exports = { - IncorrectlyParameterizedTypeScriptGenericParserError, - MisnamedModuleTypeScriptInterfaceParserError, - ModuleTypeScriptInterfaceNotFoundParserError, - MoreThanOneModuleTypeScriptInterfaceParserError, - UnnamedFunctionParamParserError, - UnsupportedArrayElementTypeAnnotationParserError, - UnsupportedTypeScriptGenericParserError, - UnsupportedTypeScriptTypeAnnotationParserError, - UnsupportedFunctionParamTypeAnnotationParserError, - UnsupportedFunctionReturnTypeAnnotationParserError, - UnsupportedTypeScriptEnumDeclarationParserError, - UnsupportedTypeScriptUnionTypeAnnotationParserError, - UnsupportedModulePropertyParserError, - UnsupportedObjectPropertyTypeAnnotationParserError, - UnsupportedObjectPropertyValueTypeAnnotationParserError, - UnusedModuleTypeScriptInterfaceParserError, - MoreThanOneModuleRegistryCallsParserError, - UntypedModuleRegistryCallParserError, - IncorrectModuleRegistryCallTypeParameterParserError, - IncorrectModuleRegistryCallArityParserError, - IncorrectModuleRegistryCallArgumentTypeParserError, -}; diff --git a/packages/react-native-codegen/src/parsers/typescript/modules/index.js b/packages/react-native-codegen/src/parsers/typescript/modules/index.js index 64cd84e914a..ec8ac8d9d54 100644 --- a/packages/react-native-codegen/src/parsers/typescript/modules/index.js +++ b/packages/react-native-codegen/src/parsers/typescript/modules/index.js @@ -39,30 +39,31 @@ const { emitInt32, } = require('../../parsers-primitives'); const { - IncorrectlyParameterizedTypeScriptGenericParserError, - MisnamedModuleTypeScriptInterfaceParserError, - ModuleTypeScriptInterfaceNotFoundParserError, - MoreThanOneModuleTypeScriptInterfaceParserError, + IncorrectlyParameterizedGenericParserError, + MisnamedModuleInterfaceParserError, + ModuleInterfaceNotFoundParserError, + MoreThanOneModuleInterfaceParserError, UnnamedFunctionParamParserError, UnsupportedArrayElementTypeAnnotationParserError, - UnsupportedTypeScriptGenericParserError, - UnsupportedTypeScriptTypeAnnotationParserError, + UnsupportedGenericParserError, + UnsupportedTypeAnnotationParserError, UnsupportedFunctionParamTypeAnnotationParserError, UnsupportedFunctionReturnTypeAnnotationParserError, - UnsupportedTypeScriptEnumDeclarationParserError, - UnsupportedTypeScriptUnionTypeAnnotationParserError, + UnsupportedEnumDeclarationParserError, + UnsupportedUnionTypeAnnotationParserError, UnsupportedModulePropertyParserError, UnsupportedObjectPropertyTypeAnnotationParserError, UnsupportedObjectPropertyValueTypeAnnotationParserError, - UnusedModuleTypeScriptInterfaceParserError, + UnusedModuleInterfaceParserError, MoreThanOneModuleRegistryCallsParserError, UntypedModuleRegistryCallParserError, IncorrectModuleRegistryCallTypeParameterParserError, IncorrectModuleRegistryCallArityParserError, IncorrectModuleRegistryCallArgumentTypeParserError, -} = require('./errors.js'); +} = require('../../errors.js'); const invariant = require('invariant'); +const language = 'TypeScript'; function nullGuard(fn: () => T): ?T { return fn(); @@ -108,6 +109,7 @@ function translateArrayTypeAnnotation( tsElementType, tsArrayType, 'void', + language, ); } @@ -117,6 +119,7 @@ function translateArrayTypeAnnotation( tsElementType, tsArrayType, 'Promise', + language, ); } @@ -126,6 +129,7 @@ function translateArrayTypeAnnotation( tsElementType, tsArrayType, 'FunctionTypeAnnotation', + language, ); } @@ -185,9 +189,10 @@ function translateTypeAnnotation( nullable, ); } else { - throw new UnsupportedTypeScriptGenericParserError( + throw new UnsupportedGenericParserError( hasteModuleName, typeAnnotation, + language, ); } } @@ -271,16 +276,18 @@ function translateTypeAnnotation( memberType: memberType, }); } else { - throw new UnsupportedTypeScriptEnumDeclarationParserError( + throw new UnsupportedEnumDeclarationParserError( hasteModuleName, typeAnnotation, memberType, + language, ); } } - throw new UnsupportedTypeScriptGenericParserError( + throw new UnsupportedGenericParserError( hasteModuleName, typeAnnotation, + language, ); } } @@ -298,6 +305,7 @@ function translateTypeAnnotation( hasteModuleName, property, property.type, + language, ); } @@ -321,6 +329,7 @@ function translateTypeAnnotation( property.typeAnnotation.typeAnnotation, property.key, propertyTypeAnnotation.type, + language, ); } @@ -330,6 +339,7 @@ function translateTypeAnnotation( property.typeAnnotation.typeAnnotation, property.key, 'void', + language, ); } @@ -339,6 +349,7 @@ function translateTypeAnnotation( property.typeAnnotation.typeAnnotation, property.key, 'Promise', + language, ); } @@ -442,10 +453,11 @@ function translateTypeAnnotation( .filter((value, index, self) => self.indexOf(value) === index); // Only support unionTypes of the same kind if (unionTypes.length > 1) { - throw new UnsupportedTypeScriptUnionTypeAnnotationParserError( + throw new UnsupportedUnionTypeAnnotationParserError( hasteModuleName, typeAnnotation, unionTypes, + language, ); } return wrapNullable(nullable, { @@ -464,9 +476,10 @@ function translateTypeAnnotation( // Fallthrough } default: { - throw new UnsupportedTypeScriptTypeAnnotationParserError( + throw new UnsupportedTypeAnnotationParserError( hasteModuleName, typeAnnotation, + language, ); } } @@ -480,9 +493,10 @@ function assertGenericTypeAnnotationHasExactlyOneTypeParameter( typeAnnotation: $FlowFixMe, ) { if (typeAnnotation.typeParameters == null) { - throw new IncorrectlyParameterizedTypeScriptGenericParserError( + throw new IncorrectlyParameterizedGenericParserError( moduleName, typeAnnotation, + language, ); } @@ -492,9 +506,10 @@ function assertGenericTypeAnnotationHasExactlyOneTypeParameter( ); if (typeAnnotation.typeParameters.params.length !== 1) { - throw new IncorrectlyParameterizedTypeScriptGenericParserError( + throw new IncorrectlyParameterizedGenericParserError( moduleName, typeAnnotation, + language, ); } } @@ -517,6 +532,7 @@ function translateFunctionTypeAnnotation( throw new UnnamedFunctionParamParserError( typeScriptParam, hasteModuleName, + language, ); } @@ -539,6 +555,7 @@ function translateFunctionTypeAnnotation( typeScriptParam.typeAnnotation, paramName, 'void', + language, ); } @@ -548,6 +565,7 @@ function translateFunctionTypeAnnotation( typeScriptParam.typeAnnotation, paramName, 'Promise', + language, ); } @@ -582,6 +600,7 @@ function translateFunctionTypeAnnotation( hasteModuleName, typescriptFunctionTypeAnnotation.returnType, 'FunctionTypeAnnotation', + language, ); } @@ -619,6 +638,7 @@ function buildPropertySchema( property.value, property.key.name, value.type, + language, ); } @@ -662,26 +682,29 @@ function buildModuleSchema( ); if (moduleSpecs.length === 0) { - throw new ModuleTypeScriptInterfaceNotFoundParserError( + throw new ModuleInterfaceNotFoundParserError( hasteModuleName, ast, + language, ); } if (moduleSpecs.length > 1) { - throw new MoreThanOneModuleTypeScriptInterfaceParserError( + throw new MoreThanOneModuleInterfaceParserError( hasteModuleName, moduleSpecs, moduleSpecs.map(node => node.id.name), + language, ); } const [moduleSpec] = moduleSpecs; if (moduleSpec.id.name !== 'Spec') { - throw new MisnamedModuleTypeScriptInterfaceParserError( + throw new MisnamedModuleInterfaceParserError( hasteModuleName, moduleSpec.id, + language, ); } @@ -697,9 +720,10 @@ function buildModuleSchema( }); if (callExpressions.length === 0) { - throw new UnusedModuleTypeScriptInterfaceParserError( + throw new UnusedModuleInterfaceParserError( hasteModuleName, moduleSpec, + language, ); } @@ -708,6 +732,7 @@ function buildModuleSchema( hasteModuleName, callExpressions, callExpressions.length, + language, ); } @@ -721,6 +746,7 @@ function buildModuleSchema( callExpression, methodName, callExpression.arguments.length, + language, ); } @@ -731,6 +757,7 @@ function buildModuleSchema( callExpression.arguments[0], methodName, type, + language, ); } @@ -742,6 +769,7 @@ function buildModuleSchema( callExpression, methodName, $moduleName, + language, ); } @@ -756,6 +784,7 @@ function buildModuleSchema( typeParameters, methodName, $moduleName, + language, ); }