@@ -234,12 +234,13 @@ @interface RCTBridge ()
234
234
235
235
- (void )_invokeAndProcessModule : (NSString *)module
236
236
method : (NSString *)method
237
- arguments : (NSArray *)args ;
237
+ arguments : (NSArray *)args
238
+ context : (NSNumber *)context ;
238
239
239
240
- (void )_actuallyInvokeAndProcessModule : (NSString *)module
240
241
method : (NSString *)method
241
- arguments : (NSArray *)args ;
242
-
242
+ arguments : (NSArray *)args
243
+ context : ( NSNumber *) context ;
243
244
@end
244
245
245
246
/* *
@@ -338,7 +339,7 @@ - (instancetype)initWithReactMethodName:(NSString *)reactMethodName
338
339
NSMutableArray *argumentBlocks = [[NSMutableArray alloc ] initWithCapacity: numberOfArguments - 2 ];
339
340
340
341
#define RCT_ARG_BLOCK (_logic ) \
341
- [argumentBlocks addObject: ^(RCTBridge *bridge, NSInvocation *invocation, NSUInteger index, id json) { \
342
+ [argumentBlocks addObject: ^(RCTBridge *bridge, NSNumber *context, NSInvocation *invocation, NSUInteger index, id json) { \
342
343
_logic \
343
344
[invocation setArgument: &value atIndex: index]; \
344
345
}]; \
@@ -355,7 +356,8 @@ - (instancetype)initWithReactMethodName:(NSString *)reactMethodName
355
356
__autoreleasing id value = (json ? ^(NSArray *args) {
356
357
[bridge _invokeAndProcessModule: @" BatchedBridge"
357
358
method: @" invokeCallbackAndReturnFlushedQueue"
358
- arguments: @[json, args]];
359
+ arguments: @[json, args]
360
+ context: context];
359
361
} : ^(NSArray *unused) {});
360
362
)
361
363
};
@@ -477,6 +479,7 @@ - (instancetype)initWithReactMethodName:(NSString *)reactMethodName
477
479
- (void )invokeWithBridge : (RCTBridge *)bridge
478
480
module : (id )module
479
481
arguments : (NSArray *)arguments
482
+ context : (NSNumber *)context
480
483
{
481
484
482
485
#if DEBUG
@@ -503,8 +506,8 @@ - (void)invokeWithBridge:(RCTBridge *)bridge
503
506
NSUInteger index = 0 ;
504
507
for (id json in arguments) {
505
508
id arg = (json == [NSNull null ]) ? nil : json;
506
- void (^block)(RCTBridge *, NSInvocation *, NSUInteger , id ) = _argumentBlocks[index];
507
- block (bridge, invocation, index + 2 , arg);
509
+ void (^block)(RCTBridge *, NSNumber *, NSInvocation *, NSUInteger , id ) = _argumentBlocks[index];
510
+ block (bridge, context, invocation, index + 2 , arg);
508
511
index++;
509
512
}
510
513
@@ -653,7 +656,6 @@ - (NSString *)description
653
656
return moduleConfig;
654
657
}
655
658
656
-
657
659
/* *
658
660
* As above, but for local modules/methods, which represent JS classes
659
661
* and methods that will be called by the native code via the bridge.
@@ -801,7 +803,7 @@ @implementation RCTBridge
801
803
RCTDisplayLink *_displayLink;
802
804
NSMutableSet *_frameUpdateObservers;
803
805
NSMutableArray *_scheduledCalls;
804
- NSMutableArray *_scheduledCallbacks;
806
+ RCTSparseArray *_scheduledCallbacks;
805
807
BOOL _loading;
806
808
807
809
NSUInteger _startingTime;
@@ -829,13 +831,13 @@ - (instancetype)initWithBundleURL:(NSURL *)bundleURL
829
831
- (void )setUp
830
832
{
831
833
Class executorClass = _executorClass ?: _globalExecutorClass ?: [RCTContextExecutor class ];
832
- _javaScriptExecutor = [[ executorClass alloc ] init ] ;
834
+ _javaScriptExecutor = RCTCreateExecutor ( executorClass) ;
833
835
_latestJSExecutor = _javaScriptExecutor;
834
836
_eventDispatcher = [[RCTEventDispatcher alloc ] initWithBridge: self ];
835
837
_displayLink = [[RCTDisplayLink alloc ] initWithBridge: self ];
836
838
_frameUpdateObservers = [[NSMutableSet alloc ] init ];
837
839
_scheduledCalls = [[NSMutableArray alloc ] init ];
838
- _scheduledCallbacks = [[NSMutableArray alloc ] init ];
840
+ _scheduledCallbacks = [[RCTSparseArray alloc ] init ];
839
841
840
842
// Register passed-in module instances
841
843
NSMutableDictionary *preregisteredModules = [[NSMutableDictionary alloc ] init ];
@@ -991,7 +993,6 @@ - (void)bindKeys
991
993
992
994
}
993
995
994
-
995
996
- (NSDictionary *)modules
996
997
{
997
998
RCTAssert (_modulesByName != nil , @" Bridge modules have not yet been initialized. "
@@ -1072,7 +1073,8 @@ - (void)enqueueJSCall:(NSString *)moduleDotMethod args:(NSArray *)args
1072
1073
if (!_loading) {
1073
1074
[self _invokeAndProcessModule: @" BatchedBridge"
1074
1075
method: @" callFunctionReturnFlushedQueue"
1075
- arguments: @[moduleID, methodID, args ?: @[]]];
1076
+ arguments: @[moduleID, methodID, args ?: @[]]
1077
+ context: RCTGetExecutorID (_javaScriptExecutor)];
1076
1078
}
1077
1079
}
1078
1080
@@ -1093,13 +1095,15 @@ - (void)_immediatelyCallTimer:(NSNumber *)timer
1093
1095
#if BATCHED_BRIDGE
1094
1096
[self _actuallyInvokeAndProcessModule: @" BatchedBridge"
1095
1097
method: @" callFunctionReturnFlushedQueue"
1096
- arguments: @[moduleID, methodID, @[@[timer]]]];
1098
+ arguments: @[moduleID, methodID, @[@[timer]]]
1099
+ context: RCTGetExecutorID (_javaScriptExecutor)];
1097
1100
1098
1101
#else
1099
1102
1100
1103
[self _invokeAndProcessModule: @" BatchedBridge"
1101
1104
method: @" callFunctionReturnFlushedQueue"
1102
- arguments: @[moduleID, methodID, @[@[timer]]]];
1105
+ arguments: @[moduleID, methodID, @[@[timer]]]
1106
+ context: RCTGetExecutorID (_javaScriptExecutor)];
1103
1107
#endif
1104
1108
}
1105
1109
}
@@ -1108,6 +1112,7 @@ - (void)enqueueApplicationScript:(NSString *)script url:(NSURL *)url onComplete:
1108
1112
{
1109
1113
RCTAssert (onComplete != nil , @" onComplete block passed in should be non-nil" );
1110
1114
RCT_PROFILE_START ();
1115
+ NSNumber *context = RCTGetExecutorID (_javaScriptExecutor);
1111
1116
[_javaScriptExecutor executeApplicationScript: script sourceURL: url onComplete: ^(NSError *scriptLoadError) {
1112
1117
RCT_PROFILE_END (js_call, scriptLoadError, @" initial_script" );
1113
1118
if (scriptLoadError) {
@@ -1119,10 +1124,11 @@ - (void)enqueueApplicationScript:(NSString *)script url:(NSURL *)url onComplete:
1119
1124
[_javaScriptExecutor executeJSCall: @" BatchedBridge"
1120
1125
method: @" flushedQueue"
1121
1126
arguments: @[]
1127
+ context: context
1122
1128
callback: ^(id json, NSError *error) {
1123
1129
RCT_PROFILE_END (js_call, error, @" initial_call" , @" BatchedBridge.flushedQueue" );
1124
1130
RCT_PROFILE_START ();
1125
- [self _handleBuffer: json];
1131
+ [self _handleBuffer: json context: context ];
1126
1132
RCT_PROFILE_END (objc_call, json, @" batched_js_calls" );
1127
1133
onComplete (error);
1128
1134
}];
@@ -1131,7 +1137,7 @@ - (void)enqueueApplicationScript:(NSString *)script url:(NSURL *)url onComplete:
1131
1137
1132
1138
#pragma mark - Payload Generation
1133
1139
1134
- - (void )_invokeAndProcessModule : (NSString *)module method : (NSString *)method arguments : (NSArray *)args
1140
+ - (void )_invokeAndProcessModule : (NSString *)module method : (NSString *)method arguments : (NSArray *)args context : ( NSNumber *) context
1135
1141
{
1136
1142
#if BATCHED_BRIDGE
1137
1143
RCT_PROFILE_START ();
@@ -1148,18 +1154,19 @@ - (void)_invokeAndProcessModule:(NSString *)module method:(NSString *)method arg
1148
1154
@" module" : module,
1149
1155
@" method" : method,
1150
1156
@" args" : args,
1157
+ @" context" : context ?: @0 ,
1151
1158
};
1152
1159
1153
1160
if ([method isEqualToString: @" invokeCallbackAndReturnFlushedQueue" ]) {
1154
- [ _scheduledCallbacks addObject: call] ;
1161
+ _scheduledCallbacks[args[ 0 ]] = call;
1155
1162
} else {
1156
1163
[_scheduledCalls addObject: call];
1157
1164
}
1158
1165
1159
1166
RCT_PROFILE_END (js_call, args, @" schedule" , module, method);
1160
1167
}
1161
1168
1162
- - (void )_actuallyInvokeAndProcessModule:(NSString *)module method:(NSString *)method arguments:(NSArray *)args
1169
+ - (void )_actuallyInvokeAndProcessModule:(NSString *)module method:(NSString *)method arguments:(NSArray *)args context:( NSNumber *)context
1163
1170
{
1164
1171
#endif
1165
1172
[[NSNotificationCenter defaultCenter ] postNotificationName: RCTEnqueueNotification object: nil userInfo: nil ];
@@ -1171,19 +1178,20 @@ - (void)_actuallyInvokeAndProcessModule:(NSString *)module method:(NSString *)me
1171
1178
RCT_PROFILE_END (js_call, args, moduleDotMethod);
1172
1179
1173
1180
RCT_PROFILE_START ();
1174
- [self _handleBuffer: json];
1181
+ [self _handleBuffer: json context: context ];
1175
1182
RCT_PROFILE_END (objc_call, json, @" batched_js_calls" );
1176
1183
};
1177
1184
1178
1185
[_javaScriptExecutor executeJSCall: module
1179
1186
method: method
1180
1187
arguments: args
1188
+ context: context
1181
1189
callback: processResponse];
1182
1190
}
1183
1191
1184
1192
#pragma mark - Payload Processing
1185
1193
1186
- - (void )_handleBuffer:(id )buffer
1194
+ - (void )_handleBuffer:(id )buffer context:( NSNumber *)context
1187
1195
{
1188
1196
if (buffer == nil || buffer == (id )kCFNull ) {
1189
1197
return ;
@@ -1228,7 +1236,8 @@ - (void)_handleBuffer:(id)buffer
1228
1236
[self _handleRequestNumber: i
1229
1237
moduleID: [moduleIDs[i] integerValue ]
1230
1238
methodID: [methodIDs[i] integerValue ]
1231
- params: paramsArrays[i]];
1239
+ params: paramsArrays[i]
1240
+ context: context];
1232
1241
}
1233
1242
}
1234
1243
@@ -1247,6 +1256,7 @@ - (BOOL)_handleRequestNumber:(NSUInteger)i
1247
1256
moduleID:(NSUInteger )moduleID
1248
1257
methodID:(NSUInteger )methodID
1249
1258
params:(NSArray *)params
1259
+ context:(NSNumber *)context
1250
1260
{
1251
1261
if (![params isKindOfClass: [NSArray class ]]) {
1252
1262
RCTLogError (@" Invalid module/method/params tuple for request #%zd " , i);
@@ -1280,7 +1290,7 @@ - (BOOL)_handleRequestNumber:(NSUInteger)i
1280
1290
}
1281
1291
1282
1292
@try {
1283
- [method invokeWithBridge: strongSelf module: module arguments: params];
1293
+ [method invokeWithBridge: strongSelf module: module arguments: params context: context ];
1284
1294
}
1285
1295
@catch (NSException *exception) {
1286
1296
RCTLogError (@" Exception thrown while invoking %@ on target %@ with params %@ : %@ " , method.JSMethodName , module, params, exception);
@@ -1313,13 +1323,18 @@ - (void)_runScheduledCalls
1313
1323
{
1314
1324
#if BATCHED_BRIDGE
1315
1325
1316
- NSArray *calls = [_scheduledCallbacks arrayByAddingObjectsFromArray: _scheduledCalls];
1326
+ NSArray *calls = [_scheduledCallbacks.allObjects arrayByAddingObjectsFromArray: _scheduledCalls];
1327
+ NSNumber *currentExecutorID = RCTGetExecutorID (_javaScriptExecutor);
1328
+ calls = [calls filteredArrayUsingPredicate: [NSPredicate predicateWithBlock: ^BOOL (NSDictionary *call, NSDictionary *bindings) {
1329
+ return [call[@" context" ] isEqualToNumber: currentExecutorID];
1330
+ }]];
1317
1331
if (calls.count > 0 ) {
1318
1332
_scheduledCalls = [[NSMutableArray alloc ] init ];
1319
- _scheduledCallbacks = [[NSMutableArray alloc ] init ];
1333
+ _scheduledCallbacks = [[RCTSparseArray alloc ] init ];
1320
1334
[self _actuallyInvokeAndProcessModule: @" BatchedBridge"
1321
- method: @" processBatch"
1322
- arguments: @[calls]];
1335
+ method: @" processBatch"
1336
+ arguments: @[calls]
1337
+ context: RCTGetExecutorID (_javaScriptExecutor)];
1323
1338
}
1324
1339
1325
1340
#endif
@@ -1357,6 +1372,7 @@ + (void)logMessage:(NSString *)message level:(NSString *)level
1357
1372
[_latestJSExecutor executeJSCall: @" RCTLog"
1358
1373
method: @" logIfNoNativeHook"
1359
1374
arguments: @[level, message]
1375
+ context: RCTGetExecutorID (_latestJSExecutor)
1360
1376
callback: ^(id json, NSError *error) {}];
1361
1377
}
1362
1378
0 commit comments