Skip to content

Commit

Permalink
Ensure signaling settings availability
Browse files Browse the repository at this point in the history
Signed-off-by: Marcel Müller <[email protected]>
  • Loading branch information
SystemKeeper committed Sep 17, 2024
1 parent cc41d19 commit 3bf31cc
Show file tree
Hide file tree
Showing 5 changed files with 77 additions and 51 deletions.
3 changes: 3 additions & 0 deletions NextcloudTalk/NCCallController.m
Original file line number Diff line number Diff line change
Expand Up @@ -97,6 +97,9 @@ - (instancetype)initWithDelegate:(id<NCCallControllerDelegate>)delegate inRoom:(
_signalingController.observer = self;

_account = [[NCDatabaseManager sharedInstance] activeAccount];

// NCCallController is only initialized after joining the room. At that point we ensured that there's
// an external signaling controller set, in case we are using external signaling.
_externalSignalingController = [[NCSettingsController sharedInstance] externalSignalingControllerForAccountId:_account.accountId];
_externalSignalingController.delegate = self;

Expand Down
4 changes: 1 addition & 3 deletions NextcloudTalk/NCConnectionController.m
Original file line number Diff line number Diff line change
Expand Up @@ -111,14 +111,12 @@ - (void)checkAppState
}

[self setAppState:kAppStateMissingSignalingConfiguration];
[[NCSettingsController sharedInstance] getSignalingConfigurationForAccountId:activeAccount.accountId withCompletionBlock:^(NSError *error) {
[[NCSettingsController sharedInstance] updateSignalingConfigurationForAccountId:activeAccount.accountId withCompletionBlock:^(NSError *error) {
if (error) {
[self notifyAppState];
return;
}

// SetSignalingConfiguration should be called just once
[[NCSettingsController sharedInstance] setSignalingConfigurationForAccountId:activeAccount.accountId];
[self checkAppState];
}];
}];
Expand Down
63 changes: 39 additions & 24 deletions NextcloudTalk/NCRoomsManagerExtensions.swift
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,8 @@ import Foundation
// MARK: - Join/Leave room

public func joinRoom(_ token: String, forCall call: Bool) {
NCUtils.log("Joining room \(token) for call \(call)")

// Clean up joining room flag and attempts
self.joiningRoomToken = nil
self.joiningSessionId = nil
Expand Down Expand Up @@ -150,19 +152,18 @@ import Foundation

NCUtils.log("Joined room \(token) in NC successfully")

guard let extSignalingController = NCSettingsController.sharedInstance().externalSignalingController(forAccountId: activeAccount.accountId)
else {
// Joined room in NC successfully and no external signaling server configured.
completionBlock(sessionId, room, nil, 0, nil)
return
}

NCUtils.log("Trying to join room \(token) in external signaling server...")

// Remember the latest sessionId we're using to join a room, to be able to check when joining the external signaling server
self.joiningSessionId = sessionId

self.getSignalingSettingsHelper(for: activeAccount, forRoom: token) { signalingSettings in
self.getExternalSignalingHelper(for: activeAccount, forRoom: token, forCall: call) { extSignalingController, signalingSettings in
guard let extSignalingController else {
// Joined room in NC successfully and no external signaling server configured.
completionBlock(sessionId, room, nil, 0, nil)
return
}

NCUtils.log("Trying to join room \(token) in external signaling server...")

let federation = signalingSettings?.getFederationJoinDictionary()

extSignalingController.joinRoom(token, withSessionId: sessionId, withFederation: federation) { error in
Expand Down Expand Up @@ -192,18 +193,30 @@ import Foundation
})
}

private func getSignalingSettingsHelper(for account: TalkAccount, forRoom token: String, withCompletion completion: @escaping (SignalingSettings?) -> Void) {
// Currently we only need the signaling settings in case the room supports federation-v2
if let room = NCDatabaseManager.sharedInstance().room(withToken: token, forAccountId: account.accountId), room.supportsFederatedCalling {
NCAPIController.sharedInstance().getSignalingSettings(for: account, forRoom: token) { signalingSettings, _ in
completion(signalingSettings)
private func getExternalSignalingHelper(for account: TalkAccount, forRoom token: String, forCall call: Bool, withCompletion completion: @escaping (NCExternalSignalingController?, SignalingSettings?) -> Void) {
// Currently there are 2 cases where we need to fetch the signaling settings in all cases, a federated room or joining for calling
let room = NCDatabaseManager.sharedInstance().room(withToken: token, forAccountId: account.accountId)

guard call || room?.supportsFederatedCalling ?? false else {
completion(nil, nil)
return
}

NCAPIController.sharedInstance().getSignalingSettings(for: account, forRoom: token) { signalingSettings, _ in
guard let signalingSettings else {
completion(nil, nil)
return
}

NCSettingsController.sharedInstance().ensureSignalingConfiguration(forAccountId: account.accountId, with: signalingSettings) { extSignalingController in
completion(extSignalingController, signalingSettings)
}
} else {
completion(nil)
}
}

public func rejoinRoom(_ token: String, completionBlock: @escaping (_ sessionId: String?, _ room: NCRoom?, _ error: Error?, _ statusCode: Int, _ statusReason: String?) -> Void) {
NCUtils.log("Rejoining room \(token)")

guard let roomController = self.activeRooms[token] as? NCRoomController else { return }

let activeAccount = NCDatabaseManager.sharedInstance().activeAccount()
Expand All @@ -214,14 +227,14 @@ import Foundation
roomController.userSessionId = sessionId
roomController.inChat = true

guard let extSignalingController = NCSettingsController.sharedInstance().externalSignalingController(forAccountId: activeAccount.accountId)
else {
// Joined room in NC successfully and no external signaling server configured.
completionBlock(sessionId, room, nil, 0, nil)
return
}
// Re-joining is currently only happening for calls, so always fetch the signaling settings
self.getExternalSignalingHelper(for: activeAccount, forRoom: token, forCall: true) { extSignalingController, signalingSettings in
guard let extSignalingController else {
// Joined room in NC successfully and no external signaling server configured.
completionBlock(sessionId, room, nil, 0, nil)
return
}

self.getSignalingSettingsHelper(for: activeAccount, forRoom: token) { signalingSettings in
let federation = signalingSettings?.getFederationJoinDictionary()

extSignalingController.joinRoom(token, withSessionId: sessionId, withFederation: federation) { error in
Expand All @@ -247,6 +260,8 @@ import Foundation
public func leaveRoom(_ token: String) {
// Check if leaving the room we are joining
if self.isJoiningRoom(withToken: token) {
NCUtils.log("Leaving room \(token), but still joining -> cancel")

self.joiningRoomToken = nil
self.joiningSessionId = nil
self.joinRoomTask?.cancel()
Expand Down
16 changes: 10 additions & 6 deletions NextcloudTalk/NCSettingsController.h
Original file line number Diff line number Diff line change
Expand Up @@ -29,19 +29,22 @@ extern NSString * const kUserProfileScopePublished;

extern NSString * const NCSettingsControllerDidChangeActiveAccountNotification;

@class NCExternalSignalingController;
@class SignalingSettings;

typedef void (^UpdatedProfileCompletionBlock)(NSError *error);
typedef void (^LogoutCompletionBlock)(NSError *error);
typedef void (^GetCapabilitiesCompletionBlock)(NSError *error);
typedef void (^GetSignalingConfigCompletionBlock)(NSError *error);
typedef void (^UpdateSignalingConfigCompletionBlock)(NSError *error);
typedef void (^SubscribeForPushNotificationsCompletionBlock)(BOOL success);
typedef void (^SetSignalingConfigCompletionBlock)(NCExternalSignalingController * _Nullable signalingServer);
typedef void (^EnsureSignalingConfigCompletionBlock)(NCExternalSignalingController * _Nullable signalingServer);

typedef NS_ENUM(NSInteger, NCPreferredFileSorting) {
NCAlphabeticalSorting = 1,
NCModificationDateSorting
};

@class NCExternalSignalingController;

@interface NCSettingsController : NSObject

@property (nonatomic, copy) ARDSettingsModel *videoSettingsModel;
Expand All @@ -56,9 +59,10 @@ typedef NS_ENUM(NSInteger, NCPreferredFileSorting) {
- (void)getUserProfileForAccountId:(NSString *)accountId withCompletionBlock:(UpdatedProfileCompletionBlock)block;
- (void)logoutAccountWithAccountId:(NSString *)accountId withCompletionBlock:(LogoutCompletionBlock)block;
- (void)getCapabilitiesForAccountId:(NSString *)accountId withCompletionBlock:(GetCapabilitiesCompletionBlock)block;
- (void)getSignalingConfigurationForAccountId:(NSString *)accountId withCompletionBlock:(GetSignalingConfigCompletionBlock)block;
- (void)setSignalingConfigurationForAccountId:(NSString *)accountId;
- (NCExternalSignalingController *)externalSignalingControllerForAccountId:(NSString *)accountId;
- (void)updateSignalingConfigurationForAccountId:(NSString * _Nonnull)accountId withCompletionBlock:(UpdateSignalingConfigCompletionBlock _Nonnull)block;
- (void)setSignalingConfigurationForAccountId:(NSString * _Nonnull)accountId withSettings:(SignalingSettings * _Nonnull)settings withCompletionBlock:(SetSignalingConfigCompletionBlock _Nonnull)block;
- (void)ensureSignalingConfigurationForAccountId:(NSString * _Nonnull)accountId withSettings:(SignalingSettings * _Nonnull)settings withCompletionBlock:(EnsureSignalingConfigCompletionBlock _Nonnull)block;
- (NCExternalSignalingController * _Nullable)externalSignalingControllerForAccountId:(NSString * _Nonnull)accountId;
- (void)connectDisconnectedExternalSignalingControllers;
- (void)disconnectAllExternalSignalingControllers;
- (void)subscribeForPushNotificationsForAccountId:(NSString *)accountId withCompletionBlock:(SubscribeForPushNotificationsCompletionBlock)block;
Expand Down
42 changes: 24 additions & 18 deletions NextcloudTalk/NCSettingsController.m
Original file line number Diff line number Diff line change
Expand Up @@ -88,7 +88,7 @@ - (id)init
_videoSettingsModel = [[ARDSettingsModel alloc] init];
_signalingConfigurations = [NSMutableDictionary new];
_externalSignalingControllers = [NSMutableDictionary new];

[self configureDatabase];
[self checkStoredDataInKechain];

Expand Down Expand Up @@ -281,16 +281,12 @@ - (void)talkConfigurationHasChanged:(NSNotification *)notification
return;
}

[[NCSettingsController sharedInstance] getSignalingConfigurationForAccountId:accountId withCompletionBlock:^(NSError *error) {
if (error) {
return;
}

BGTaskHelper *bgTask = [BGTaskHelper startBackgroundTaskWithName:@"NCUpdateSignalingConfiguration" expirationHandler:nil];
BGTaskHelper *bgTask = [BGTaskHelper startBackgroundTaskWithName:@"NCUpdateSignalingConfiguration" expirationHandler:nil];

// SetSignalingConfiguration should be called just once
[[NCSettingsController sharedInstance] setSignalingConfigurationForAccountId:accountId];
[[NCDatabaseManager sharedInstance] updateTalkConfigurationHashForAccountId:accountId withHash:configurationHash];
[[NCSettingsController sharedInstance] updateSignalingConfigurationForAccountId:accountId withCompletionBlock:^(NSError *error) {
if (!error) {
[[NCDatabaseManager sharedInstance] updateTalkConfigurationHashForAccountId:accountId withHash:configurationHash];
}

[bgTask stopBackgroundTask];
}];
Expand Down Expand Up @@ -461,7 +457,7 @@ - (void)switchToAnyInactiveAccount

#pragma mark - Signaling Configuration

- (void)getSignalingConfigurationForAccountId:(NSString *)accountId withCompletionBlock:(GetSignalingConfigCompletionBlock)block
- (void)updateSignalingConfigurationForAccountId:(NSString *)accountId withCompletionBlock:(UpdateSignalingConfigCompletionBlock)block
{
TalkAccount *account = [[NCDatabaseManager sharedInstance] talkAccountForAccountId:accountId];

Expand All @@ -477,11 +473,11 @@ - (void)getSignalingConfigurationForAccountId:(NSString *)accountId withCompleti
[[NCAPIController sharedInstance] getSignalingSettingsFor:account forRoom:nil completionBlock:^(SignalingSettings * _Nullable settings, NSError * _Nullable error) {
if (!error) {
if (settings && account && account.accountId) {
[self->_signalingConfigurations setObject:settings forKey:account.accountId];

if (block) {
block(nil);
}
[self setSignalingConfigurationForAccountId:account.accountId withSettings:settings withCompletionBlock:^(NCExternalSignalingController * _Nullable signalingServer) {
if (block) {
block(nil);
}
}];
} else {
NSError *error = [NSError errorWithDomain:NSCocoaErrorDomain code:0 userInfo:nil];

Expand All @@ -497,9 +493,9 @@ - (void)getSignalingConfigurationForAccountId:(NSString *)accountId withCompleti
}

// SetSignalingConfiguration should be called just once
- (void)setSignalingConfigurationForAccountId:(NSString *)accountId
- (void)setSignalingConfigurationForAccountId:(NSString *)accountId withSettings:(SignalingSettings * _Nonnull)signalingSettings withCompletionBlock:(SetSignalingConfigCompletionBlock)block
{
SignalingSettings *signalingSettings = [_signalingConfigurations objectForKey:accountId];
[self->_signalingConfigurations setObject:signalingSettings forKey:accountId];

if (signalingSettings.server && signalingSettings.server.length > 0 && signalingSettings.ticket && signalingSettings.ticket.length > 0) {
BGTaskHelper *bgTask = [BGTaskHelper startBackgroundTaskWithName:@"NCSetSignalingConfiguration" expirationHandler:nil];
Expand All @@ -515,8 +511,18 @@ - (void)setSignalingConfigurationForAccountId:(NSString *)accountId
extSignalingController = [[NCExternalSignalingController alloc] initWithAccount:account server:signalingSettings.server andTicket:signalingSettings.ticket];
[self->_externalSignalingControllers setObject:extSignalingController forKey:accountId];

if (block) {
block(extSignalingController);
}

[bgTask stopBackgroundTask];
});

return;
}

if (block) {
block(nil);
}
}

Expand Down

0 comments on commit 3bf31cc

Please sign in to comment.