diff --git a/AlphaWallet.xcodeproj/project.pbxproj b/AlphaWallet.xcodeproj/project.pbxproj index 5c5fa3e1f..7fc41a384 100644 --- a/AlphaWallet.xcodeproj/project.pbxproj +++ b/AlphaWallet.xcodeproj/project.pbxproj @@ -540,7 +540,7 @@ 76F1D7F08263A663C3A67926 /* GetIsERC721ContractCoordinator.swift in Sources */ = {isa = PBXBuildFile; fileRef = 76F1D4F77311FBF3A442E4B5 /* GetIsERC721ContractCoordinator.swift */; }; 76F1D850F4F2E968CF8D9C86 /* MonkeyTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = B138ABCF208C2C93000FC28A /* MonkeyTest.swift */; }; 76F1D91659771C9EEA7B48DC /* CreateRedeem.swift in Sources */ = {isa = PBXBuildFile; fileRef = 76F1DF80932454E9F58B7830 /* CreateRedeem.swift */; }; - 76F1D9BBB4ACAA00C8391172 /* GetENSNameEncode.swift in Sources */ = {isa = PBXBuildFile; fileRef = 76F1DC4B9964504DA12D8D3C /* GetENSNameEncode.swift */; }; + 76F1D9BBB4ACAA00C8391172 /* GetENSInfoEncode.swift in Sources */ = {isa = PBXBuildFile; fileRef = 76F1DC4B9964504DA12D8D3C /* GetENSInfoEncode.swift */; }; 76F1DA1D816C1D6759FAAB5D /* ClaimNativeCurrencyOrder.swift in Sources */ = {isa = PBXBuildFile; fileRef = 76F1D00BB549E72210412062 /* ClaimNativeCurrencyOrder.swift */; }; 76F1DB9E1443DCFC36228B08 /* ClaimOrderCoordinator.swift in Sources */ = {isa = PBXBuildFile; fileRef = 76F1D419EE36261E50ABAFAE /* ClaimOrderCoordinator.swift */; }; 76F1DBCA8BAAA42BAEB14719 /* GetERC721BalanceCoordinator.swift in Sources */ = {isa = PBXBuildFile; fileRef = 76F1D473FF303828D93C95EB /* GetERC721BalanceCoordinator.swift */; }; @@ -1161,7 +1161,7 @@ 76F1DADFD07E2941897FD2E1 /* OrderHandler.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = OrderHandler.swift; sourceTree = ""; }; 76F1DAFCBB43B6639472A229 /* BrowserHistoryViewController.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = BrowserHistoryViewController.swift; sourceTree = ""; }; 76F1DB8034ACC2FC91F818F9 /* MyDappsViewController.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MyDappsViewController.swift; sourceTree = ""; }; - 76F1DC4B9964504DA12D8D3C /* GetENSNameEncode.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = GetENSNameEncode.swift; sourceTree = ""; }; + 76F1DC4B9964504DA12D8D3C /* GetENSInfoEncode.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = GetENSInfoEncode.swift; sourceTree = ""; }; 76F1DCD54618349AC91C6DF8 /* UniversalLinkHandler.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = UniversalLinkHandler.swift; sourceTree = ""; }; 76F1DD09B44FD653C1500DA8 /* DappsHomeViewController.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = DappsHomeViewController.swift; sourceTree = ""; }; 76F1DE7BEE799DDFB68D0F54 /* GetENSOwnerCoordinator.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = GetENSOwnerCoordinator.swift; sourceTree = ""; }; @@ -2817,7 +2817,7 @@ 5E7C7CA7D65743AEE3411F3A /* GetIsERC721Encode.swift */, 5E7C7DCB0BDDD30D10130AE7 /* GetIsERC875Encode.swift */, 5E7C72CD0C22247A6AF7C95E /* GetERC721BalanceEncode.swift */, - 76F1DC4B9964504DA12D8D3C /* GetENSNameEncode.swift */, + 76F1DC4B9964504DA12D8D3C /* GetENSInfoEncode.swift */, 5E7C787CA216AFED8023A35F /* CallForAssetAttribute.swift */, ); path = "web3swift-pod"; @@ -4038,7 +4038,7 @@ 5E7C7E7AEF01B9D170228342 /* TimeEntryField.swift in Sources */, 5E7C7719948721FE9120B5B2 /* PeekOpenSeaNonFungibleTokenViewController.swift in Sources */, 76F1D5ECC391A932C96CAC13 /* GetENSOwnerCoordinator.swift in Sources */, - 76F1D9BBB4ACAA00C8391172 /* GetENSNameEncode.swift in Sources */, + 76F1D9BBB4ACAA00C8391172 /* GetENSInfoEncode.swift in Sources */, 5E7C73CA81FB2CE9BCAFC992 /* CallForAssetAttribute.swift in Sources */, 5E7C77552A957D1B144D9209 /* CallForAssetAttributeCoordinator.swift in Sources */, 5E7C7C8BC4763CFDD3EE119D /* AssetAttributeFunctionCall.swift in Sources */, diff --git a/AlphaWallet/RPC/Commands/web3swift-pod/GetENSInfoEncode.swift b/AlphaWallet/RPC/Commands/web3swift-pod/GetENSInfoEncode.swift new file mode 100644 index 000000000..634bf0dad --- /dev/null +++ b/AlphaWallet/RPC/Commands/web3swift-pod/GetENSInfoEncode.swift @@ -0,0 +1,15 @@ +// +// Created by James Sangalli on 8/11/18. +// + +import Foundation + +struct GetENSResolverEncode { + let abi = "[ { \"constant\": false, \"inputs\": [ { \"name\": \"node\", \"type\": \"bytes32\" } ], \"name\": \"resolver\", \"outputs\": [ { \"name\": \"\", \"type\": \"address\" } ], \"payable\": false, \"stateMutability\": \"nonpayable\", \"type\": \"function\" } ]" + let name = "resolver" +} + +struct GetENSRecordFromResolverEncode { + let abi = "[ { \"constant\": false, \"inputs\": [ { \"name\": \"node\", \"type\": \"bytes32\" } ], \"name\": \"addr\", \"outputs\": [ { \"name\": \"\", \"type\": \"address\" } ], \"payable\": false, \"stateMutability\": \"nonpayable\", \"type\": \"function\" } ]" + let name = "addr" +} diff --git a/AlphaWallet/RPC/Commands/web3swift-pod/GetENSNameEncode.swift b/AlphaWallet/RPC/Commands/web3swift-pod/GetENSNameEncode.swift deleted file mode 100644 index 4052dcdc1..000000000 --- a/AlphaWallet/RPC/Commands/web3swift-pod/GetENSNameEncode.swift +++ /dev/null @@ -1,10 +0,0 @@ -// -// Created by James Sangalli on 8/11/18. -// - -import Foundation - -struct GetENSOwnerEncode { - let abi = "{\"constant\":true,\"inputs\":[{\"name\":\"node\",\"type\":\"bytes32\"}],\"name\":\"owner\",\"outputs\":[{\"name\":\"\",\"type\":\"address\"}],\"payable\":false,\"type\":\"function\"}" - let name = "owner" -} diff --git a/AlphaWallet/RPC/Commands/web3swift-pod/GetERC721BalanceEncode.swift b/AlphaWallet/RPC/Commands/web3swift-pod/GetERC721BalanceEncode.swift index c6a695c32..b5e37cf86 100644 --- a/AlphaWallet/RPC/Commands/web3swift-pod/GetERC721BalanceEncode.swift +++ b/AlphaWallet/RPC/Commands/web3swift-pod/GetERC721BalanceEncode.swift @@ -6,6 +6,6 @@ import Foundation struct GetERC721Balance { - let abi = "{\"constant\":true,\"inputs\":[{\"name\":\"_owner\",\"type\":\"address\"}],\"name\":\"balanceOf\",\"outputs\":[{\"name\":\"\",\"type\":\"uint256\"}],\"payable\":false,\"stateMutability\":\"view\",\"type\":\"function\"}" + let abi = "[{\"constant\":true,\"inputs\":[{\"name\":\"_owner\",\"type\":\"address\"}],\"name\":\"balanceOf\",\"outputs\":[{\"name\":\"\",\"type\":\"uint256\"}],\"payable\":false,\"stateMutability\":\"view\",\"type\":\"function\"}]" let name = "balanceOf" } diff --git a/AlphaWallet/RPC/Commands/web3swift-pod/GetERC875Balance.swift b/AlphaWallet/RPC/Commands/web3swift-pod/GetERC875Balance.swift index a2d132701..2355b963d 100644 --- a/AlphaWallet/RPC/Commands/web3swift-pod/GetERC875Balance.swift +++ b/AlphaWallet/RPC/Commands/web3swift-pod/GetERC875Balance.swift @@ -2,6 +2,6 @@ import Foundation import TrustKeystore struct GetERC875Balance { - let abi = "{\"constant\":true,\"inputs\":[{\"name\":\"_owner\",\"type\":\"address\"}],\"name\":\"balanceOf\",\"outputs\":[{\"name\":\"\",\"type\":\"bytes32[]\"}],\"payable\":false,\"stateMutability\":\"view\",\"type\":\"function\"}" + let abi = "[{\"constant\":true,\"inputs\":[{\"name\":\"_owner\",\"type\":\"address\"}],\"name\":\"balanceOf\",\"outputs\":[{\"name\":\"\",\"type\":\"bytes32[]\"}],\"payable\":false,\"stateMutability\":\"view\",\"type\":\"function\"}]" let name = "balanceOf" } diff --git a/AlphaWallet/RPC/Commands/web3swift-pod/GetIsERC721Encode.swift b/AlphaWallet/RPC/Commands/web3swift-pod/GetIsERC721Encode.swift index d3e8f75a0..27082dfb4 100644 --- a/AlphaWallet/RPC/Commands/web3swift-pod/GetIsERC721Encode.swift +++ b/AlphaWallet/RPC/Commands/web3swift-pod/GetIsERC721Encode.swift @@ -6,6 +6,6 @@ import Foundation struct GetIsERC721 { - let abi = "{ \"constant\": true, \"inputs\": [ { \"name\": \"interfaceID\", \"type\": \"bytes4\" } ], \"name\": \"supportsInterface\", \"outputs\": [ { \"name\": \"\", \"type\": \"bool\" } ], \"payable\": false, \"stateMutability\": \"view\", \"type\": \"function\" }" + let abi = "[{ \"constant\": true, \"inputs\": [ { \"name\": \"interfaceID\", \"type\": \"bytes4\" } ], \"name\": \"supportsInterface\", \"outputs\": [ { \"name\": \"\", \"type\": \"bool\" } ], \"payable\": false, \"stateMutability\": \"view\", \"type\": \"function\" }]" let name = "supportsInterface" } diff --git a/AlphaWallet/RPC/Commands/web3swift-pod/GetIsERC875Encode.swift b/AlphaWallet/RPC/Commands/web3swift-pod/GetIsERC875Encode.swift index d29d92149..ca32d752e 100644 --- a/AlphaWallet/RPC/Commands/web3swift-pod/GetIsERC875Encode.swift +++ b/AlphaWallet/RPC/Commands/web3swift-pod/GetIsERC875Encode.swift @@ -3,6 +3,6 @@ import Foundation struct GetIsERC875 { - let abi = "{\"constant\":true,\"inputs\":[],\"name\":\"isStormBirdContract\",\"outputs\":[{\"name\":\"\",\"type\":\"bool\"}],\"payable\":false,\"stateMutability\":\"view\",\"type\":\"function\"}" + let abi = "[{\"constant\":true,\"inputs\":[],\"name\":\"isStormBirdContract\",\"outputs\":[{\"name\":\"\",\"type\":\"bool\"}],\"payable\":false,\"stateMutability\":\"view\",\"type\":\"function\"}]" let name = "isStormBirdContract" } diff --git a/AlphaWallet/Tokens/Coordinators/GetENSOwnerCoordinator.swift b/AlphaWallet/Tokens/Coordinators/GetENSOwnerCoordinator.swift index 96717a3a5..acac381dd 100644 --- a/AlphaWallet/Tokens/Coordinators/GetENSOwnerCoordinator.swift +++ b/AlphaWallet/Tokens/Coordinators/GetENSOwnerCoordinator.swift @@ -21,7 +21,7 @@ extension String { } } -class GetENSOwnerCoordinator { +class GetENSAddressCoordinator { private struct ENSLookupKey: Hashable { let name: String let server: RPCServer @@ -37,7 +37,7 @@ class GetENSOwnerCoordinator { self.server = server } - func getENSOwner( + func getENSAddressFromResolver( for input: String, completion: @escaping (Result) -> Void ) { @@ -60,21 +60,34 @@ class GetENSOwnerCoordinator { return } - let function = GetENSOwnerEncode() + let function = GetENSResolverEncode() guard let ensRegistrarContract = Address(string: server.ensRegistrarContract.address) else { completion(.failure(AnyError(Web3Error(description: "Error converting contract address: \(server.ensRegistrarContract.address)")))) return } - callSmartContract(withServer: server, contract: ensRegistrarContract, functionName: function.name, abiString: "[\(function.abi)]", parameters: [node] as [AnyObject]).done { result in + callSmartContract(withServer: server, contract: ensRegistrarContract, functionName: function.name, abiString: function.abi, parameters: [node] as [AnyObject]).done { result in //if null address is returned (as 0) we count it as invalid //this is because it is not assigned to an ENS and puts the user in danger of sending funds to null - if let owner = result["0"] as? EthereumAddress { - if owner.address == Constants.nullAddress { + if let resolver = result["0"] as? EthereumAddress { + if resolver.address == Constants.nullAddress { completion(.failure(AnyError(Web3Error(description: "Null address returned")))) } else { - //Retain self because it's useful to cache the results even if we don't immediately need it now - self.cache(forNode: node, result: owner) - completion(.success(owner)) + let function = GetENSRecordFromResolverEncode() + //TODO remove Address as a type because EthereumAddress co-exists or vice versa + callSmartContract(withServer: self.server, contract: Address(string: resolver.address)!, functionName: function.name, abiString: function.abi, parameters: [node] as [AnyObject]).done { result in + if let ensAddress = result["0"] as? EthereumAddress { + if ensAddress.address == Constants.nullAddress { + completion(.failure(AnyError(Web3Error(description: "Null address returned")))) + } else { + //Retain self because it's useful to cache the results even if we don't immediately need it now + self.cache(forNode: node, result: ensAddress) + completion(.success(ensAddress)) + } + } else { + completion(.failure(AnyError(Web3Error(description: "Incorrect data output from ENS resolver")))) + } + } + } } else { completion(.failure(AnyError(Web3Error(description: "Error extracting result from \(ensRegistrarContract).\(function.name)()")))) @@ -92,19 +105,19 @@ class GetENSOwnerCoordinator { } toStartResolvingEnsNameTimer?.invalidate() - toStartResolvingEnsNameTimer = Timer.scheduledTimer(withTimeInterval: GetENSOwnerCoordinator.DELAY_AFTER_STOP_TYPING_TO_START_RESOLVING_ENS_NAME, repeats: false) { _ in + toStartResolvingEnsNameTimer = Timer.scheduledTimer(withTimeInterval: GetENSAddressCoordinator.DELAY_AFTER_STOP_TYPING_TO_START_RESOLVING_ENS_NAME, repeats: false) { _ in //Retain self because it's useful to cache the results even if we don't immediately need it now - self.getENSOwner(for: input) { result in + self.getENSAddressFromResolver(for: input) { result in completion(result) } } } private func cachedResult(forNode node: String) -> EthereumAddress? { - return GetENSOwnerCoordinator.resultsCache[ENSLookupKey(name: node, server: server)] + return GetENSAddressCoordinator.resultsCache[ENSLookupKey(name: node, server: server)] } private func cache(forNode node: String, result: EthereumAddress) { - GetENSOwnerCoordinator.resultsCache[ENSLookupKey(name: node, server: server)] = result + GetENSAddressCoordinator.resultsCache[ENSLookupKey(name: node, server: server)] = result } } diff --git a/AlphaWallet/Tokens/Coordinators/GetERC721BalanceCoordinator.swift b/AlphaWallet/Tokens/Coordinators/GetERC721BalanceCoordinator.swift index 6a208f9e4..238ca4ad6 100644 --- a/AlphaWallet/Tokens/Coordinators/GetERC721BalanceCoordinator.swift +++ b/AlphaWallet/Tokens/Coordinators/GetERC721BalanceCoordinator.swift @@ -21,7 +21,7 @@ class GetERC721BalanceCoordinator { completion: @escaping (Result) -> Void ) { let function = GetERC721Balance() - callSmartContract(withServer: server, contract: contract, functionName: function.name, abiString: "[\(function.abi)]", parameters: [address.eip55String] as [AnyObject]).done { balanceResult in + callSmartContract(withServer: server, contract: contract, functionName: function.name, abiString: function.abi, parameters: [address.eip55String] as [AnyObject]).done { balanceResult in let balance = self.adapt(balanceResult["0"]) completion(.success(balance)) }.catch { error in diff --git a/AlphaWallet/Tokens/Coordinators/GetERC875BalanceCoordinator.swift b/AlphaWallet/Tokens/Coordinators/GetERC875BalanceCoordinator.swift index f3d89f002..ed9d001e7 100644 --- a/AlphaWallet/Tokens/Coordinators/GetERC875BalanceCoordinator.swift +++ b/AlphaWallet/Tokens/Coordinators/GetERC875BalanceCoordinator.swift @@ -17,7 +17,7 @@ class GetERC875BalanceCoordinator { completion: @escaping (Result<[String], AnyError>) -> Void ) { let function = GetERC875Balance() - callSmartContract(withServer: server, contract: contract, functionName: function.name, abiString: "[\(function.abi)]", parameters: [address.eip55String] as [AnyObject]).done { balanceResult in + callSmartContract(withServer: server, contract: contract, functionName: function.name, abiString: function.abi, parameters: [address.eip55String] as [AnyObject]).done { balanceResult in let balances = self.adapt(balanceResult["0"]) completion(.success(balances)) }.catch { diff --git a/AlphaWallet/Tokens/Coordinators/GetIsERC721ContractCoordinator.swift b/AlphaWallet/Tokens/Coordinators/GetIsERC721ContractCoordinator.swift index de49cde16..4defc2b6b 100644 --- a/AlphaWallet/Tokens/Coordinators/GetIsERC721ContractCoordinator.swift +++ b/AlphaWallet/Tokens/Coordinators/GetIsERC721ContractCoordinator.swift @@ -54,7 +54,7 @@ class GetIsERC721ContractCoordinator { let web3 = web3swift.web3(provider: webProvider) let function = GetIsERC721() - guard let contractInstance = web3swift.web3.web3contract(web3: web3, abiString: "[\(function.abi)]", at: contractAddress, options: web3.options) else { + guard let contractInstance = web3swift.web3.web3contract(web3: web3, abiString: function.abi, at: contractAddress, options: web3.options) else { completion(.failure(AnyError(Web3Error(description: "Error creating web3swift contract instance to call \(function.name)()")))) return } diff --git a/AlphaWallet/Tokens/Coordinators/GetIsERC875ContractCoordinator.swift b/AlphaWallet/Tokens/Coordinators/GetIsERC875ContractCoordinator.swift index b7892dbfd..971d36f54 100644 --- a/AlphaWallet/Tokens/Coordinators/GetIsERC875ContractCoordinator.swift +++ b/AlphaWallet/Tokens/Coordinators/GetIsERC875ContractCoordinator.swift @@ -16,7 +16,7 @@ class GetIsERC875ContractCoordinator { completion: @escaping (Result) -> Void ) { let function = GetIsERC875() - callSmartContract(withServer: server, contract: contract, functionName: function.name, abiString: "[\(function.abi)]").done { dictionary in + callSmartContract(withServer: server, contract: contract, functionName: function.name, abiString: function.abi).done { dictionary in if let isERC875 = dictionary["0"] as? Bool { completion(.success(isERC875)) } else { diff --git a/AlphaWallet/UI/AddressTextField.swift b/AlphaWallet/UI/AddressTextField.swift index b01231904..449c76f38 100644 --- a/AlphaWallet/UI/AddressTextField.swift +++ b/AlphaWallet/UI/AddressTextField.swift @@ -149,7 +149,7 @@ class AddressTextField: UIControl { return } else { textField.text = value - GetENSOwnerCoordinator(server: serverToResolveEns).getENSOwner(for: value) { result in + GetENSAddressCoordinator(server: serverToResolveEns).getENSAddressFromResolver(for: value) { result in guard let address = result.value else { //Don't show an error when pasting what seems like a wrong ENS name for better usability return @@ -171,7 +171,7 @@ class AddressTextField: UIControl { private func queueResolution(ofValue value: String) { let value = value.trimmed let oldTextValue = textField.text?.trimmed - GetENSOwnerCoordinator(server: serverToResolveEns).queueGetENSOwner(for: value) { [weak self] result in + GetENSAddressCoordinator(server: serverToResolveEns).queueGetENSOwner(for: value) { [weak self] result in guard let strongSelf = self else { return } if let address = result.value { guard CryptoAddressValidator.isValidAddress(address.address) else { diff --git a/AlphaWalletTests/Tokens/Coordinators/GetENSOwnerCoordinatorTests.swift b/AlphaWalletTests/Tokens/Coordinators/GetENSOwnerCoordinatorTests.swift index 7181d3146..aa522f20e 100644 --- a/AlphaWalletTests/Tokens/Coordinators/GetENSOwnerCoordinatorTests.swift +++ b/AlphaWalletTests/Tokens/Coordinators/GetENSOwnerCoordinatorTests.swift @@ -17,7 +17,7 @@ class GetENSOwnerCoordinatorTests: XCTestCase { expectations.append(expectation) let ensName = "b00n.thisisme.eth" let server = makeServerForMainnet() - GetENSOwnerCoordinator(server: server).getENSOwner(for: ensName) { result in + GetENSAddressCoordinator(server: server).getENSAddressFromResolver(for: ensName) { result in if let address = result.value, address.address.sameContract(as: "0xbbce83173d5c1D122AE64856b4Af0D5AE07Fa362") { expectation.fulfill() }