@react-native-windows/codegen 0.0.0-canary.3 → 0.0.0-canary.32
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/CHANGELOG.md +283 -6
- package/bin.js +0 -0
- package/lib-commonjs/Cli.d.ts +7 -0
- package/lib-commonjs/Cli.js +231 -0
- package/lib-commonjs/Cli.js.map +1 -0
- package/lib-commonjs/generators/AliasGen.d.ts +11 -0
- package/lib-commonjs/generators/AliasGen.js +72 -0
- package/lib-commonjs/generators/AliasGen.js.map +1 -0
- package/lib-commonjs/generators/AliasManaging.d.ts +15 -0
- package/lib-commonjs/generators/AliasManaging.js +49 -0
- package/lib-commonjs/generators/AliasManaging.js.map +1 -0
- package/lib-commonjs/generators/GenerateNM2.d.ts +11 -0
- package/lib-commonjs/generators/GenerateNM2.js +94 -0
- package/lib-commonjs/generators/GenerateNM2.js.map +1 -0
- package/lib-commonjs/generators/GenerateTypeScript.d.ts +11 -0
- package/lib-commonjs/generators/GenerateTypeScript.js +166 -0
- package/lib-commonjs/generators/GenerateTypeScript.js.map +1 -0
- package/lib-commonjs/generators/ObjectTypes.d.ts +8 -0
- package/lib-commonjs/generators/ObjectTypes.js +53 -0
- package/lib-commonjs/generators/ObjectTypes.js.map +1 -0
- package/lib-commonjs/generators/ParamTypes.d.ts +11 -0
- package/lib-commonjs/generators/ParamTypes.js +114 -0
- package/lib-commonjs/generators/ParamTypes.js.map +1 -0
- package/lib-commonjs/generators/ReturnTypes.d.ts +9 -0
- package/lib-commonjs/generators/ReturnTypes.js +63 -0
- package/lib-commonjs/generators/ReturnTypes.js.map +1 -0
- package/lib-commonjs/generators/ValidateConstants.d.ts +8 -0
- package/lib-commonjs/generators/ValidateConstants.js +38 -0
- package/lib-commonjs/generators/ValidateConstants.js.map +1 -0
- package/lib-commonjs/generators/ValidateMethods.d.ts +8 -0
- package/lib-commonjs/generators/ValidateMethods.js +70 -0
- package/lib-commonjs/generators/ValidateMethods.js.map +1 -0
- package/package.json +28 -16
- package/src/Cli.ts +172 -35
- package/src/generators/AliasGen.ts +105 -0
- package/src/generators/AliasManaging.ts +75 -0
- package/src/generators/GenerateNM2.ts +62 -296
- package/src/generators/GenerateTypeScript.ts +247 -0
- package/src/generators/ObjectTypes.ts +70 -0
- package/src/generators/ParamTypes.ts +220 -0
- package/src/generators/ReturnTypes.ts +92 -0
- package/src/generators/ValidateConstants.ts +50 -0
- package/src/generators/ValidateMethods.ts +135 -0
- package/.eslintrc.js +0 -4
- package/.vscode/launch.json +0 -23
- package/CHANGELOG.json +0 -447
- package/jest.config.js +0 -1
- package/tsconfig.json +0 -5
|
@@ -0,0 +1,247 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Microsoft Corporation.
|
|
3
|
+
* Licensed under the MIT License.
|
|
4
|
+
* @format
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
'use strict';
|
|
8
|
+
|
|
9
|
+
import {
|
|
10
|
+
NamedShape,
|
|
11
|
+
NativeModuleBaseTypeAnnotation,
|
|
12
|
+
NativeModuleFunctionTypeAnnotation,
|
|
13
|
+
NativeModuleObjectTypeAnnotation,
|
|
14
|
+
NativeModuleParamTypeAnnotation,
|
|
15
|
+
NativeModuleReturnTypeAnnotation,
|
|
16
|
+
NativeModuleSchema,
|
|
17
|
+
Nullable,
|
|
18
|
+
SchemaType,
|
|
19
|
+
} from 'react-native-tscodegen';
|
|
20
|
+
|
|
21
|
+
interface CodegenNativeModuleSchema extends NativeModuleSchema {
|
|
22
|
+
optionalTurboModule?: boolean;
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
export function setOptionalTurboModule(
|
|
26
|
+
schema: NativeModuleSchema,
|
|
27
|
+
optional: boolean,
|
|
28
|
+
): void {
|
|
29
|
+
const cs = <CodegenNativeModuleSchema>schema;
|
|
30
|
+
cs.optionalTurboModule = optional;
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
export function getOptionalTurboModule(schema: NativeModuleSchema): boolean {
|
|
34
|
+
return (<CodegenNativeModuleSchema>schema).optionalTurboModule ?? false;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
type ObjectProp = NamedShape<Nullable<NativeModuleBaseTypeAnnotation>>;
|
|
38
|
+
type FunctionParam = NamedShape<Nullable<NativeModuleParamTypeAnnotation>>;
|
|
39
|
+
type FunctionDecl = NamedShape<Nullable<NativeModuleFunctionTypeAnnotation>>;
|
|
40
|
+
type FilesOutput = Map<string, string>;
|
|
41
|
+
|
|
42
|
+
const moduleTemplate = `
|
|
43
|
+
/*
|
|
44
|
+
* This file is auto-generated from a NativeModule spec file in js.
|
|
45
|
+
*
|
|
46
|
+
* This is a TypeScript turbo module definition file.
|
|
47
|
+
*/
|
|
48
|
+
|
|
49
|
+
import {TurboModule, TurboModuleRegistry} from 'react-native';
|
|
50
|
+
'use strict';
|
|
51
|
+
::_MODULE_ALIASED_STRUCTS_::
|
|
52
|
+
export interface Spec extends TurboModule {
|
|
53
|
+
::_MODULE_MEMBERS_::
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
export default TurboModuleRegistry.::_MODULE_GETTER_::<Spec>('::_MODULE_NAME_::');
|
|
57
|
+
`;
|
|
58
|
+
|
|
59
|
+
function optionalSign<T>(obj: NamedShape<T>): string {
|
|
60
|
+
return obj.optional ? '?' : '';
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
function translateType(
|
|
64
|
+
type: Nullable<
|
|
65
|
+
| NativeModuleBaseTypeAnnotation
|
|
66
|
+
| NativeModuleParamTypeAnnotation
|
|
67
|
+
| NativeModuleReturnTypeAnnotation
|
|
68
|
+
>,
|
|
69
|
+
): string {
|
|
70
|
+
// avoid: Property 'type' does not exist on type 'never'
|
|
71
|
+
const returnType = type.type;
|
|
72
|
+
switch (type.type) {
|
|
73
|
+
case 'StringTypeAnnotation':
|
|
74
|
+
return 'string';
|
|
75
|
+
case 'NumberTypeAnnotation':
|
|
76
|
+
case 'FloatTypeAnnotation':
|
|
77
|
+
case 'DoubleTypeAnnotation':
|
|
78
|
+
case 'Int32TypeAnnotation':
|
|
79
|
+
return 'number';
|
|
80
|
+
case 'BooleanTypeAnnotation':
|
|
81
|
+
return 'boolean';
|
|
82
|
+
case 'ArrayTypeAnnotation':
|
|
83
|
+
if (type.elementType) {
|
|
84
|
+
return `${translateType(type.elementType)}[]`;
|
|
85
|
+
} else {
|
|
86
|
+
return `Array`;
|
|
87
|
+
}
|
|
88
|
+
case 'GenericObjectTypeAnnotation':
|
|
89
|
+
return 'object';
|
|
90
|
+
case 'ObjectTypeAnnotation':
|
|
91
|
+
return `{${type.properties
|
|
92
|
+
.map((prop: ObjectProp) => {
|
|
93
|
+
return `${prop.name}${optionalSign(prop)}: ${translateType(
|
|
94
|
+
prop.typeAnnotation,
|
|
95
|
+
)}`;
|
|
96
|
+
})
|
|
97
|
+
.join(', ')}}`;
|
|
98
|
+
case 'ReservedTypeAnnotation': {
|
|
99
|
+
// avoid: Property 'name' does not exist on type 'never'
|
|
100
|
+
const name = type.name;
|
|
101
|
+
// (#6597)
|
|
102
|
+
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
|
103
|
+
if (name !== 'RootTag')
|
|
104
|
+
throw new Error(
|
|
105
|
+
`Unknown reserved function: ${name} in translateReturnType`,
|
|
106
|
+
);
|
|
107
|
+
return 'number';
|
|
108
|
+
}
|
|
109
|
+
case 'TypeAliasTypeAnnotation':
|
|
110
|
+
return type.name;
|
|
111
|
+
case 'NullableTypeAnnotation':
|
|
112
|
+
return `(${translateType(type.typeAnnotation)} | null | undefined)`;
|
|
113
|
+
case 'VoidTypeAnnotation':
|
|
114
|
+
return `void`;
|
|
115
|
+
case 'PromiseTypeAnnotation':
|
|
116
|
+
return `Promise`;
|
|
117
|
+
case `FunctionTypeAnnotation`:
|
|
118
|
+
return `((${type.params
|
|
119
|
+
.map((param: FunctionParam) => {
|
|
120
|
+
return `${param.name}${optionalSign(param)}: ${translateType(
|
|
121
|
+
param.typeAnnotation,
|
|
122
|
+
)}`;
|
|
123
|
+
})
|
|
124
|
+
.join(', ')}) => ${translateType(type.returnTypeAnnotation)})`;
|
|
125
|
+
default:
|
|
126
|
+
throw new Error(`Unhandled type in translateReturnType: ${returnType}`);
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
function translateAlias(
|
|
131
|
+
name: string,
|
|
132
|
+
type: NativeModuleObjectTypeAnnotation,
|
|
133
|
+
): string {
|
|
134
|
+
return `
|
|
135
|
+
export interface ${name} {
|
|
136
|
+
${type.properties
|
|
137
|
+
.map((prop: ObjectProp) => {
|
|
138
|
+
return ` ${prop.name}${optionalSign(prop)}: ${translateType(
|
|
139
|
+
prop.typeAnnotation,
|
|
140
|
+
)};`;
|
|
141
|
+
})
|
|
142
|
+
.join('\n')}
|
|
143
|
+
}
|
|
144
|
+
`;
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
function tryGetConstantType(
|
|
148
|
+
nativeModule: NativeModuleSchema,
|
|
149
|
+
): NativeModuleObjectTypeAnnotation | undefined {
|
|
150
|
+
const candidates = nativeModule.spec.properties.filter(
|
|
151
|
+
prop => prop.name === 'getConstants',
|
|
152
|
+
);
|
|
153
|
+
if (candidates.length === 0) {
|
|
154
|
+
return undefined;
|
|
155
|
+
}
|
|
156
|
+
|
|
157
|
+
const getConstant = candidates[0];
|
|
158
|
+
const funcType =
|
|
159
|
+
getConstant.typeAnnotation.type === 'NullableTypeAnnotation'
|
|
160
|
+
? getConstant.typeAnnotation.typeAnnotation
|
|
161
|
+
: getConstant.typeAnnotation;
|
|
162
|
+
if (
|
|
163
|
+
funcType.params.length > 0 ||
|
|
164
|
+
funcType.returnTypeAnnotation.type !== 'ObjectTypeAnnotation'
|
|
165
|
+
) {
|
|
166
|
+
return undefined;
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
const constantType = funcType.returnTypeAnnotation;
|
|
170
|
+
if (constantType.properties.length === 0) {
|
|
171
|
+
return undefined;
|
|
172
|
+
}
|
|
173
|
+
|
|
174
|
+
return constantType;
|
|
175
|
+
}
|
|
176
|
+
|
|
177
|
+
function translateMethod(func: FunctionDecl): string {
|
|
178
|
+
const funcType =
|
|
179
|
+
func.typeAnnotation.type === 'NullableTypeAnnotation'
|
|
180
|
+
? func.typeAnnotation.typeAnnotation
|
|
181
|
+
: func.typeAnnotation;
|
|
182
|
+
|
|
183
|
+
return `
|
|
184
|
+
${func.name}(${funcType.params
|
|
185
|
+
.map((param: FunctionParam) => {
|
|
186
|
+
return `${param.name}${optionalSign(param)}: ${translateType(
|
|
187
|
+
param.typeAnnotation,
|
|
188
|
+
)}`;
|
|
189
|
+
})
|
|
190
|
+
.join(', ')})${optionalSign(func)}: ${translateType(
|
|
191
|
+
funcType.returnTypeAnnotation,
|
|
192
|
+
)}${
|
|
193
|
+
funcType.returnTypeAnnotation.type === 'ObjectTypeAnnotation' ? '' : ';'
|
|
194
|
+
}`;
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
export function generateTypeScript(
|
|
198
|
+
_libraryName: string,
|
|
199
|
+
schema: SchemaType,
|
|
200
|
+
_moduleSpecName: string,
|
|
201
|
+
): FilesOutput {
|
|
202
|
+
const files = new Map<string, string>();
|
|
203
|
+
|
|
204
|
+
for (const moduleName of Object.keys(schema.modules)) {
|
|
205
|
+
const nativeModule = schema.modules[moduleName];
|
|
206
|
+
// from 0.65 facebook's react-native-codegen
|
|
207
|
+
// the module name has the Native prefix comparing to 0.63
|
|
208
|
+
// when reading files we provided
|
|
209
|
+
const nativePrefix = 'Native';
|
|
210
|
+
const preferredModuleName = moduleName.startsWith(nativePrefix)
|
|
211
|
+
? moduleName.substr(nativePrefix.length)
|
|
212
|
+
: moduleName;
|
|
213
|
+
|
|
214
|
+
if (nativeModule.type === 'NativeModule') {
|
|
215
|
+
console.log(`Generating ${preferredModuleName}Spec.g.ts`);
|
|
216
|
+
|
|
217
|
+
const aliasCode = Object.keys(nativeModule.aliases)
|
|
218
|
+
.map(name => translateAlias(name, nativeModule.aliases[name]))
|
|
219
|
+
.join('');
|
|
220
|
+
|
|
221
|
+
const constantType = tryGetConstantType(nativeModule);
|
|
222
|
+
const constantCode =
|
|
223
|
+
constantType === undefined
|
|
224
|
+
? ''
|
|
225
|
+
: ` getConstants(): ${translateType(constantType)}`;
|
|
226
|
+
|
|
227
|
+
const methods = nativeModule.spec.properties.filter(
|
|
228
|
+
prop => prop.name !== 'getConstants',
|
|
229
|
+
);
|
|
230
|
+
const membersCode = methods.map(translateMethod).join('');
|
|
231
|
+
|
|
232
|
+
files.set(
|
|
233
|
+
`${preferredModuleName}Spec.g.ts`,
|
|
234
|
+
moduleTemplate
|
|
235
|
+
.replace(/::_MODULE_ALIASED_STRUCTS_::/g, aliasCode)
|
|
236
|
+
.replace(/::_MODULE_MEMBERS_::/g, constantCode + membersCode)
|
|
237
|
+
.replace(/::_MODULE_NAME_::/g, preferredModuleName)
|
|
238
|
+
.replace(
|
|
239
|
+
/::_MODULE_GETTER_::/g,
|
|
240
|
+
getOptionalTurboModule(nativeModule) ? 'get' : 'getEnforcing',
|
|
241
|
+
),
|
|
242
|
+
);
|
|
243
|
+
}
|
|
244
|
+
}
|
|
245
|
+
|
|
246
|
+
return files;
|
|
247
|
+
}
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Microsoft Corporation.
|
|
3
|
+
* Licensed under the MIT License.
|
|
4
|
+
* @format
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
'use strict';
|
|
8
|
+
|
|
9
|
+
import {NativeModuleBaseTypeAnnotation, Nullable} from 'react-native-tscodegen';
|
|
10
|
+
import {
|
|
11
|
+
AliasMap,
|
|
12
|
+
getAliasCppName,
|
|
13
|
+
getAnonymousAliasCppName,
|
|
14
|
+
} from './AliasManaging';
|
|
15
|
+
|
|
16
|
+
export function translateField(
|
|
17
|
+
type: Nullable<NativeModuleBaseTypeAnnotation>,
|
|
18
|
+
aliases: AliasMap,
|
|
19
|
+
baseAliasName: string,
|
|
20
|
+
): string {
|
|
21
|
+
// avoid: Property 'type' does not exist on type 'never'
|
|
22
|
+
const returnType = type.type;
|
|
23
|
+
switch (type.type) {
|
|
24
|
+
case 'StringTypeAnnotation':
|
|
25
|
+
return 'std::string';
|
|
26
|
+
case 'NumberTypeAnnotation':
|
|
27
|
+
case 'FloatTypeAnnotation':
|
|
28
|
+
case 'DoubleTypeAnnotation':
|
|
29
|
+
return 'double';
|
|
30
|
+
case 'Int32TypeAnnotation':
|
|
31
|
+
return 'int';
|
|
32
|
+
case 'BooleanTypeAnnotation':
|
|
33
|
+
return 'bool';
|
|
34
|
+
case 'ArrayTypeAnnotation':
|
|
35
|
+
if (type.elementType) {
|
|
36
|
+
return `std::vector<${translateField(
|
|
37
|
+
type.elementType,
|
|
38
|
+
aliases,
|
|
39
|
+
`${baseAliasName}_element`,
|
|
40
|
+
)}>`;
|
|
41
|
+
} else {
|
|
42
|
+
return `::React::JSValueArray`;
|
|
43
|
+
}
|
|
44
|
+
case 'GenericObjectTypeAnnotation':
|
|
45
|
+
return '::React::JSValue';
|
|
46
|
+
case 'ObjectTypeAnnotation':
|
|
47
|
+
return getAnonymousAliasCppName(aliases, baseAliasName, type);
|
|
48
|
+
case 'ReservedTypeAnnotation': {
|
|
49
|
+
// avoid: Property 'name' does not exist on type 'never'
|
|
50
|
+
const name = type.name;
|
|
51
|
+
// (#6597)
|
|
52
|
+
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
|
53
|
+
if (name !== 'RootTag')
|
|
54
|
+
throw new Error(
|
|
55
|
+
`Unknown reserved function: ${name} in translateReturnType`,
|
|
56
|
+
);
|
|
57
|
+
return 'double';
|
|
58
|
+
}
|
|
59
|
+
case 'TypeAliasTypeAnnotation':
|
|
60
|
+
return getAliasCppName(type.name);
|
|
61
|
+
case 'NullableTypeAnnotation':
|
|
62
|
+
return `std::optional<${translateField(
|
|
63
|
+
type.typeAnnotation,
|
|
64
|
+
aliases,
|
|
65
|
+
baseAliasName,
|
|
66
|
+
)}>`;
|
|
67
|
+
default:
|
|
68
|
+
throw new Error(`Unhandled type in translateReturnType: ${returnType}`);
|
|
69
|
+
}
|
|
70
|
+
}
|
|
@@ -0,0 +1,220 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Microsoft Corporation.
|
|
3
|
+
* Licensed under the MIT License.
|
|
4
|
+
* @format
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
'use strict';
|
|
8
|
+
|
|
9
|
+
import {
|
|
10
|
+
NamedShape,
|
|
11
|
+
NativeModuleParamTypeAnnotation,
|
|
12
|
+
Nullable,
|
|
13
|
+
} from 'react-native-tscodegen';
|
|
14
|
+
import {
|
|
15
|
+
AliasMap,
|
|
16
|
+
getAliasCppName,
|
|
17
|
+
getAnonymousAliasCppName,
|
|
18
|
+
} from './AliasManaging';
|
|
19
|
+
|
|
20
|
+
type NativeModuleParamShape = NamedShape<
|
|
21
|
+
Nullable<NativeModuleParamTypeAnnotation>
|
|
22
|
+
>;
|
|
23
|
+
|
|
24
|
+
type ParamTarget = 'spec' | 'template' | 'callback-arg' | 'method-arg';
|
|
25
|
+
|
|
26
|
+
function decorateType(type: string, target: ParamTarget): string {
|
|
27
|
+
switch (target) {
|
|
28
|
+
case 'method-arg':
|
|
29
|
+
return `${type} &&`;
|
|
30
|
+
case 'callback-arg':
|
|
31
|
+
return `${type} const &`;
|
|
32
|
+
default:
|
|
33
|
+
return type;
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
function translateParam(
|
|
38
|
+
param: NativeModuleParamTypeAnnotation,
|
|
39
|
+
aliases: AliasMap,
|
|
40
|
+
baseAliasName: string,
|
|
41
|
+
target: ParamTarget,
|
|
42
|
+
): string {
|
|
43
|
+
// avoid: Property 'type' does not exist on type 'never'
|
|
44
|
+
const paramType = param.type;
|
|
45
|
+
switch (param.type) {
|
|
46
|
+
case 'StringTypeAnnotation':
|
|
47
|
+
return 'std::string';
|
|
48
|
+
case 'NumberTypeAnnotation':
|
|
49
|
+
case 'FloatTypeAnnotation':
|
|
50
|
+
case 'DoubleTypeAnnotation':
|
|
51
|
+
return 'double';
|
|
52
|
+
case 'Int32TypeAnnotation':
|
|
53
|
+
return 'int';
|
|
54
|
+
case 'BooleanTypeAnnotation':
|
|
55
|
+
return 'bool';
|
|
56
|
+
case 'FunctionTypeAnnotation': {
|
|
57
|
+
// TODO: type.returnTypeAnnotation
|
|
58
|
+
switch (target) {
|
|
59
|
+
case 'spec':
|
|
60
|
+
return `Callback<${param.params
|
|
61
|
+
.map((p: NativeModuleParamShape) =>
|
|
62
|
+
translateSpecFunctionParam(
|
|
63
|
+
p,
|
|
64
|
+
aliases,
|
|
65
|
+
`${baseAliasName}_${p.name}`,
|
|
66
|
+
),
|
|
67
|
+
)
|
|
68
|
+
.join(', ')}>`;
|
|
69
|
+
case 'template':
|
|
70
|
+
return `std::function<void(${param.params
|
|
71
|
+
.map((p: NativeModuleParamShape) =>
|
|
72
|
+
translateCallbackParam(p, aliases, `${baseAliasName}_${p.name}`),
|
|
73
|
+
)
|
|
74
|
+
.join(', ')})>`;
|
|
75
|
+
default:
|
|
76
|
+
return `std::function<void(${param.params
|
|
77
|
+
.map((p: NativeModuleParamShape) =>
|
|
78
|
+
translateCallbackParam(p, aliases, `${baseAliasName}_${p.name}`),
|
|
79
|
+
)
|
|
80
|
+
.join(', ')})> const &`;
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
case 'ArrayTypeAnnotation':
|
|
84
|
+
if (param.elementType) {
|
|
85
|
+
switch (target) {
|
|
86
|
+
case 'spec':
|
|
87
|
+
case 'template':
|
|
88
|
+
return `std::vector<${translateNullableParamType(
|
|
89
|
+
param.elementType,
|
|
90
|
+
aliases,
|
|
91
|
+
`${baseAliasName}_element`,
|
|
92
|
+
'template',
|
|
93
|
+
'template',
|
|
94
|
+
)}>`;
|
|
95
|
+
default:
|
|
96
|
+
return `std::vector<${translateNullableParamType(
|
|
97
|
+
param.elementType,
|
|
98
|
+
aliases,
|
|
99
|
+
`${baseAliasName}_element`,
|
|
100
|
+
'template',
|
|
101
|
+
'template',
|
|
102
|
+
)}> const &`;
|
|
103
|
+
}
|
|
104
|
+
} else {
|
|
105
|
+
return decorateType('::React::JSValueArray', target);
|
|
106
|
+
}
|
|
107
|
+
case 'GenericObjectTypeAnnotation':
|
|
108
|
+
return decorateType('::React::JSValue', target);
|
|
109
|
+
case 'ObjectTypeAnnotation':
|
|
110
|
+
return decorateType(
|
|
111
|
+
getAnonymousAliasCppName(aliases, baseAliasName, param),
|
|
112
|
+
target,
|
|
113
|
+
);
|
|
114
|
+
case 'ReservedTypeAnnotation': {
|
|
115
|
+
// avoid: Property 'name' does not exist on type 'never'
|
|
116
|
+
const name = param.name;
|
|
117
|
+
// (#6597)
|
|
118
|
+
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
|
119
|
+
if (name !== 'RootTag')
|
|
120
|
+
throw new Error(`Unknown reserved function: ${name} in translateParam`);
|
|
121
|
+
return 'double';
|
|
122
|
+
}
|
|
123
|
+
case 'TypeAliasTypeAnnotation':
|
|
124
|
+
return decorateType(getAliasCppName(param.name), target);
|
|
125
|
+
default:
|
|
126
|
+
throw new Error(`Unhandled type in translateParam: ${paramType}`);
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
function translateNullableParamType(
|
|
131
|
+
paramType: Nullable<NativeModuleParamTypeAnnotation>,
|
|
132
|
+
aliases: AliasMap,
|
|
133
|
+
baseAliasName: string,
|
|
134
|
+
nullableTarget: ParamTarget,
|
|
135
|
+
target: ParamTarget,
|
|
136
|
+
): string {
|
|
137
|
+
switch (paramType.type) {
|
|
138
|
+
case 'NullableTypeAnnotation':
|
|
139
|
+
return `std::optional<${translateParam(
|
|
140
|
+
paramType.typeAnnotation,
|
|
141
|
+
aliases,
|
|
142
|
+
baseAliasName,
|
|
143
|
+
nullableTarget,
|
|
144
|
+
)}>`;
|
|
145
|
+
default:
|
|
146
|
+
return translateParam(paramType, aliases, baseAliasName, target);
|
|
147
|
+
}
|
|
148
|
+
}
|
|
149
|
+
|
|
150
|
+
function translateSpecFunctionParam(
|
|
151
|
+
param: NativeModuleParamShape,
|
|
152
|
+
aliases: AliasMap,
|
|
153
|
+
baseAliasName: string,
|
|
154
|
+
): string {
|
|
155
|
+
return translateNullableParamType(
|
|
156
|
+
param.typeAnnotation,
|
|
157
|
+
aliases,
|
|
158
|
+
baseAliasName,
|
|
159
|
+
'spec',
|
|
160
|
+
'spec',
|
|
161
|
+
);
|
|
162
|
+
}
|
|
163
|
+
|
|
164
|
+
function translateCallbackParam(
|
|
165
|
+
param: NativeModuleParamShape,
|
|
166
|
+
aliases: AliasMap,
|
|
167
|
+
baseAliasName: string,
|
|
168
|
+
): string {
|
|
169
|
+
return translateNullableParamType(
|
|
170
|
+
param.typeAnnotation,
|
|
171
|
+
aliases,
|
|
172
|
+
baseAliasName,
|
|
173
|
+
'template',
|
|
174
|
+
'callback-arg',
|
|
175
|
+
);
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
function translateFunctionParam(
|
|
179
|
+
param: NativeModuleParamShape,
|
|
180
|
+
aliases: AliasMap,
|
|
181
|
+
baseAliasName: string,
|
|
182
|
+
): string {
|
|
183
|
+
return translateNullableParamType(
|
|
184
|
+
param.typeAnnotation,
|
|
185
|
+
aliases,
|
|
186
|
+
baseAliasName,
|
|
187
|
+
'template',
|
|
188
|
+
'method-arg',
|
|
189
|
+
);
|
|
190
|
+
}
|
|
191
|
+
|
|
192
|
+
export function translateSpecArgs(
|
|
193
|
+
params: ReadonlyArray<NativeModuleParamShape>,
|
|
194
|
+
aliases: AliasMap,
|
|
195
|
+
baseAliasName: string,
|
|
196
|
+
) {
|
|
197
|
+
return params.map(param => {
|
|
198
|
+
const translatedParam = translateSpecFunctionParam(
|
|
199
|
+
param,
|
|
200
|
+
aliases,
|
|
201
|
+
`${baseAliasName}_${param.name}`,
|
|
202
|
+
);
|
|
203
|
+
return `${translatedParam}`;
|
|
204
|
+
});
|
|
205
|
+
}
|
|
206
|
+
|
|
207
|
+
export function translateArgs(
|
|
208
|
+
params: ReadonlyArray<NativeModuleParamShape>,
|
|
209
|
+
aliases: AliasMap,
|
|
210
|
+
baseAliasName: string,
|
|
211
|
+
) {
|
|
212
|
+
return params.map(param => {
|
|
213
|
+
const translatedParam = translateFunctionParam(
|
|
214
|
+
param,
|
|
215
|
+
aliases,
|
|
216
|
+
`${baseAliasName}_${param.name}`,
|
|
217
|
+
);
|
|
218
|
+
return `${translatedParam} ${param.name}`;
|
|
219
|
+
});
|
|
220
|
+
}
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Microsoft Corporation.
|
|
3
|
+
* Licensed under the MIT License.
|
|
4
|
+
* @format
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
'use strict';
|
|
8
|
+
|
|
9
|
+
import {
|
|
10
|
+
NativeModuleReturnTypeAnnotation,
|
|
11
|
+
Nullable,
|
|
12
|
+
} from 'react-native-tscodegen';
|
|
13
|
+
import {
|
|
14
|
+
AliasMap,
|
|
15
|
+
getAliasCppName,
|
|
16
|
+
getAnonymousAliasCppName,
|
|
17
|
+
} from './AliasManaging';
|
|
18
|
+
|
|
19
|
+
function translateReturnType(
|
|
20
|
+
type: Nullable<NativeModuleReturnTypeAnnotation>,
|
|
21
|
+
aliases: AliasMap,
|
|
22
|
+
baseAliasName: string,
|
|
23
|
+
): string {
|
|
24
|
+
// avoid: Property 'type' does not exist on type 'never'
|
|
25
|
+
const returnType = type.type;
|
|
26
|
+
switch (type.type) {
|
|
27
|
+
case 'VoidTypeAnnotation':
|
|
28
|
+
case 'PromiseTypeAnnotation':
|
|
29
|
+
return 'void';
|
|
30
|
+
case 'StringTypeAnnotation':
|
|
31
|
+
return 'std::string';
|
|
32
|
+
case 'NumberTypeAnnotation':
|
|
33
|
+
case 'FloatTypeAnnotation':
|
|
34
|
+
case 'DoubleTypeAnnotation':
|
|
35
|
+
return 'double';
|
|
36
|
+
case 'Int32TypeAnnotation':
|
|
37
|
+
return 'int';
|
|
38
|
+
case 'BooleanTypeAnnotation':
|
|
39
|
+
return 'bool';
|
|
40
|
+
case 'ArrayTypeAnnotation':
|
|
41
|
+
if (type.elementType) {
|
|
42
|
+
return `std::vector<${translateReturnType(
|
|
43
|
+
type.elementType,
|
|
44
|
+
aliases,
|
|
45
|
+
`${baseAliasName}_element`,
|
|
46
|
+
)}>`;
|
|
47
|
+
} else {
|
|
48
|
+
return '::React::JSValueArray';
|
|
49
|
+
}
|
|
50
|
+
case 'GenericObjectTypeAnnotation':
|
|
51
|
+
return '::React::JSValue';
|
|
52
|
+
case 'ObjectTypeAnnotation':
|
|
53
|
+
return getAnonymousAliasCppName(aliases, baseAliasName, type);
|
|
54
|
+
case 'ReservedTypeAnnotation': {
|
|
55
|
+
// avoid: Property 'name' does not exist on type 'never'
|
|
56
|
+
const name = type.name;
|
|
57
|
+
// (#6597)
|
|
58
|
+
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
|
59
|
+
if (name !== 'RootTag')
|
|
60
|
+
throw new Error(
|
|
61
|
+
`Unknown reserved function: ${name} in translateReturnType`,
|
|
62
|
+
);
|
|
63
|
+
return 'double';
|
|
64
|
+
}
|
|
65
|
+
case 'TypeAliasTypeAnnotation':
|
|
66
|
+
return getAliasCppName(type.name);
|
|
67
|
+
case 'NullableTypeAnnotation':
|
|
68
|
+
return `std::optional<${translateReturnType(
|
|
69
|
+
type.typeAnnotation,
|
|
70
|
+
aliases,
|
|
71
|
+
baseAliasName,
|
|
72
|
+
)}>`;
|
|
73
|
+
default:
|
|
74
|
+
throw new Error(`Unhandled type in translateReturnType: ${returnType}`);
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
export function translateSpecReturnType(
|
|
79
|
+
type: Nullable<NativeModuleReturnTypeAnnotation>,
|
|
80
|
+
aliases: AliasMap,
|
|
81
|
+
baseAliasName: string,
|
|
82
|
+
) {
|
|
83
|
+
return translateReturnType(type, aliases, `${baseAliasName}_returnType`);
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
export function translateImplReturnType(
|
|
87
|
+
type: Nullable<NativeModuleReturnTypeAnnotation>,
|
|
88
|
+
aliases: AliasMap,
|
|
89
|
+
baseAliasName: string,
|
|
90
|
+
) {
|
|
91
|
+
return translateReturnType(type, aliases, `${baseAliasName}_returnType`);
|
|
92
|
+
}
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Microsoft Corporation.
|
|
3
|
+
* Licensed under the MIT License.
|
|
4
|
+
* @format
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
'use strict';
|
|
8
|
+
|
|
9
|
+
import {NativeModuleSchema} from 'react-native-tscodegen';
|
|
10
|
+
import {AliasMap, getAnonymousAliasCppName} from './AliasManaging';
|
|
11
|
+
|
|
12
|
+
export function generateValidateConstants(
|
|
13
|
+
nativeModule: NativeModuleSchema,
|
|
14
|
+
aliases: AliasMap,
|
|
15
|
+
): [string, string] | undefined {
|
|
16
|
+
const candidates = nativeModule.spec.properties.filter(
|
|
17
|
+
prop => prop.name === 'getConstants',
|
|
18
|
+
);
|
|
19
|
+
if (candidates.length === 0) {
|
|
20
|
+
return undefined;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
const getConstant = candidates[0];
|
|
24
|
+
const funcType =
|
|
25
|
+
getConstant.typeAnnotation.type === 'NullableTypeAnnotation'
|
|
26
|
+
? getConstant.typeAnnotation.typeAnnotation
|
|
27
|
+
: getConstant.typeAnnotation;
|
|
28
|
+
if (
|
|
29
|
+
funcType.params.length > 0 ||
|
|
30
|
+
funcType.returnTypeAnnotation.type !== 'ObjectTypeAnnotation'
|
|
31
|
+
) {
|
|
32
|
+
return undefined;
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
const constantType = funcType.returnTypeAnnotation;
|
|
36
|
+
if (constantType.properties.length === 0) {
|
|
37
|
+
return undefined;
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
const cppName = getAnonymousAliasCppName(aliases, 'Constants', constantType);
|
|
41
|
+
|
|
42
|
+
return [
|
|
43
|
+
` TypedConstant<${cppName}>{0},`,
|
|
44
|
+
` REACT_SHOW_CONSTANT_SPEC_ERRORS(
|
|
45
|
+
0,
|
|
46
|
+
"${cppName}",
|
|
47
|
+
" REACT_GET_CONSTANTS(GetConstants) ${cppName} GetConstants() noexcept {/*implementation*/}\\n"
|
|
48
|
+
" REACT_GET_CONSTANTS(GetConstants) static ${cppName} GetConstants() noexcept {/*implementation*/}\\n");`,
|
|
49
|
+
];
|
|
50
|
+
}
|