mirror of
https://github.com/facebook/react-native.git
synced 2025-11-01 09:14:26 +00:00
generate bindings for objcpp TM
Summary: In this diff I add generetion of bindings for objcpp TM. Reviewed By: RSNara Differential Revision: D16438572 fbshipit-source-id: e92163b1b42306eec931e465b89b176f0fd8a658
This commit is contained in:
committed by
Facebook Github Bot
parent
69888b0820
commit
451171acb1
@@ -0,0 +1,160 @@
|
||||
/**
|
||||
* Copyright (c) Facebook, Inc. and its 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
|
||||
* @format
|
||||
*/
|
||||
|
||||
'use strict';
|
||||
|
||||
import type {SchemaType} from '../../CodegenSchema';
|
||||
|
||||
type FilesOutput = Map<string, string>;
|
||||
|
||||
const propertyHeaderTemplate =
|
||||
'static facebook::jsi::Value __hostFunction_Native::_MODULE_NAME_::SpecJSI_::_PROPERTY_NAME_::(facebook::jsi::Runtime& rt, TurboModule &turboModule, const facebook::jsi::Value* args, size_t count) {';
|
||||
|
||||
const propertyCastTemplate = `static_cast<ObjCTurboModule &>(turboModule)
|
||||
.invokeObjCMethod(rt, ::_KIND_::, "::_PROPERTY_NAME_::", @selector(::_PROPERTY_NAME_::::_ARGS_::), args, count);`;
|
||||
|
||||
const propertyTemplate = `
|
||||
${propertyHeaderTemplate}
|
||||
return ${propertyCastTemplate}
|
||||
}`.trim();
|
||||
|
||||
const proprertyDefTemplate =
|
||||
' methodMap_["::_PROPERTY_NAME_::"] = MethodMetadata {::_ARGS_COUNT_::, __hostFunction_Native::_MODULE_NAME_::SpecJSI_::_PROPERTY_NAME_::};';
|
||||
|
||||
const moduleTemplate = `
|
||||
::_TURBOMODULE_METHOD_INVOKERS_::
|
||||
|
||||
Native::_MODULE_NAME_::SpecJSI::Native::_MODULE_NAME_::SpecJSI(id<RCTTurboModule> instance, std::shared_ptr<JSCallInvoker> jsInvoker)
|
||||
: ObjCTurboModule("SampleTurboModule", instance, jsInvoker) {
|
||||
::_PROPERTIES_MAP_::
|
||||
}`.trim();
|
||||
|
||||
const template = `
|
||||
/**
|
||||
* Copyright (c) Facebook, Inc. and its affiliates.
|
||||
*
|
||||
* This source code is licensed under the MIT license found in the
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*/
|
||||
|
||||
#include <react/modules/::_LIBRARY_NAME_::/RCTNativeModules.h>
|
||||
|
||||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
::_MODULES_::
|
||||
|
||||
|
||||
} // namespace react
|
||||
} // namespace facebook
|
||||
`;
|
||||
|
||||
function translateReturnTypeToKind(type): string {
|
||||
switch (type) {
|
||||
case 'VoidTypeAnnotation':
|
||||
return 'VoidKind';
|
||||
case 'StringTypeAnnotation':
|
||||
return 'StringKind';
|
||||
case 'BooleanTypeAnnotation':
|
||||
return 'BooleanKind';
|
||||
case 'NumberTypeAnnotation':
|
||||
case 'FloatTypeAnnotation':
|
||||
case 'Int32TypeAnnotation':
|
||||
return 'NumberKind';
|
||||
case 'GenericPromiseTypeAnnotation':
|
||||
return 'PromiseKind';
|
||||
case 'GenericObjectTypeAnnotation':
|
||||
case 'ObjectTypeAnnotation':
|
||||
return 'ObjectKind';
|
||||
case 'ArrayTypeAnnotation':
|
||||
return 'ArrayKind';
|
||||
default:
|
||||
(type: empty);
|
||||
throw new Error(`Unknown prop type for returning value, found: ${type}"`);
|
||||
}
|
||||
}
|
||||
|
||||
function tranlsateMethodForImplementation(property): string {
|
||||
const numberOfParams =
|
||||
property.typeAnnotation.params.length +
|
||||
(property.typeAnnotation.returnTypeAnnotation.type ===
|
||||
'GenericPromiseTypeAnnotation'
|
||||
? 2
|
||||
: 0);
|
||||
const translatedArguments = property.typeAnnotation.params
|
||||
.map(param => param.name)
|
||||
.concat(
|
||||
property.typeAnnotation.returnTypeAnnotation.type ===
|
||||
'GenericPromiseTypeAnnotation'
|
||||
? ['resolve', 'reject']
|
||||
: [],
|
||||
)
|
||||
.slice(1)
|
||||
.join(':')
|
||||
.concat(':');
|
||||
return propertyTemplate
|
||||
.replace(
|
||||
/::_KIND_::/g,
|
||||
translateReturnTypeToKind(
|
||||
property.typeAnnotation.returnTypeAnnotation.type,
|
||||
),
|
||||
)
|
||||
.replace(/::_PROPERTY_NAME_::/g, property.name)
|
||||
.replace(
|
||||
/::_ARGS_::/g,
|
||||
numberOfParams === 0
|
||||
? ''
|
||||
: (numberOfParams === 1 ? '' : ':') + translatedArguments,
|
||||
);
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
generate(libraryName: string, schema: SchemaType): FilesOutput {
|
||||
const nativeModules = Object.keys(schema.modules)
|
||||
.map(moduleName => {
|
||||
const modules = schema.modules[moduleName].nativeModules;
|
||||
if (modules == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return modules;
|
||||
})
|
||||
.filter(Boolean)
|
||||
.reduce((acc, modules) => Object.assign(acc, modules), {});
|
||||
|
||||
const modules = Object.keys(nativeModules)
|
||||
.map(name => {
|
||||
const {properties} = nativeModules[name];
|
||||
const translatedMethods = properties
|
||||
.map(property => tranlsateMethodForImplementation(property))
|
||||
.join('\n');
|
||||
return moduleTemplate
|
||||
.replace(/::_TURBOMODULE_METHOD_INVOKERS_::/g, translatedMethods)
|
||||
.replace(
|
||||
'::_PROPERTIES_MAP_::',
|
||||
properties
|
||||
.map(({name: propertyName, typeAnnotation: {params}}) =>
|
||||
proprertyDefTemplate
|
||||
.replace(/::_PROPERTY_NAME_::/g, propertyName)
|
||||
.replace(/::_ARGS_COUNT_::/g, params.length.toString()),
|
||||
)
|
||||
.join('\n'),
|
||||
)
|
||||
.replace(/::_MODULE_NAME_::/g, name);
|
||||
})
|
||||
.join('\n');
|
||||
|
||||
const fileName = 'RCTNativeModules.mm';
|
||||
const replacedTemplate = template
|
||||
.replace(/::_MODULES_::/g, modules)
|
||||
.replace(/::_LIBRARY_NAME_::/g, libraryName);
|
||||
return new Map([[fileName, replacedTemplate]]);
|
||||
},
|
||||
};
|
||||
+27
@@ -0,0 +1,27 @@
|
||||
/**
|
||||
* Copyright (c) Facebook, Inc. and its affiliates.
|
||||
*
|
||||
* This source code is licensed under the MIT license found in the
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*
|
||||
* @emails oncall+react_native
|
||||
* @flow strict-local
|
||||
* @format
|
||||
*/
|
||||
|
||||
'use strict';
|
||||
|
||||
const fixtures = require('../__test_fixtures__/fixtures.js');
|
||||
const generator = require('../GenerateModuleMm.js');
|
||||
|
||||
describe('GenerateModuleHObjCpp', () => {
|
||||
Object.keys(fixtures)
|
||||
.sort()
|
||||
.forEach(fixtureName => {
|
||||
const fixture = fixtures[fixtureName];
|
||||
|
||||
it(`can generate fixture ${fixtureName}`, () => {
|
||||
expect(generator.generate(fixtureName, fixture)).toMatchSnapshot();
|
||||
});
|
||||
});
|
||||
});
|
||||
+189
@@ -0,0 +1,189 @@
|
||||
// Jest Snapshot v1, https://goo.gl/fbAQLP
|
||||
|
||||
exports[`GenerateModuleHObjCpp can generate fixture EMPTY_NATIVE_MODULES 1`] = `
|
||||
Map {
|
||||
"RCTNativeModules.mm" => "
|
||||
/**
|
||||
* Copyright (c) Facebook, Inc. and its affiliates.
|
||||
*
|
||||
* This source code is licensed under the MIT license found in the
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*/
|
||||
|
||||
#include <react/modules/EMPTY_NATIVE_MODULES/RCTNativeModules.h>
|
||||
|
||||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
|
||||
|
||||
NativeSampleTurboModuleSpecJSI::NativeSampleTurboModuleSpecJSI(id<RCTTurboModule> instance, std::shared_ptr<JSCallInvoker> jsInvoker)
|
||||
: ObjCTurboModule(\\"SampleTurboModule\\", instance, jsInvoker) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
} // namespace react
|
||||
} // namespace facebook
|
||||
",
|
||||
}
|
||||
`;
|
||||
|
||||
exports[`GenerateModuleHObjCpp can generate fixture SIMPLE_NATIVE_MODULES 1`] = `
|
||||
Map {
|
||||
"RCTNativeModules.mm" => "
|
||||
/**
|
||||
* Copyright (c) Facebook, Inc. and its affiliates.
|
||||
*
|
||||
* This source code is licensed under the MIT license found in the
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*/
|
||||
|
||||
#include <react/modules/SIMPLE_NATIVE_MODULES/RCTNativeModules.h>
|
||||
|
||||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
static facebook::jsi::Value __hostFunction_NativeSampleTurboModuleSpecJSI_getConstants(facebook::jsi::Runtime& rt, TurboModule &turboModule, const facebook::jsi::Value* args, size_t count) {
|
||||
return static_cast<ObjCTurboModule &>(turboModule)
|
||||
.invokeObjCMethod(rt, ObjectKind, \\"getConstants\\", @selector(getConstants), args, count);
|
||||
}
|
||||
static facebook::jsi::Value __hostFunction_NativeSampleTurboModuleSpecJSI_voidFunc(facebook::jsi::Runtime& rt, TurboModule &turboModule, const facebook::jsi::Value* args, size_t count) {
|
||||
return static_cast<ObjCTurboModule &>(turboModule)
|
||||
.invokeObjCMethod(rt, VoidKind, \\"voidFunc\\", @selector(voidFunc), args, count);
|
||||
}
|
||||
static facebook::jsi::Value __hostFunction_NativeSampleTurboModuleSpecJSI_getBool(facebook::jsi::Runtime& rt, TurboModule &turboModule, const facebook::jsi::Value* args, size_t count) {
|
||||
return static_cast<ObjCTurboModule &>(turboModule)
|
||||
.invokeObjCMethod(rt, BooleanKind, \\"getBool\\", @selector(getBool:), args, count);
|
||||
}
|
||||
static facebook::jsi::Value __hostFunction_NativeSampleTurboModuleSpecJSI_getNumber(facebook::jsi::Runtime& rt, TurboModule &turboModule, const facebook::jsi::Value* args, size_t count) {
|
||||
return static_cast<ObjCTurboModule &>(turboModule)
|
||||
.invokeObjCMethod(rt, NumberKind, \\"getNumber\\", @selector(getNumber:), args, count);
|
||||
}
|
||||
static facebook::jsi::Value __hostFunction_NativeSampleTurboModuleSpecJSI_getString(facebook::jsi::Runtime& rt, TurboModule &turboModule, const facebook::jsi::Value* args, size_t count) {
|
||||
return static_cast<ObjCTurboModule &>(turboModule)
|
||||
.invokeObjCMethod(rt, StringKind, \\"getString\\", @selector(getString:), args, count);
|
||||
}
|
||||
static facebook::jsi::Value __hostFunction_NativeSampleTurboModuleSpecJSI_getArray(facebook::jsi::Runtime& rt, TurboModule &turboModule, const facebook::jsi::Value* args, size_t count) {
|
||||
return static_cast<ObjCTurboModule &>(turboModule)
|
||||
.invokeObjCMethod(rt, ArrayKind, \\"getArray\\", @selector(getArray:), args, count);
|
||||
}
|
||||
static facebook::jsi::Value __hostFunction_NativeSampleTurboModuleSpecJSI_getObject(facebook::jsi::Runtime& rt, TurboModule &turboModule, const facebook::jsi::Value* args, size_t count) {
|
||||
return static_cast<ObjCTurboModule &>(turboModule)
|
||||
.invokeObjCMethod(rt, ObjectKind, \\"getObject\\", @selector(getObject:), args, count);
|
||||
}
|
||||
static facebook::jsi::Value __hostFunction_NativeSampleTurboModuleSpecJSI_getValue(facebook::jsi::Runtime& rt, TurboModule &turboModule, const facebook::jsi::Value* args, size_t count) {
|
||||
return static_cast<ObjCTurboModule &>(turboModule)
|
||||
.invokeObjCMethod(rt, ObjectKind, \\"getValue\\", @selector(getValue:y:z:), args, count);
|
||||
}
|
||||
static facebook::jsi::Value __hostFunction_NativeSampleTurboModuleSpecJSI_getValueWithCallback(facebook::jsi::Runtime& rt, TurboModule &turboModule, const facebook::jsi::Value* args, size_t count) {
|
||||
return static_cast<ObjCTurboModule &>(turboModule)
|
||||
.invokeObjCMethod(rt, VoidKind, \\"getValueWithCallback\\", @selector(getValueWithCallback:), args, count);
|
||||
}
|
||||
static facebook::jsi::Value __hostFunction_NativeSampleTurboModuleSpecJSI_getValueWithPromise(facebook::jsi::Runtime& rt, TurboModule &turboModule, const facebook::jsi::Value* args, size_t count) {
|
||||
return static_cast<ObjCTurboModule &>(turboModule)
|
||||
.invokeObjCMethod(rt, PromiseKind, \\"getValueWithPromise\\", @selector(getValueWithPromise:resolve:reject:), args, count);
|
||||
}
|
||||
|
||||
NativeSampleTurboModuleSpecJSI::NativeSampleTurboModuleSpecJSI(id<RCTTurboModule> instance, std::shared_ptr<JSCallInvoker> jsInvoker)
|
||||
: ObjCTurboModule(\\"SampleTurboModule\\", instance, jsInvoker) {
|
||||
methodMap_[\\"getConstants\\"] = MethodMetadata {0, __hostFunction_NativeSampleTurboModuleSpecJSI_getConstants};
|
||||
methodMap_[\\"voidFunc\\"] = MethodMetadata {0, __hostFunction_NativeSampleTurboModuleSpecJSI_voidFunc};
|
||||
methodMap_[\\"getBool\\"] = MethodMetadata {1, __hostFunction_NativeSampleTurboModuleSpecJSI_getBool};
|
||||
methodMap_[\\"getNumber\\"] = MethodMetadata {1, __hostFunction_NativeSampleTurboModuleSpecJSI_getNumber};
|
||||
methodMap_[\\"getString\\"] = MethodMetadata {1, __hostFunction_NativeSampleTurboModuleSpecJSI_getString};
|
||||
methodMap_[\\"getArray\\"] = MethodMetadata {1, __hostFunction_NativeSampleTurboModuleSpecJSI_getArray};
|
||||
methodMap_[\\"getObject\\"] = MethodMetadata {1, __hostFunction_NativeSampleTurboModuleSpecJSI_getObject};
|
||||
methodMap_[\\"getValue\\"] = MethodMetadata {3, __hostFunction_NativeSampleTurboModuleSpecJSI_getValue};
|
||||
methodMap_[\\"getValueWithCallback\\"] = MethodMetadata {1, __hostFunction_NativeSampleTurboModuleSpecJSI_getValueWithCallback};
|
||||
methodMap_[\\"getValueWithPromise\\"] = MethodMetadata {1, __hostFunction_NativeSampleTurboModuleSpecJSI_getValueWithPromise};
|
||||
}
|
||||
|
||||
|
||||
} // namespace react
|
||||
} // namespace facebook
|
||||
",
|
||||
}
|
||||
`;
|
||||
|
||||
exports[`GenerateModuleHObjCpp can generate fixture TWO_MODULES_DIFFERENT_FILES 1`] = `
|
||||
Map {
|
||||
"RCTNativeModules.mm" => "
|
||||
/**
|
||||
* Copyright (c) Facebook, Inc. and its affiliates.
|
||||
*
|
||||
* This source code is licensed under the MIT license found in the
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*/
|
||||
|
||||
#include <react/modules/TWO_MODULES_DIFFERENT_FILES/RCTNativeModules.h>
|
||||
|
||||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
static facebook::jsi::Value __hostFunction_NativeSampleTurboModuleSpecJSI_voidFunc(facebook::jsi::Runtime& rt, TurboModule &turboModule, const facebook::jsi::Value* args, size_t count) {
|
||||
return static_cast<ObjCTurboModule &>(turboModule)
|
||||
.invokeObjCMethod(rt, VoidKind, \\"voidFunc\\", @selector(voidFunc), args, count);
|
||||
}
|
||||
|
||||
NativeSampleTurboModuleSpecJSI::NativeSampleTurboModuleSpecJSI(id<RCTTurboModule> instance, std::shared_ptr<JSCallInvoker> jsInvoker)
|
||||
: ObjCTurboModule(\\"SampleTurboModule\\", instance, jsInvoker) {
|
||||
methodMap_[\\"voidFunc\\"] = MethodMetadata {0, __hostFunction_NativeSampleTurboModuleSpecJSI_voidFunc};
|
||||
}
|
||||
static facebook::jsi::Value __hostFunction_NativeSample2TurboModuleSpecJSI_voidFunc(facebook::jsi::Runtime& rt, TurboModule &turboModule, const facebook::jsi::Value* args, size_t count) {
|
||||
return static_cast<ObjCTurboModule &>(turboModule)
|
||||
.invokeObjCMethod(rt, VoidKind, \\"voidFunc\\", @selector(voidFunc), args, count);
|
||||
}
|
||||
|
||||
NativeSample2TurboModuleSpecJSI::NativeSample2TurboModuleSpecJSI(id<RCTTurboModule> instance, std::shared_ptr<JSCallInvoker> jsInvoker)
|
||||
: ObjCTurboModule(\\"SampleTurboModule\\", instance, jsInvoker) {
|
||||
methodMap_[\\"voidFunc\\"] = MethodMetadata {0, __hostFunction_NativeSample2TurboModuleSpecJSI_voidFunc};
|
||||
}
|
||||
|
||||
|
||||
} // namespace react
|
||||
} // namespace facebook
|
||||
",
|
||||
}
|
||||
`;
|
||||
|
||||
exports[`GenerateModuleHObjCpp can generate fixture TWO_MODULES_SAME_FILE 1`] = `
|
||||
Map {
|
||||
"RCTNativeModules.mm" => "
|
||||
/**
|
||||
* Copyright (c) Facebook, Inc. and its affiliates.
|
||||
*
|
||||
* This source code is licensed under the MIT license found in the
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*/
|
||||
|
||||
#include <react/modules/TWO_MODULES_SAME_FILE/RCTNativeModules.h>
|
||||
|
||||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
static facebook::jsi::Value __hostFunction_NativeSampleTurboModuleSpecJSI_voidFunc(facebook::jsi::Runtime& rt, TurboModule &turboModule, const facebook::jsi::Value* args, size_t count) {
|
||||
return static_cast<ObjCTurboModule &>(turboModule)
|
||||
.invokeObjCMethod(rt, VoidKind, \\"voidFunc\\", @selector(voidFunc), args, count);
|
||||
}
|
||||
|
||||
NativeSampleTurboModuleSpecJSI::NativeSampleTurboModuleSpecJSI(id<RCTTurboModule> instance, std::shared_ptr<JSCallInvoker> jsInvoker)
|
||||
: ObjCTurboModule(\\"SampleTurboModule\\", instance, jsInvoker) {
|
||||
methodMap_[\\"voidFunc\\"] = MethodMetadata {0, __hostFunction_NativeSampleTurboModuleSpecJSI_voidFunc};
|
||||
}
|
||||
static facebook::jsi::Value __hostFunction_NativeSample2TurboModuleSpecJSI_voidFunc(facebook::jsi::Runtime& rt, TurboModule &turboModule, const facebook::jsi::Value* args, size_t count) {
|
||||
return static_cast<ObjCTurboModule &>(turboModule)
|
||||
.invokeObjCMethod(rt, VoidKind, \\"voidFunc\\", @selector(voidFunc), args, count);
|
||||
}
|
||||
|
||||
NativeSample2TurboModuleSpecJSI::NativeSample2TurboModuleSpecJSI(id<RCTTurboModule> instance, std::shared_ptr<JSCallInvoker> jsInvoker)
|
||||
: ObjCTurboModule(\\"SampleTurboModule\\", instance, jsInvoker) {
|
||||
methodMap_[\\"voidFunc\\"] = MethodMetadata {0, __hostFunction_NativeSample2TurboModuleSpecJSI_voidFunc};
|
||||
}
|
||||
|
||||
|
||||
} // namespace react
|
||||
} // namespace facebook
|
||||
",
|
||||
}
|
||||
`;
|
||||
Reference in New Issue
Block a user