|
9 | 9 |
|
10 | 10 | import SwiftMultihash |
11 | 11 | import SwiftMultiaddr |
| 12 | +import Foundation |
12 | 13 |
|
13 | 14 | public class Dht : ClientSubCommand { |
14 | 15 |
|
15 | 16 | var parent: IpfsApiClient? |
16 | 17 |
|
17 | 18 | /** FindProviders will return a list of peers who are able to provide the value requested. */ |
18 | | - public func findProvs(_ hash: Multihash, completionHandler: @escaping (JsonType) -> Void) throws { |
19 | | - try parent!.fetchJson("dht/findprovs?arg=" + b58String(hash), completionHandler: completionHandler) |
| 19 | +// public func findProvs(_ hash: Multihash, numProviders: Int = 20, completionHandler: @escaping (JsonType) -> Void) throws { |
| 20 | +// try parent!.fetchJson("dht/findprovs?arg=\(b58String(hash))&num-providers=\(numProviders)", completionHandler: completionHandler) |
| 21 | +// } |
| 22 | + public func findProvs(_ hash: Multihash, numProviders: Int = 20, completionHandler: @escaping (JsonType) -> Void) throws { |
| 23 | + /// Two test closures to be passed to the fetchStreamJson as parameters. |
| 24 | + let comp = { (result: AnyObject) -> Void in |
| 25 | + print("Job done") |
| 26 | + } |
| 27 | + |
| 28 | + let update : ((Data, URLSessionDataTask) -> Bool) = { (data: Data, task: URLSessionDataTask) -> Bool in |
| 29 | + |
| 30 | + func getHash(from obj: [String : JsonType], forResponse type: Int) -> [String]? { |
| 31 | + |
| 32 | + if obj["Type"]?.number?.intValue == type { |
| 33 | + if let responses = obj["Responses"]?.array { |
| 34 | + // only keep the responses that contain an ID. |
| 35 | + return responses.compactMap { $0.object?["ID"]?.string } |
| 36 | + } |
| 37 | + } |
| 38 | + return nil |
| 39 | + } |
| 40 | + |
| 41 | + |
| 42 | + print("updates") |
| 43 | + let fixed = fixStreamJson(data) |
| 44 | + let json = try? JSONSerialization.jsonObject(with: fixed, options: JSONSerialization.ReadingOptions.allowFragments) |
| 45 | + let parsedJ = JsonType.parse(json as AnyObject) |
| 46 | + |
| 47 | + var providers = [JsonType]() |
| 48 | + // A valid response can either be an array of objects or an object. |
| 49 | + switch parsedJ { |
| 50 | + case JsonType.Array(let array): |
| 51 | +// print("we iz got de arrays") |
| 52 | + providers += array.filter { $0.object?["Type"]?.number == 4 } |
| 53 | +// for obj in array { |
| 54 | +// if let jobj = obj.object, jobj["Type"]?.number == 4 { |
| 55 | +// providers += jobj |
| 56 | +// } |
| 57 | +// } |
| 58 | + case JsonType.Object(let obj): |
| 59 | +// print("we iz got de hobj innit? \(obj)") |
| 60 | + if obj["Type"]?.number == 4 { |
| 61 | + providers.append(parsedJ) |
| 62 | + } |
| 63 | +// if let provs = getHash(from: obj, forResponse: 4) { |
| 64 | +// providers += provs |
| 65 | +// } |
| 66 | + |
| 67 | + default: |
| 68 | + print("fukkal") |
| 69 | + } |
| 70 | + |
| 71 | + |
| 72 | + if providers.count >= numProviders { |
| 73 | + print("We found these providers \(providers)") |
| 74 | + let provs = JsonType.parse(providers as AnyObject) |
| 75 | + completionHandler(provs) |
| 76 | + |
| 77 | + } |
| 78 | + |
| 79 | +// guard let jarray = parsedJ.array else { |
| 80 | +// print("No array in parsed json update \(parsedJ)") |
| 81 | +// return true |
| 82 | +// } |
| 83 | +// |
| 84 | +// for obj in jarray { |
| 85 | +// print("json: \(String(describing: obj.object?["Type"]))") |
| 86 | +// } |
| 87 | + |
| 88 | +// print("json: \(json)") |
| 89 | +// |
| 90 | +// if let arr = json as? [AnyObject] { |
| 91 | +// for res in arr { |
| 92 | +// print(res) |
| 93 | +// } |
| 94 | +// } else { |
| 95 | +// if let dict = json as? [String: AnyObject] { |
| 96 | +// print("It's a dict!:",dict ) |
| 97 | +// } |
| 98 | +// } |
| 99 | + return true |
| 100 | + } |
| 101 | + |
| 102 | + try parent!.fetchStreamJson("dht/findprovs?arg=\(b58String(hash))&num-providers=\(numProviders)", updateHandler: update, completionHandler: comp) |
20 | 103 | } |
21 | 104 |
|
22 | 105 | /** Run a 'findClosestPeers' query through the DHT */ |
|
0 commit comments