From 69cc53f53e76edb05b2e626f378accdebf882a0a Mon Sep 17 00:00:00 2001 From: Mpendulo Ndlovu Date: Tue, 10 Sep 2024 18:26:26 +0200 Subject: [PATCH 1/2] fix: handling rn sdk read-only calls --- README.md | 2 +- .../Classes/API/InfuraProvider.swift | 16 ++++++++++++---- .../Classes/Ethereum/Ethereum.swift | 15 ++++++++++++++- metamask-ios-sdk.podspec | 2 +- 4 files changed, 28 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index f2d3434..2bcd90a 100644 --- a/README.md +++ b/README.md @@ -54,7 +54,7 @@ Alternatively, you can add the URL directly in your project's package file: dependencies: [ .package( url: "https://github.com/MetaMask/metamask-ios-sdk", - from: "0.8.6" + from: "0.8.7" ) ] ``` diff --git a/Sources/metamask-ios-sdk/Classes/API/InfuraProvider.swift b/Sources/metamask-ios-sdk/Classes/API/InfuraProvider.swift index 4fa89bd..dcf9617 100644 --- a/Sources/metamask-ios-sdk/Classes/API/InfuraProvider.swift +++ b/Sources/metamask-ios-sdk/Classes/API/InfuraProvider.swift @@ -99,14 +99,17 @@ public class ReadOnlyRPCProvider { readonlyRPCMap[chainId] } - public func sendRequest(_ request: any RPCRequest, chainId: String, appMetadata: AppMetadata) async -> Any? { + public func sendRequest(_ request: any RPCRequest, + params: Any = "", + chainId: String, + appMetadata: AppMetadata) async -> Any? { Logging.log("ReadOnlyRPCProvider:: Sending request \(request.method) on chain \(chainId) via Infura API") let params: [String: Any] = [ "method": request.method, "jsonrpc": "2.0", "id": request.id, - "params": request.params + "params": params ] guard let endpoint = endpoint(for: chainId) else { @@ -132,10 +135,15 @@ public class ReadOnlyRPCProvider { } Logging.error("ReadOnlyRPCProvider:: could not get result from response \(json)") + + if let error = json["error"] as? [String: Any] { + return RequestError(from: error) + } + return nil } catch { - Logging.error("tracking error: \(error.localizedDescription)") - return nil + Logging.error("ReadOnlyRPCProvider:: error: \(error.localizedDescription)") + return RequestError(from: ["code": -1, "message": error.localizedDescription]) } } } diff --git a/Sources/metamask-ios-sdk/Classes/Ethereum/Ethereum.swift b/Sources/metamask-ios-sdk/Classes/Ethereum/Ethereum.swift index bef9550..921a457 100644 --- a/Sources/metamask-ios-sdk/Classes/Ethereum/Ethereum.swift +++ b/Sources/metamask-ios-sdk/Classes/Ethereum/Ethereum.swift @@ -443,8 +443,21 @@ public class Ethereum { EthereumMethod.isReadOnly(request.methodType), useReadOnlyRPCProvider() { Task { + let readOnlyRequest = EthereumRequest( + id: request.id, + method: request.method + ) + var params: Any = request.params + + if + let paramsData = request.params as? Data, + let json = try? JSONSerialization.jsonObject(with: paramsData, options: []) { + params = json + } + if let result = await readOnlyRPCProvider.sendRequest( - request, + readOnlyRequest, + params: params, chainId: chainId, appMetadata: commClient.appMetadata ?? AppMetadata(name: "", url: "")) { sendResult(result, id: request.id) diff --git a/metamask-ios-sdk.podspec b/metamask-ios-sdk.podspec index 85d2e3c..9a31e0c 100644 --- a/metamask-ios-sdk.podspec +++ b/metamask-ios-sdk.podspec @@ -1,6 +1,6 @@ Pod::Spec.new do |s| s.name = 'metamask-ios-sdk' - s.version = '0.8.6' + s.version = '0.8.7' s.summary = 'Enable users to easily connect with their MetaMask Mobile wallet.' s.swift_version = '5.5' From 46d8c18f78b5452b1e820614e37a021877080ccc Mon Sep 17 00:00:00 2001 From: Mpendulo Ndlovu Date: Tue, 10 Sep 2024 19:57:28 +0200 Subject: [PATCH 2/2] update read only provider --- .../Classes/API/InfuraProvider.swift | 17 +++++++++++------ .../Classes/Ethereum/Ethereum.swift | 6 +----- 2 files changed, 12 insertions(+), 11 deletions(-) diff --git a/Sources/metamask-ios-sdk/Classes/API/InfuraProvider.swift b/Sources/metamask-ios-sdk/Classes/API/InfuraProvider.swift index dcf9617..6097566 100644 --- a/Sources/metamask-ios-sdk/Classes/API/InfuraProvider.swift +++ b/Sources/metamask-ios-sdk/Classes/API/InfuraProvider.swift @@ -9,6 +9,7 @@ public class ReadOnlyRPCProvider { let infuraAPIKey: String private let network: any Networking + let rpcUrls: [String: String] let readonlyRPCMap: [String: String] public convenience init(infuraAPIKey: String? = nil, readonlyRPCMap: [String: String]? = nil) { @@ -18,26 +19,31 @@ public class ReadOnlyRPCProvider { init(infuraAPIKey: String? = nil, readonlyRPCMap: [String: String]?, network: any Networking) { self.infuraAPIKey = infuraAPIKey ?? "" self.network = network + self.readonlyRPCMap = readonlyRPCMap ?? [:] if let providedRPCMap = readonlyRPCMap { if let apiKey = infuraAPIKey { // Merge infuraReadonlyRPCMap with readonlyRPCMap, overriding infura's keys if they are present in readonlyRPCMap var mergedMap = ReadOnlyRPCProvider.infuraReadonlyRPCMap(apiKey) providedRPCMap.forEach { mergedMap[$0.key] = $0.value } - self.readonlyRPCMap = mergedMap + self.rpcUrls = mergedMap } else { // Use only the provided readonlyRPCMap - self.readonlyRPCMap = providedRPCMap + self.rpcUrls = providedRPCMap } } else if let apiKey = infuraAPIKey { // Use infuraReadonlyRPCMap as default - self.readonlyRPCMap = ReadOnlyRPCProvider.infuraReadonlyRPCMap(apiKey) + self.rpcUrls = ReadOnlyRPCProvider.infuraReadonlyRPCMap(apiKey) } else { // Default to an empty map if neither are provided - self.readonlyRPCMap = [:] + self.rpcUrls = [:] } } + func supportsChain(_ chainId: String) -> Bool { + return rpcUrls[chainId] != nil && (readonlyRPCMap[chainId] != nil || !infuraAPIKey.isEmpty) + } + static func infuraReadonlyRPCMap(_ infuraAPIKey: String) -> [String: String] { [ // ###### Ethereum ###### @@ -96,7 +102,7 @@ public class ReadOnlyRPCProvider { } func endpoint(for chainId: String) -> String? { - readonlyRPCMap[chainId] + rpcUrls[chainId] } public func sendRequest(_ request: any RPCRequest, @@ -135,7 +141,6 @@ public class ReadOnlyRPCProvider { } Logging.error("ReadOnlyRPCProvider:: could not get result from response \(json)") - if let error = json["error"] as? [String: Any] { return RequestError(from: error) } diff --git a/Sources/metamask-ios-sdk/Classes/Ethereum/Ethereum.swift b/Sources/metamask-ios-sdk/Classes/Ethereum/Ethereum.swift index 921a457..cfd4a27 100644 --- a/Sources/metamask-ios-sdk/Classes/Ethereum/Ethereum.swift +++ b/Sources/metamask-ios-sdk/Classes/Ethereum/Ethereum.swift @@ -431,17 +431,13 @@ public class Ethereum { submittedRequests.removeAll() clearSession() } - - func useReadOnlyRPCProvider() -> Bool { - !readOnlyRPCProvider.infuraAPIKey.isEmpty || !readOnlyRPCProvider.readonlyRPCMap.isEmpty - } // MARK: Request Sending func sendRequest(_ request: any RPCRequest) { if EthereumMethod.isReadOnly(request.methodType), - useReadOnlyRPCProvider() { + readOnlyRPCProvider.supportsChain(chainId) { Task { let readOnlyRequest = EthereumRequest( id: request.id,