From 2fe1f0d26e0083e93e3b99f6de0b849d095fa90b Mon Sep 17 00:00:00 2001 From: Scott Kyle Date: Thu, 22 Oct 2015 02:49:15 -0700 Subject: [PATCH] Fix RealmReactTests to work through Chrome The key idea was the cycle the runloop once after receiving the RCTJavaScriptDidLoadNotification so that the RCTDevMenu could also handle that notification and setup the bridge properly, as well as not block the main thread by spinning the runloop instead. --- .../ios/ReactTestsTests/RealmReactTests.m | 39 ++++++++++++------- 1 file changed, 24 insertions(+), 15 deletions(-) diff --git a/tests/ReactTests/ios/ReactTestsTests/RealmReactTests.m b/tests/ReactTests/ios/ReactTestsTests/RealmReactTests.m index 58adc9f8..f4d0e323 100644 --- a/tests/ReactTests/ios/ReactTestsTests/RealmReactTests.m +++ b/tests/ReactTests/ios/ReactTestsTests/RealmReactTests.m @@ -40,6 +40,9 @@ static id s_currentJavaScriptExecutor; exit(1); } + // Wait for the RCTDevMenu to handle this notification and act upon it. + [[NSRunLoop currentRunLoop] runMode:NSDefaultRunLoopMode beforeDate:[NSDate dateWithTimeIntervalSinceNow:0.1]]; + s_currentJavaScriptExecutor = [bridge valueForKey:@"javaScriptExecutor"]; // FIXME: Remove this nonsense once the crashes go away when a test fails! @@ -66,43 +69,49 @@ static id s_currentJavaScriptExecutor; } + (NSNotification *)waitForNotification:(NSString *)notificationName { - NSRunLoop *runLoop = [NSRunLoop currentRunLoop]; NSNotificationCenter *nc = [NSNotificationCenter defaultCenter]; + __block BOOL condition = NO; __block NSNotification *notification; id token = [nc addObserverForName:notificationName object:nil queue:[NSOperationQueue mainQueue] usingBlock:^(NSNotification *note) { + condition = YES; notification = note; }]; - while (!notification) { + [self waitForCondition:&condition]; + [nc removeObserver:token]; + + return notification; +} + ++ (void)waitForCondition:(BOOL *)condition { + NSRunLoop *runLoop = [NSRunLoop currentRunLoop]; + + while (!*condition) { @autoreleasepool { [runLoop runMode:NSDefaultRunLoopMode beforeDate:[NSDate distantFuture]]; } } - - [nc removeObserver:token]; - return notification; } + (id)invokeMethod:(NSString *)method inModule:(NSString *)module error:(NSError * __strong *)outError { module = [NSString stringWithFormat:@"realm-tests/%@.js", module]; - dispatch_group_t group = dispatch_group_create(); + __block BOOL condition = NO; __block id result; - dispatch_group_enter(group); - [s_currentJavaScriptExecutor executeJSCall:module method:method arguments:@[] callback:^(id json, NSError *error) { - result = json; + dispatch_async(dispatch_get_main_queue(), ^{ + condition = YES; + result = json; - if (error && outError) { - *outError = error; - } - - dispatch_group_leave(group); + if (error && outError) { + *outError = error; + } + }); }]; - dispatch_group_wait(group, DISPATCH_TIME_FOREVER); + [self waitForCondition:&condition]; return result; }