Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions packages/react-native/React/Base/RCTBundleManager.h
Original file line number Diff line number Diff line change
Expand Up @@ -54,9 +54,9 @@ typedef NSMutableArray<NSURLQueryItem *> *_Nullable (^RCTPackagerOptionsUpdater)

- (nullable NSURL *)getBundleURL;

- (nullable NSString *)getPackagerServerScheme;
- (nonnull NSString *)getPackagerServerScheme;

- (nullable NSString *)getPackagerServerHost;
- (nonnull NSString *)getPackagerServerHost;

@end

Expand Down
15 changes: 14 additions & 1 deletion packages/react-native/React/Base/RCTBundleManager.m
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@

#import "RCTBundleManager.h"
#import <React/RCTBundleURLProvider.h>
#import <React/RCTDevLoadingViewSetEnabled.h>
#import "RCTAssert.h"
#import "RCTBridge+Private.h"
#import "RCTBridge.h"
Expand Down Expand Up @@ -48,6 +49,12 @@ - (instancetype)initWithBundleFilePath:(NSURL *)bundleFilePath
{
return options;
};

// When the bundleFilePath is set in the RCTBundleConfiguration the Metro connection
// shouldn't be suggested/required.
if (_bundleFilePath != nil) {
RCTDevLoadingViewSetEnabled(false);
}
}

return self;
Expand Down Expand Up @@ -160,7 +167,13 @@ - (NSURL *)bundleURL
_bridgelessBundleURLGetter != nil,
@"RCTBundleManager: In bridgeless mode, RCTBridgelessBundleURLGetter must not be nil.");

return _bridgelessBundleURLGetter();
NSURL *bundleURL = [_bundleConfig getBundleURL];

if (bundleURL == nil) {
return _bridgelessBundleURLGetter();
}

return bundleURL;
}

- (void)resetBundleURL
Expand Down
37 changes: 36 additions & 1 deletion packages/react-native/React/CoreModules/RCTDevSettings.h
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,14 @@
#import <React/RCTEventEmitter.h>
#import <React/RCTInitializing.h>

@class RCTPackagerClientResponder;
typedef uint32_t RCTHandlerToken;
typedef void (^RCTNotificationHandler)(NSDictionary<NSString *, id> *);
typedef void (^RCTRequestHandler)(NSDictionary<NSString *, id> *, RCTPackagerClientResponder *);
typedef void (^RCTConnectedHandler)(void);

@class RCTPackagerConnection;

@protocol RCTPackagerClientMethod;

/**
Expand Down Expand Up @@ -85,6 +93,10 @@
*/
@property (nonatomic, assign) BOOL isPerfMonitorShown;

#if RCT_DEV
@property (nonatomic, readonly) RCTPackagerConnection *packagerConnection;
#endif

/**
* Toggle the element inspector.
*/
Expand All @@ -102,7 +114,30 @@

#if RCT_DEV_MENU
- (void)addHandler:(id<RCTPackagerClientMethod>)handler
forPackagerMethod:(NSString *)name __deprecated_msg("Use RCTPackagerConnection directly instead");
forPackagerMethod:(NSString *)name __deprecated_msg("Use addRequestHandler or addNotificationHandler instead");
#endif

#if RCT_DEV
/**
* Registers a handler for a notification broadcast from the packager. An
* example is "reload" - an instruction to reload from the packager.
* If multiple notification handlers are registered for the same method, they
* will all be invoked sequentially.
*/
- (RCTHandlerToken)addNotificationHandler:(RCTNotificationHandler)handler
queue:(dispatch_queue_t)queue
forMethod:(NSString *)method;

/**
* Registers a handler for a request from the packager. An example is
* pokeSamplingProfiler; it asks for profile data from the client.
* Only one handler can be registered for a given method; calling this
* displaces any previous request handler registered for that method.
*/
- (RCTHandlerToken)addRequestHandler:(RCTRequestHandler)handler
queue:(dispatch_queue_t)queue
forMethod:(NSString *)method;

#endif

@end
Expand Down
54 changes: 45 additions & 9 deletions packages/react-native/React/CoreModules/RCTDevSettings.mm
Original file line number Diff line number Diff line change
Expand Up @@ -32,9 +32,12 @@

static NSString *const kRCTDevSettingsUserDefaultsKey = @"RCTDevMenu";

#if RCT_DEV
#import <React/RCTPackagerConnection.h>
#endif

#if RCT_DEV_SETTINGS_ENABLE_PACKAGER_CONNECTION
#import <React/RCTPackagerClient.h>
#import <React/RCTPackagerConnection.h>
#endif

#if RCT_ENABLE_INSPECTOR
Expand All @@ -52,7 +55,7 @@ void RCTDevSettingsSetEnabled(BOOL enabled)
devSettingsMenuEnabled = enabled;
}

#if RCT_DEV_MENU || RCT_REMOTE_PROFILE
#if RCT_DEV || RCT_REMOTE_PROFILE

@interface RCTDevSettingsUserDefaultsDataSource : NSObject <RCTDevSettingsDataSource>

Expand Down Expand Up @@ -145,6 +148,9 @@ - (instancetype)init
};
RCTDevSettingsUserDefaultsDataSource *dataSource =
[[RCTDevSettingsUserDefaultsDataSource alloc] initWithDefaultValues:defaultValues];
#if RCT_DEV
_packagerConnection = [RCTPackagerConnection new];
#endif
_isShakeGestureEnabled = true;
return [self initWithDataSource:dataSource];
}
Expand Down Expand Up @@ -178,18 +184,27 @@ - (instancetype)initWithDataSource:(id<RCTDevSettingsDataSource>)dataSource

- (void)initialize
{
#if RCT_DEV
[_packagerConnection startWithBundleManager:_bundleManager];
#endif

#if RCT_DEV_SETTINGS_ENABLE_PACKAGER_CONNECTION
if (numInitializedModules++ == 0) {
reloadToken = [[RCTPackagerConnection sharedPackagerConnection]
reloadToken = [self
addNotificationHandler:^(id params) {
RCTTriggerReloadCommandListeners(@"Global hotkey");
}
queue:dispatch_get_main_queue()
forMethod:@"reload"];
#if RCT_DEV_MENU
devMenuToken = [[RCTPackagerConnection sharedPackagerConnection]
__weak __typeof(self) weakSelf = self;
devMenuToken = [self
addNotificationHandler:^(id params) {
[[self.moduleRegistry moduleForName:"DevMenu"] show];
__typeof(self) strongSelf = weakSelf;
if (strongSelf == nullptr) {
return;
}
[[strongSelf.moduleRegistry moduleForName:"DevMenu"] show];
}
queue:dispatch_get_main_queue()
forMethod:@"devMenu"];
Expand Down Expand Up @@ -240,9 +255,9 @@ - (void)invalidate
[super invalidate];
#if RCT_DEV_SETTINGS_ENABLE_PACKAGER_CONNECTION
if (--numInitializedModules == 0) {
[[RCTPackagerConnection sharedPackagerConnection] removeHandler:reloadToken];
[_packagerConnection removeHandler:reloadToken];
#if RCT_DEV_MENU
[[RCTPackagerConnection sharedPackagerConnection] removeHandler:devMenuToken];
[_packagerConnection removeHandler:devMenuToken];
#endif
}
#endif
Expand Down Expand Up @@ -422,10 +437,27 @@ - (void)setExecutorClass:(Class)executorClass
}
}

#if RCT_DEV
- (RCTHandlerToken)addNotificationHandler:(RCTNotificationHandler)handler
queue:(dispatch_queue_t)queue
forMethod:(NSString *)method
{
return [_packagerConnection addNotificationHandler:handler queue:queue forMethod:method];
}

- (RCTHandlerToken)addRequestHandler:(RCTRequestHandler)handler
queue:(dispatch_queue_t)queue
forMethod:(NSString *)method
{
return [_packagerConnection addRequestHandler:handler queue:queue forMethod:method];
}

#endif

- (void)addHandler:(id<RCTPackagerClientMethod>)handler forPackagerMethod:(NSString *)name
{
#if RCT_DEV_SETTINGS_ENABLE_PACKAGER_CONNECTION
[[RCTPackagerConnection sharedPackagerConnection] addHandler:handler forMethod:name];
[_packagerConnection addHandler:handler forMethod:name];
#endif
}

Expand Down Expand Up @@ -512,7 +544,7 @@ - (void)jsLoaded:(NSNotification *)notification

@end

#else // #if RCT_DEV_MENU
#else // #if RCT_DEV || RCT_REMOTE_PROFILE

@interface RCTDevSettings () <NativeDevSettingsSpec>
@end
Expand Down Expand Up @@ -578,6 +610,10 @@ - (void)setIsShakeToShowDevMenuEnabled:(BOOL)enabled
return std::make_shared<facebook::react::NativeDevSettingsSpecJSI>(params);
}

- (void)addHandler:(id<RCTPackagerClientMethod>)handler forPackagerMethod:(NSString *)name
{
}

@end

#endif // #if RCT_DEV_MENU
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@

#import <Foundation/Foundation.h>

#import <React/RCTBundleManager.h>
#import <React/RCTDefines.h>

#if RCT_DEV
Expand All @@ -24,8 +25,6 @@ typedef void (^RCTConnectedHandler)(void);
/** Encapsulates singleton connection to React Native packager. */
@interface RCTPackagerConnection : NSObject

+ (instancetype)sharedPackagerConnection;

/**
* Registers a handler for a notification broadcast from the packager. An
* example is "reload" - an instruction to reload from the packager.
Expand Down Expand Up @@ -62,6 +61,9 @@ typedef void (^RCTConnectedHandler)(void);
/** Reconnect with given packager server, if packagerServerHostPort has changed. */
- (void)reconnect:(NSString *)packagerServerHostPort;

/** starts packager connection with configuration from the bundle manager */
- (void)startWithBundleManager:(RCTBundleManager *)bundleManager;

/**
* Historically no distinction was made between notification and request
* handlers. If you use this method, it will be registered as *both* a
Expand Down
63 changes: 30 additions & 33 deletions packages/react-native/React/DevSupport/RCTPackagerConnection.mm
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@

#import <React/RCTAssert.h>
#import <React/RCTBridge.h>
#import <React/RCTBundleManager.h>
#import <React/RCTBundleURLProvider.h>
#import <React/RCTConstants.h>
#import <React/RCTConvert.h>
Expand Down Expand Up @@ -50,43 +51,13 @@ @implementation RCTPackagerConnection {
std::vector<Registration<RCTNotificationHandler>> _notificationRegistrations;
std::vector<Registration<RCTRequestHandler>> _requestRegistrations;
std::vector<Registration<RCTConnectedHandler>> _connectedRegistrations;
}

+ (instancetype)sharedPackagerConnection
{
static RCTPackagerConnection *connection;
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
connection = [RCTPackagerConnection new];
});
return connection;
RCTBundleManager *_bundleManager;
}

- (instancetype)init
{
if (self = [super init]) {
_nextToken = 1; // Prevent randomly erasing a handler if you pass a bogus 0 token
_serverHostPortForSocket = [[RCTBundleURLProvider sharedSettings] packagerServerHostPort];
_serverSchemeForSocket = [[RCTBundleURLProvider sharedSettings] packagerScheme];
_socket = socketForLocation(_serverHostPortForSocket, _serverSchemeForSocket);
_socket.delegate = self;
[_socket start];

RCTPackagerConnection *const __weak weakSelf = self;
_bundleURLChangeObserver =
[[NSNotificationCenter defaultCenter] addObserverForName:RCTBundleURLProviderUpdatedNotification
object:nil
queue:[NSOperationQueue mainQueue]
usingBlock:^(NSNotification *_Nonnull __unused note) {
[weakSelf bundleURLSettingsChanged];
}];
_reloadWithPotentiallyNewURLObserver =
[[NSNotificationCenter defaultCenter] addObserverForName:RCTTriggerReloadCommandNotification
object:nil
queue:[NSOperationQueue mainQueue]
usingBlock:^(NSNotification *_Nonnull __unused note) {
[weakSelf bundleURLSettingsChanged];
}];
}
return self;
}
Expand Down Expand Up @@ -119,6 +90,32 @@ - (instancetype)init
return [[RCTReconnectingWebSocket alloc] initWithURL:components.URL queue:queue];
}

- (void)startWithBundleManager:(RCTBundleManager *)bundleManager
{
_serverHostPortForSocket = [bundleManager.bundleConfig getPackagerServerHost];
_serverSchemeForSocket = [bundleManager.bundleConfig getPackagerServerScheme];
_socket = socketForLocation(_serverHostPortForSocket, _serverSchemeForSocket);
_socket.delegate = self;
[_socket start];
_bundleManager = bundleManager;

RCTPackagerConnection *const __weak weakSelf = self;
_bundleURLChangeObserver =
[[NSNotificationCenter defaultCenter] addObserverForName:RCTBundleURLProviderUpdatedNotification
object:nil
queue:[NSOperationQueue mainQueue]
usingBlock:^(NSNotification *_Nonnull __unused note) {
[weakSelf bundleURLSettingsChanged];
}];
_reloadWithPotentiallyNewURLObserver =
[[NSNotificationCenter defaultCenter] addObserverForName:RCTTriggerReloadCommandNotification
object:nil
queue:[NSOperationQueue mainQueue]
usingBlock:^(NSNotification *_Nonnull __unused note) {
[weakSelf bundleURLSettingsChanged];
}];
}

- (void)stop
{
std::lock_guard<std::mutex> l(_mutex);
Expand All @@ -144,7 +141,7 @@ - (void)reconnect:(NSString *)packagerServerHostPort
return; // already stopped
}

NSString *const serverScheme = [[RCTBundleURLProvider sharedSettings] packagerScheme];
NSString *const serverScheme = [_bundleManager.bundleConfig getPackagerServerScheme];
if ([packagerServerHostPort isEqual:_serverHostPortForSocket] && [serverScheme isEqual:_serverSchemeForSocket]) {
return; // unchanged
}
Expand All @@ -161,7 +158,7 @@ - (void)reconnect:(NSString *)packagerServerHostPort
- (void)bundleURLSettingsChanged
{
// Will only reconnect if `packagerServerHostPort` has actually changed
[self reconnect:[[RCTBundleURLProvider sharedSettings] packagerServerHostPort]];
[self reconnect:[_bundleManager.bundleConfig getPackagerServerHost]];
}

- (RCTHandlerToken)addNotificationHandler:(RCTNotificationHandler)handler
Expand Down
Loading