Start to use the Obj-C JSContext instead of the C API

Summary: The Obj-C API is usually easier to work with, and also makes it very easy to use the C API when necessary (performance, for example). This diff just switches the designated initializer of RCTContextExecutor to take a JSContext instead of JSGlobalContextRef, but the old initializer still works if needed.

I was doing some memory leak investigation and it is easier with ARC so I wanted to incrementally move the executor to Obj-C.
Closes https://github.com/facebook/react-native/pull/2159

Reviewed By: svcscm

Differential Revision: D2554890

Pulled By: tadeuzagallo

fb-gh-sync-id: 75b96d04cddff68fa3daf5d0fafdffad21dae307
This commit is contained in:
James Ide 2015-10-19 03:49:43 -07:00 committed by facebook-github-bot-7
parent 716f7e8ef2
commit 45d2c691a3
2 changed files with 31 additions and 15 deletions

View File

@ -19,10 +19,16 @@
@interface RCTContextExecutor : NSObject <RCTJavaScriptExecutor>
/**
* Configures the executor to run JavaScript on a custom performer.
* Configures the executor to run JavaScript on a specific thread with a given JS context.
* You probably don't want to use this; use -init instead.
*/
- (instancetype)initWithJavaScriptThread:(NSThread *)javaScriptThread
globalContextRef:(JSGlobalContextRef)context NS_DESIGNATED_INITIALIZER;
context:(JSContext *)context NS_DESIGNATED_INITIALIZER;
/**
* Like -[initWithJavaScriptThread:context:] but uses JSGlobalContextRef from JavaScriptCore's C API.
*/
- (instancetype)initWithJavaScriptThread:(NSThread *)javaScriptThread
globalContextRef:(JSGlobalContextRef)contextRef;
@end

View File

@ -42,9 +42,10 @@ static NSString * const RCTJSCProfilerEnabledDefaultsKey = @"RCTJSCProfilerEnabl
@interface RCTJavaScriptContext : NSObject <RCTInvalidating>
@property (nonatomic, strong, readonly) JSContext *context;
@property (nonatomic, assign, readonly) JSGlobalContextRef ctx;
- (instancetype)initWithJSContext:(JSGlobalContextRef)context NS_DESIGNATED_INITIALIZER;
- (instancetype)initWithJSContext:(JSContext *)context NS_DESIGNATED_INITIALIZER;
@end
@ -53,10 +54,10 @@ static NSString * const RCTJSCProfilerEnabledDefaultsKey = @"RCTJSCProfilerEnabl
RCTJavaScriptContext *_self;
}
- (instancetype)initWithJSContext:(JSGlobalContextRef)context
- (instancetype)initWithJSContext:(JSContext *)context
{
if ((self = [super init])) {
_ctx = context;
_context = context;
_self = self;
}
return self;
@ -64,16 +65,20 @@ static NSString * const RCTJSCProfilerEnabledDefaultsKey = @"RCTJSCProfilerEnabl
RCT_NOT_IMPLEMENTED(-(instancetype)init)
- (JSGlobalContextRef)ctx
{
return _context.JSGlobalContextRef;
}
- (BOOL)isValid
{
return _ctx != NULL;
return _context != nil;
}
- (void)invalidate
{
if (self.isValid) {
JSGlobalContextRelease(_ctx);
_ctx = NULL;
_context = nil;
_self = nil;
}
}
@ -282,11 +287,11 @@ static void RCTInstallJSCProfiler(RCTBridge *bridge, JSContextRef context)
javaScriptThread.threadPriority = [NSThread mainThread].threadPriority;
[javaScriptThread start];
return [self initWithJavaScriptThread:javaScriptThread globalContextRef:NULL];
return [self initWithJavaScriptThread:javaScriptThread context:nil];
}
- (instancetype)initWithJavaScriptThread:(NSThread *)javaScriptThread
globalContextRef:(JSGlobalContextRef)context
context:(JSContext *)context
{
RCTAssert(javaScriptThread != nil,
@"Can't initialize RCTContextExecutor without a javaScriptThread");
@ -301,10 +306,8 @@ static void RCTInstallJSCProfiler(RCTBridge *bridge, JSContextRef context)
return;
}
// Assumes that no other JS tasks are scheduled before.
JSGlobalContextRef ctx;
if (context) {
ctx = JSGlobalContextRetain(context);
strongSelf->_context = [[RCTJavaScriptContext alloc] initWithJSContext:ctx];
strongSelf->_context = [[RCTJavaScriptContext alloc] initWithJSContext:context];
}
}];
}
@ -312,6 +315,13 @@ static void RCTInstallJSCProfiler(RCTBridge *bridge, JSContextRef context)
return self;
}
- (instancetype)initWithJavaScriptThread:(NSThread *)javaScriptThread
globalContextRef:(JSGlobalContextRef)contextRef
{
JSContext *context = contextRef ? [JSContext contextWithJSGlobalContextRef:contextRef] : nil;
return [self initWithJavaScriptThread:javaScriptThread context:context];
}
- (void)setUp
{
__weak RCTContextExecutor *weakSelf = self;
@ -321,8 +331,8 @@ static void RCTInstallJSCProfiler(RCTBridge *bridge, JSContextRef context)
return;
}
if (!strongSelf->_context) {
JSGlobalContextRef ctx = JSGlobalContextCreate(NULL);
strongSelf->_context = [[RCTJavaScriptContext alloc] initWithJSContext:ctx];
JSContext *context = [[JSContext alloc] init];
strongSelf->_context = [[RCTJavaScriptContext alloc] initWithJSContext:context];
}
[strongSelf _addNativeHook:RCTNativeLoggingHook withName:"nativeLoggingHook"];
[strongSelf _addNativeHook:RCTNoop withName:"noop"];