Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: ios crashes #168

Open
wants to merge 3 commits into
base: master
Choose a base branch
from
Open
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
128 changes: 120 additions & 8 deletions ios/Classes/SwiftAgoraRtmPlugin.swift
Original file line number Diff line number Diff line change
Expand Up @@ -12,23 +12,23 @@ import AgoraRtmKit
public class SwiftAgoraRtmPlugin: NSObject, FlutterPlugin {
var registrar: FlutterPluginRegistrar!
var methodChannel: FlutterMethodChannel!

var nextClientIndex: Int = 0
var clients: [Int: RTMClient] = [:]

public static func register(with registrar: FlutterPluginRegistrar) {
let channel = FlutterMethodChannel(name: "io.agora.rtm", binaryMessenger: registrar.messenger())
let instance = SwiftAgoraRtmPlugin()
instance.methodChannel = channel
instance.registrar = registrar
registrar.addMethodCallDelegate(instance, channel: channel)
}

public func detachFromEngine(for registrar: FlutterPluginRegistrar) {
methodChannel.setMethodCallHandler(nil)
clients.removeAll()
}

public func handle(_ call: FlutterMethodCall, result: @escaping FlutterResult) {
let methodName = call.method
guard let callArguments = call.arguments as? [String: Any] else {
Expand All @@ -49,35 +49,59 @@ public class SwiftAgoraRtmPlugin: NSObject, FlutterPlugin {
result(FlutterMethodNotImplemented)
}
}

func handleCallManagerMethod(_ methodName: String?, _ params: [String: Any?]?, _ result: @escaping FlutterResult) {
if let clientIndex = params?["clientIndex"] as? Int, let agoraClient = clients[clientIndex], let callManager = agoraClient.call?.manager {
let args = params?["args"] as? [String: Any?]
if (agoraClient.call == nil) {
result(["errorCode": -1])
return
}
switch methodName {
case "createLocalInvitation":
let calleeId = args?["calleeId"] as? String
if (calleeId == nil) {
result(["errorCode": -1])
return
}
let localInvitation = AgoraRtmLocalInvitation(calleeId: calleeId!)
agoraClient.call!.localInvitations[localInvitation.hash] = localInvitation
result(["errorCode": 0, "result": localInvitation.toJson()])
case "sendLocalInvitation":
let localInvitation = (args?["localInvitation"] as? [String: Any?])?.toLocalInvitation(agoraClient.call!)
if (localInvitation == nil) {
result(["errorCode": -1])
return
}
callManager.send(localInvitation!) {
result(["errorCode": $0.rawValue])
}
case "acceptRemoteInvitation":
let remoteInvitation = (args?["remoteInvitation"] as? [String: Any?])?.toRemoteInvitation(agoraClient.call!)
if (remoteInvitation == nil) {
result(["errorCode": -1])
return
}
callManager.accept(remoteInvitation!) {
agoraClient.call!.remoteInvitations.removeValue(forKey: remoteInvitation!.hash)
result(["errorCode": $0.rawValue])
}
case "refuseRemoteInvitation":
let remoteInvitation = (args?["remoteInvitation"] as? [String: Any?])?.toRemoteInvitation(agoraClient.call!)
if (remoteInvitation == nil) {
result(["errorCode": -1])
return
}
callManager.refuse(remoteInvitation!) {
agoraClient.call!.remoteInvitations.removeValue(forKey: remoteInvitation!.hash)
result(["errorCode": $0.rawValue])
}
case "cancelLocalInvitation":
let localInvitation = (args?["localInvitation"] as? [String: Any?])?.toLocalInvitation(agoraClient.call!)
if (localInvitation == nil) {
result(["errorCode": -1])
return
}
callManager.cancel(localInvitation!) {
agoraClient.call!.localInvitations.removeValue(forKey: localInvitation!.hash)
result(["errorCode": $0.rawValue])
Expand All @@ -87,7 +111,7 @@ public class SwiftAgoraRtmPlugin: NSObject, FlutterPlugin {
}
}
}

func handleStaticMethod(_ methodName: String?, _ params: [String: Any?]?, _ result: @escaping FlutterResult) {
switch methodName {
case "createInstance":
Expand All @@ -112,7 +136,7 @@ public class SwiftAgoraRtmPlugin: NSObject, FlutterPlugin {
result(FlutterMethodNotImplemented)
}
}

func handleClientMethod(_ methodName: String?, _ params: [String: Any?]?, _ result: @escaping FlutterResult) {
if let clientIndex = params?["clientIndex"] as? Int, let agoraClient = clients[clientIndex], let client = agoraClient.client {
let args = params?["args"] as? [String: Any?]
Expand All @@ -123,6 +147,10 @@ public class SwiftAgoraRtmPlugin: NSObject, FlutterPlugin {
case "login":
let token = args?["token"] as? String
let userId = args?["userId"] as? String
if userId == nil {
result(["errorCode": -1])
return
}
client.login(byToken: token, user: userId!) {
result(["errorCode": $0.rawValue])
}
Expand All @@ -134,39 +162,67 @@ public class SwiftAgoraRtmPlugin: NSObject, FlutterPlugin {
let peerId = args?["peerId"] as? String
let message = args?["message"] as? [String: Any?] ?? [:]
let options = args?["options"] as? [String: Any?] ?? [:]
if peerId == nil {
result(["errorCode": -1])
return
}
client.send(message.toRtmMessage(), toPeer: peerId!, sendMessageOptions: options.toSendMessageOptions()) {
result(["errorCode": $0.rawValue])
}
case "createChannel":
let channelId = args?["channelId"] as? String
if channelId == nil {
result(["errorCode": -1])
return
}
let agoraRtmChannel = RTMChannel(clientIndex, channelId!, registrar.messenger())
let channel = client.createChannel(withId: channelId!, delegate: agoraRtmChannel)
agoraClient.channels[channelId!] = channel
result(["errorCode": 0])
case "queryPeersOnlineStatus":
let peerIds = args?["peerIds"] as? [String]
if peerIds == nil {
result(["errorCode": -1])
return
}
client.queryPeersOnlineStatus(peerIds!) {
result(["errorCode": $1.rawValue, "result": $0?.reduce(into: [String: Int]()) {
$0[$1.peerId] = $1.state.rawValue
}])
}
case "subscribePeersOnlineStatus":
let peerIds = args?["peerIds"] as? [String]
if peerIds == nil {
result(["errorCode": -1])
return
}
client.subscribePeersOnlineStatus(peerIds!) {
result(["errorCode": $0.rawValue])
}
case "unsubscribePeersOnlineStatus":
let peerIds = args?["peerIds"] as? [String]
if peerIds == nil {
result(["errorCode": -1])
return
}
client.unsubscribePeersOnlineStatus(peerIds!) {
result(["errorCode": $0.rawValue])
}
case "queryPeersBySubscriptionOption":
let option = args?["option"] as? Int
if option == nil {
result(["errorCode": -1])
return
}
client.queryPeers(bySubscriptionOption: AgoraRtmPeerSubscriptionOptions(rawValue: option!)!) {
result(["errorCode": $1.rawValue, "result": $0])
}
case "renewToken":
let token = args?["token"] as? String
if token == nil {
result(["errorCode": -1])
return
}
client.renewToken(token!) {
result(["errorCode": $1.rawValue, "result": $0])
}
Expand All @@ -182,6 +238,10 @@ public class SwiftAgoraRtmPlugin: NSObject, FlutterPlugin {
}
case "deleteLocalUserAttributesByKeys":
let keys = args?["keys"] as? [String]
if keys == nil {
result(["errorCode": -1])
return
}
client.deleteLocalUserAttributes(byKeys: keys!) {
result(["errorCode": $0.rawValue])
}
Expand All @@ -191,80 +251,132 @@ public class SwiftAgoraRtmPlugin: NSObject, FlutterPlugin {
}
case "getUserAttributes":
let userId = args?["userId"] as? String
if userId == nil {
result(["errorCode": -1])
return
}
client.getUserAllAttributes(userId!) {
result(["errorCode": $2.rawValue, "result": $0?.toJson(), "userId": $1])
}
case "getUserAttributesByKeys":
let userId = args?["userId"] as? String
let keys = args?["keys"] as? [String]
if userId == nil || keys == nil {
result(["errorCode": -1])
return
}
client.getUserAttributes(userId!, byKeys: keys!) {
result(["errorCode": $2.rawValue, "result": $0?.toJson(), "userId": $1])
}
case "setChannelAttributes":
let channelId = args?["channelId"] as? String
let attributes = args?["attributes"] as? [[String: Any?]] ?? []
let options = args?["options"] as? [String: Any?] ?? [:]
if channelId == nil {
result(["errorCode": -1])
return
}
client.setChannel(channelId!, attributes: attributes.toRtmChannelAttributeList(), options: options.toChannelAttributeOptions()) {
result(["errorCode": $0.rawValue])
}
case "addOrUpdateChannelAttributes":
let channelId = args?["channelId"] as? String
let attributes = args?["attributes"] as? [[String: Any?]] ?? []
let options = args?["options"] as? [String: Any?] ?? [:]
if channelId == nil {
result(["errorCode": -1])
return
}
client.addOrUpdateChannel(channelId!, attributes: attributes.toRtmChannelAttributeList(), options: options.toChannelAttributeOptions()) {
result(["errorCode": $0.rawValue])
}
case "deleteChannelAttributesByKeys":
let channelId = args?["channelId"] as? String
let keys = args?["keys"] as? [String]
let options = args?["options"] as? [String: Any?] ?? [:]
if channelId == nil || keys == nil {
result(["errorCode": -1])
return
}
client.deleteChannel(channelId!, attributesByKeys: keys!, options: options.toChannelAttributeOptions()) {
result(["errorCode": $0.rawValue])
}
case "clearChannelAttributes":
let channelId = args?["channelId"] as? String
let options = args?["options"] as? [String: Any?] ?? [:]
if channelId == nil {
result(["errorCode": -1])
return
}
client.clearChannel(channelId!, options: options.toChannelAttributeOptions()) {
result(["errorCode": $0.rawValue])
}
case "getChannelAttributes":
let channelId = args?["channelId"] as? String
if channelId == nil {
result(["errorCode": -1])
return
}
client.getChannelAllAttributes(channelId!) {
result(["errorCode": $1.rawValue, "result": $0?.toJson()])
}
case "getChannelAttributesByKeys":
let channelId = args?["channelId"] as? String
let keys = args?["keys"] as? [String]
if channelId == nil || keys == nil {
result(["errorCode": -1])
return
}
client.getChannelAttributes(channelId!, byKeys: keys!) {
result(["errorCode": $1.rawValue, "result": $0?.toJson()])
}
case "getChannelMemberCount":
let channelIds = args?["channelIds"] as? [String]
if channelIds == nil {
result(["errorCode": -1])
return
}
client.getChannelMemberCount(channelIds!) {
result(["errorCode": $1.rawValue, "result": $0?.toJson()])
}
case "setParameters":
let parameters = args?["parameters"] as? String
if parameters == nil {
result(["errorCode": -1])
return
}
let errorCode = client.setParameters(parameters!)
result(["errorCode": errorCode])
case "setLogFile":
let filePath = args?["filePath"] as? String
if filePath == nil {
result(["errorCode": -1])
return
}
let errorCode = client.setLogFile(filePath!)
result(["errorCode": errorCode])
case "setLogFilter":
let filter = args?["filter"] as? Int
if filter == nil {
result(["errorCode": -1])
return
}
let errorCode = client.setLogFilters(AgoraRtmLogFilter(rawValue: filter!)!)
result(["errorCode": errorCode])
case "setLogFileSize":
let fileSizeInKBytes = args?["fileSizeInKBytes"] as? Int32
if fileSizeInKBytes == nil {
result(["errorCode": -1])
return
}
let errorCode = client.setLogFileSize(fileSizeInKBytes!)
result(["errorCode": errorCode])
default:
result(FlutterMethodNotImplemented)
}
}
}

func handleChannelMethod(_ methodName: String?, _ params: [String: Any?]?, _ result: @escaping FlutterResult) {
if let clientIndex = params?["clientIndex"] as? Int, let channelId = params?["channelId"] as? String, let agoraClient = clients[clientIndex], let channel = agoraClient.channels[channelId] {
let args = params?["args"] as? [String: Any?]
Expand Down