From a74170e70b2510bc9ce5f7a5fb8bdf46626a15a9 Mon Sep 17 00:00:00 2001 From: Piet Brauer Date: Tue, 28 Nov 2017 13:59:32 +0100 Subject: [PATCH 1/5] Migrate to Swift 4 --- .travis.yml | 10 +- Gemfile.lock | 134 +++++++++--------- RequestKit.xcodeproj/project.pbxproj | 28 +++- .../xcschemes/RequestKit Mac.xcscheme | 4 +- .../xcschemes/RequestKit tvOS.xcscheme | 4 +- .../xcschemes/RequestKit watchOS.xcscheme | 4 +- .../xcschemes/RequestKit.xcscheme | 4 +- RequestKitTests/JSONPostRouterTests.swift | 4 - fastlane/.env.default | 6 +- fastlane/.env.ios93 | 2 +- 10 files changed, 113 insertions(+), 87 deletions(-) diff --git a/.travis.yml b/.travis.yml index 5275ec8..6c6a306 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,5 +1,5 @@ language: objective-c -osx_image: xcode8.2 +osx_image: xcode9.1 sudo: false env: global: @@ -8,13 +8,13 @@ env: - FASTLANE_LANE=ci_commit matrix: include: - - osx_image: xcode8.2 + - osx_image: xcode9.1 env: FASTLANE_LANE=code_coverage FASTLANE_ENV=default - - osx_image: xcode8.2 + - osx_image: xcode9.1 env: FASTLANE_ENV=ios93 - - osx_image: xcode8.2 + - osx_image: xcode9.1 env: FASTLANE_ENV=tvos92 - - osx_image: xcode8.2 + - osx_image: xcode9.1 env: FASTLANE_ENV=osx before_install: - make install diff --git a/Gemfile.lock b/Gemfile.lock index 8086d1b..2b7f27e 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -1,17 +1,16 @@ GEM remote: https://rubygems.org/ specs: - CFPropertyList (2.3.4) - activesupport (4.2.7.1) + CFPropertyList (2.3.5) + activesupport (4.2.10) i18n (~> 0.7) - json (~> 1.7, >= 1.7.7) minitest (~> 5.1) thread_safe (~> 0.3, >= 0.3.4) tzinfo (~> 1.1) - addressable (2.5.0) - public_suffix (~> 2.0, >= 2.0.2) + addressable (2.5.2) + public_suffix (>= 2.0.2, < 4.0) babosa (1.0.2) - claide (1.0.1) + claide (1.0.2) clamp (0.6.5) cocoapods (1.1.1) activesupport (>= 4.0.2, < 5) @@ -46,37 +45,40 @@ GEM netrc (= 0.7.8) cocoapods-try (1.1.0) colored (1.2) - commander (4.4.3) + colored2 (3.1.2) + commander-fastlane (4.4.5) highline (~> 1.7.2) - domain_name (0.5.20161129) + concurrent-ruby (1.0.5) + declarative (0.0.10) + declarative-option (0.1.0) + domain_name (0.5.20170404) unf (>= 0.0.5, < 1.0.0) - dotenv (2.1.2) + dotenv (2.2.1) escape (0.0.4) - excon (0.54.0) - faraday (0.11.0) + excon (0.59.0) + faraday (0.13.1) multipart-post (>= 1.2, < 3) faraday-cookie_jar (0.0.6) faraday (>= 0.7.4) http-cookie (~> 1.0.0) - faraday_middleware (0.11.0) + faraday_middleware (0.12.2) faraday (>= 0.7.4, < 1.0) - fastimage (2.0.1) - addressable (~> 2) - fastlane (2.9.0) - activesupport (< 5) + fastimage (2.1.0) + fastlane (2.68.0) + CFPropertyList (>= 2.3, < 3.0.0) addressable (>= 2.3, < 3.0.0) babosa (>= 1.0.2, < 2.0.0) - bundler (~> 1.12) + bundler (>= 1.12.0, < 2.0.0) colored - commander (>= 4.4.0, < 5.0.0) + commander-fastlane (>= 4.4.5, < 5.0.0) dotenv (>= 2.1.1, < 3.0.0) excon (>= 0.45.0, < 1.0.0) faraday (~> 0.9) faraday-cookie_jar (~> 0.0.6) faraday_middleware (~> 0.9) - fastimage (>= 1.6) + fastimage (>= 2.1.0, < 3.0.0) gh_inspector (>= 1.0.1, < 2.0.0) - google-api-client (~> 0.9.2) + google-api-client (>= 0.13.1, < 0.14.0) highline (>= 1.7.2, < 2.0.0) json (< 3.0.0) mini_magick (~> 4.5.1) @@ -84,56 +86,56 @@ GEM multi_xml (~> 0.5) multipart-post (~> 2.0.0) plist (>= 3.1.0, < 4.0.0) + public_suffix (~> 2.0.0) rubyzip (>= 1.1.0, < 2.0.0) security (= 0.1.3) slack-notifier (>= 1.3, < 2.0.0) terminal-notifier (>= 1.6.2, < 2.0.0) terminal-table (>= 1.4.5, < 2.0.0) + tty-screen (~> 0.6.2) word_wrap (~> 1.0.0) - xcodeproj (>= 0.20, < 2.0.0) + xcodeproj (>= 1.5.2, < 2.0.0) xcpretty (>= 0.2.4, < 1.0.0) xcpretty-travis-formatter (>= 0.0.3) fourflusher (2.0.1) fuzzy_match (2.0.4) gh_inspector (1.0.3) - google-api-client (0.9.20) - addressable (~> 2.3) + google-api-client (0.13.6) + addressable (~> 2.5, >= 2.5.1) googleauth (~> 0.5) - httpclient (~> 2.7) - hurley (~> 0.1) - memoist (~> 0.11) - mime-types (>= 1.6) - representable (~> 2.3.0) - retriable (~> 2.0) - googleauth (0.5.1) - faraday (~> 0.9) - jwt (~> 1.4) + httpclient (>= 2.8.1, < 3.0) + mime-types (~> 3.0) + representable (~> 3.0) + retriable (>= 2.0, < 4.0) + googleauth (0.6.2) + faraday (~> 0.12) + jwt (>= 1.4, < 3.0) logging (~> 2.0) memoist (~> 0.12) multi_json (~> 1.11) os (~> 0.9) signet (~> 0.7) - highline (1.7.8) + highline (1.7.10) http-cookie (1.0.3) domain_name (~> 0.5) httpclient (2.8.3) - hurley (0.2) - i18n (0.7.0) - json (1.8.6) - jwt (1.5.6) + i18n (0.9.1) + concurrent-ruby (~> 1.0) + json (2.1.0) + jwt (2.1.0) little-plugger (1.1.4) - logging (2.1.0) + logging (2.2.2) little-plugger (~> 1.1) multi_json (~> 1.10) - memoist (0.15.0) + memoist (0.16.0) mime-types (3.1) mime-types-data (~> 3.2015) mime-types-data (3.2016.0521) mini_magick (4.5.1) mini_portile2 (2.1.0) - minitest (5.10.1) + minitest (5.10.3) molinillo (0.5.5) - multi_json (1.12.1) + multi_json (1.12.2) multi_xml (0.6.0) multipart-post (2.0.0) nanaimo (0.2.3) @@ -142,18 +144,20 @@ GEM nokogiri (1.6.8.1) mini_portile2 (~> 2.1.0) os (0.9.6) - plist (3.2.0) + plist (3.3.0) public_suffix (2.0.5) - representable (2.3.0) - uber (~> 0.0.7) - retriable (2.1.0) - rouge (1.11.1) - rubyzip (1.2.0) + representable (3.0.4) + declarative (< 0.1.0) + declarative-option (< 0.2.0) + uber (< 0.2.0) + retriable (3.1.1) + rouge (2.0.7) + rubyzip (1.2.1) security (0.1.3) - signet (0.7.3) + signet (0.8.1) addressable (~> 2.3) faraday (~> 0.9) - jwt (~> 1.5) + jwt (>= 1.5, < 3.0) multi_json (~> 1.10) slack-notifier (1.5.1) slather (2.3.0) @@ -161,27 +165,27 @@ GEM clamp (~> 0.6) nokogiri (~> 1.6.3) xcodeproj (>= 0.20, < 2.0.0) - terminal-notifier (1.7.1) - terminal-table (1.7.3) - unicode-display_width (~> 1.1.1) - thread_safe (0.3.5) - tzinfo (1.2.2) + terminal-notifier (1.8.0) + terminal-table (1.8.0) + unicode-display_width (~> 1.1, >= 1.1.1) + thread_safe (0.3.6) + tty-screen (0.6.3) + tzinfo (1.2.4) thread_safe (~> 0.1) - uber (0.0.15) + uber (0.1.0) unf (0.1.4) unf_ext - unf_ext (0.0.7.2) - unicode-display_width (1.1.3) + unf_ext (0.0.7.4) + unicode-display_width (1.3.0) word_wrap (1.0.0) - xcodeproj (1.4.2) + xcodeproj (1.5.3) CFPropertyList (~> 2.3.3) - activesupport (>= 3) - claide (>= 1.0.1, < 2.0) - colored (~> 1.2) + claide (>= 1.0.2, < 2.0) + colored2 (~> 3.1) nanaimo (~> 0.2.3) - xcpretty (0.2.4) - rouge (~> 1.8) - xcpretty-travis-formatter (0.0.4) + xcpretty (0.2.8) + rouge (~> 2.0.7) + xcpretty-travis-formatter (1.0.0) xcpretty (~> 0.2, >= 0.0.7) PLATFORMS @@ -193,4 +197,4 @@ DEPENDENCIES slather (~> 2.0) BUNDLED WITH - 1.13.6 + 1.16.0 diff --git a/RequestKit.xcodeproj/project.pbxproj b/RequestKit.xcodeproj/project.pbxproj index b2f0d6d..89cc268 100644 --- a/RequestKit.xcodeproj/project.pbxproj +++ b/RequestKit.xcodeproj/project.pbxproj @@ -368,7 +368,7 @@ isa = PBXProject; attributes = { LastSwiftUpdateCheck = 0720; - LastUpgradeCheck = 0830; + LastUpgradeCheck = 0910; ORGANIZATIONNAME = nerdishbynature; TargetAttributes = { 233742FF1C7981A800013492 = { @@ -398,13 +398,13 @@ CreatedOnToolsVersion = 7.1; DevelopmentTeam = 3NPZ2HXWU8; DevelopmentTeamName = "Piet Brauer"; - LastSwiftMigration = 0800; + LastSwiftMigration = 0910; }; 234F4C251BDDF64300A58EF7 = { CreatedOnToolsVersion = 7.1; DevelopmentTeam = 3NPZ2HXWU8; DevelopmentTeamName = "Piet Brauer"; - LastSwiftMigration = 0800; + LastSwiftMigration = 0910; }; }; }; @@ -761,14 +761,20 @@ CLANG_CXX_LIBRARY = "libc++"; CLANG_ENABLE_MODULES = YES; CLANG_ENABLE_OBJC_ARC = YES; + CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; CLANG_WARN_BOOL_CONVERSION = YES; + CLANG_WARN_COMMA = YES; CLANG_WARN_CONSTANT_CONVERSION = YES; CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; CLANG_WARN_EMPTY_BODY = YES; CLANG_WARN_ENUM_CONVERSION = YES; CLANG_WARN_INFINITE_RECURSION = YES; CLANG_WARN_INT_CONVERSION = YES; + CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; + CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; + CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; + CLANG_WARN_STRICT_PROTOTYPES = YES; CLANG_WARN_SUSPICIOUS_MOVE = YES; CLANG_WARN_UNREACHABLE_CODE = YES; CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; @@ -815,14 +821,20 @@ CLANG_CXX_LIBRARY = "libc++"; CLANG_ENABLE_MODULES = YES; CLANG_ENABLE_OBJC_ARC = YES; + CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; CLANG_WARN_BOOL_CONVERSION = YES; + CLANG_WARN_COMMA = YES; CLANG_WARN_CONSTANT_CONVERSION = YES; CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; CLANG_WARN_EMPTY_BODY = YES; CLANG_WARN_ENUM_CONVERSION = YES; CLANG_WARN_INFINITE_RECURSION = YES; CLANG_WARN_INT_CONVERSION = YES; + CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; + CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; + CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; + CLANG_WARN_STRICT_PROTOTYPES = YES; CLANG_WARN_SUSPICIOUS_MOVE = YES; CLANG_WARN_UNREACHABLE_CODE = YES; CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; @@ -867,6 +879,8 @@ LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks"; SKIP_INSTALL = YES; SWIFT_OPTIMIZATION_LEVEL = "-Onone"; + SWIFT_SWIFT3_OBJC_INFERENCE = On; + SWIFT_VERSION = 4.0; }; name = Debug; }; @@ -883,6 +897,8 @@ LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks"; SKIP_INSTALL = YES; SWIFT_OPTIMIZATION_LEVEL = "-Owholemodule"; + SWIFT_SWIFT3_OBJC_INFERENCE = On; + SWIFT_VERSION = 4.0; }; name = Release; }; @@ -895,7 +911,8 @@ PRODUCT_BUNDLE_IDENTIFIER = com.nerdishbynature.RequestKitTests; PRODUCT_NAME = "$(TARGET_NAME)"; SWIFT_OPTIMIZATION_LEVEL = "-Onone"; - SWIFT_VERSION = 3.0; + SWIFT_SWIFT3_OBJC_INFERENCE = On; + SWIFT_VERSION = 4.0; }; name = Debug; }; @@ -908,7 +925,8 @@ PRODUCT_BUNDLE_IDENTIFIER = com.nerdishbynature.RequestKitTests; PRODUCT_NAME = "$(TARGET_NAME)"; SWIFT_OPTIMIZATION_LEVEL = "-Owholemodule"; - SWIFT_VERSION = 3.0; + SWIFT_SWIFT3_OBJC_INFERENCE = On; + SWIFT_VERSION = 4.0; }; name = Release; }; diff --git a/RequestKit.xcodeproj/xcshareddata/xcschemes/RequestKit Mac.xcscheme b/RequestKit.xcodeproj/xcshareddata/xcschemes/RequestKit Mac.xcscheme index 8d5386d..adf759f 100644 --- a/RequestKit.xcodeproj/xcshareddata/xcschemes/RequestKit Mac.xcscheme +++ b/RequestKit.xcodeproj/xcshareddata/xcschemes/RequestKit Mac.xcscheme @@ -1,6 +1,6 @@ @@ -45,6 +46,7 @@ buildConfiguration = "Debug" selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB" selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB" + language = "" launchStyle = "0" useCustomWorkingDirectory = "NO" ignoresPersistentStateOnLaunch = "NO" diff --git a/RequestKit.xcodeproj/xcshareddata/xcschemes/RequestKit.xcscheme b/RequestKit.xcodeproj/xcshareddata/xcschemes/RequestKit.xcscheme index 0c71c93..78fb1bc 100644 --- a/RequestKit.xcodeproj/xcshareddata/xcschemes/RequestKit.xcscheme +++ b/RequestKit.xcodeproj/xcshareddata/xcschemes/RequestKit.xcscheme @@ -1,6 +1,6 @@ @@ -56,6 +57,7 @@ buildConfiguration = "Debug" selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB" selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB" + language = "" launchStyle = "0" useCustomWorkingDirectory = "NO" ignoresPersistentStateOnLaunch = "NO" diff --git a/RequestKitTests/JSONPostRouterTests.swift b/RequestKitTests/JSONPostRouterTests.swift index 2481e61..3e4afed 100644 --- a/RequestKitTests/JSONPostRouterTests.swift +++ b/RequestKitTests/JSONPostRouterTests.swift @@ -14,8 +14,6 @@ class JSONPostRouterTests: XCTestCase { XCTAssertEqual(error.code, 401) XCTAssertEqual(error.domain, "com.nerdishbynature.RequestKitTests") XCTAssertEqual((error.userInfo[RequestKitErrorResponseKey] as? [String: String]) ?? [:], jsonDict) - case .failure: - XCTAssertTrue(false) } } XCTAssertNotNil(task) @@ -33,8 +31,6 @@ class JSONPostRouterTests: XCTestCase { XCTAssertEqual(error.code, 401) XCTAssertEqual(error.domain, "com.nerdishbynature.RequestKitTests") XCTAssertEqual((error.userInfo[RequestKitErrorResponseKey] as? String) ?? "", errorString) - case .failure: - XCTAssertTrue(false) } } XCTAssertNotNil(task) diff --git a/fastlane/.env.default b/fastlane/.env.default index 76a6d9c..e08f51d 100644 --- a/fastlane/.env.default +++ b/fastlane/.env.default @@ -1,6 +1,6 @@ -AF_IOS_SDK=iphonesimulator10.2 -AF_MAC_SDK=macosx10.12 -AF_TVOS_SDK=appletvsimulator10.1 +AF_IOS_SDK=iphonesimulator11.1 +AF_MAC_SDK=macosx10.13 +AF_TVOS_SDK=appletvsimulator11.1 AF_CONFIGURATION=Release diff --git a/fastlane/.env.ios93 b/fastlane/.env.ios93 index d677f88..e0f3f7a 100644 --- a/fastlane/.env.ios93 +++ b/fastlane/.env.ios93 @@ -1,3 +1,3 @@ SCAN_DEVICE="iPhone 6s" -SCAN_SDK=iphonesimulator10.2 +SCAN_SDK=iphonesimulator11.1 EXAMPLE_DESTINATION="platform=iOS Simulator,name=iPhone 6s" From 9ac8a3186e6401aa56f4ee3826939ee2a57b4c3f Mon Sep 17 00:00:00 2001 From: Piet Brauer Date: Tue, 28 Nov 2017 16:40:44 +0100 Subject: [PATCH 2/5] Add codable methods --- RequestKit/JSONPostRouter.swift | 46 ++++++++++++++++++++++++++++++++ RequestKit/Router.swift | 33 ++++++++++++++++++++++- RequestKitTests/TestHelper.swift | 7 +++++ 3 files changed, 85 insertions(+), 1 deletion(-) diff --git a/RequestKit/JSONPostRouter.swift b/RequestKit/JSONPostRouter.swift index 77c2e98..733e34d 100644 --- a/RequestKit/JSONPostRouter.swift +++ b/RequestKit/JSONPostRouter.swift @@ -2,6 +2,7 @@ import Foundation public protocol JSONPostRouter: Router { func postJSON(_ session: RequestKitURLSession, expectedResultType: T.Type, completion: @escaping (_ json: T?, _ error: Error?) -> Void) -> URLSessionDataTaskProtocol? + func post(_ session: RequestKitURLSession, expectedResultType: T.Type, completion: @escaping (_ json: T?, _ error: Error?) -> Void) -> URLSessionDataTaskProtocol? } public let RequestKitErrorResponseKey = "RequestKitErrorResponseKey" @@ -51,4 +52,49 @@ public extension JSONPostRouter { task.resume() return task } + + public func post(_ session: RequestKitURLSession = URLSession.shared, expectedResultType: T.Type, completion: @escaping (_ json: T?, _ error: Error?) -> Void) -> URLSessionDataTaskProtocol? { + guard let request = request() else { + return nil + } + + let data: Data + do { + data = try JSONSerialization.data(withJSONObject: params, options: JSONSerialization.WritingOptions()) + } catch { + completion(nil, error) + return nil + } + + let task = session.uploadTask(with: request, fromData: data) { data, response, error in + if let response = response as? HTTPURLResponse { + if !response.wasSuccessful { + var userInfo = [String: AnyObject]() + if let data = data, let json = try? JSONSerialization.jsonObject(with: data, options: .mutableContainers) as? [String: AnyObject] { + userInfo[RequestKitErrorResponseKey] = json as AnyObject? + } else if let data = data, let string = String(data: data, encoding: String.Encoding.utf8) { + userInfo[RequestKitErrorResponseKey] = string as AnyObject? + } + let error = NSError(domain: self.configuration.errorDomain, code: response.statusCode, userInfo: userInfo) + completion(nil, error) + return + } + } + + if let error = error { + completion(nil, error) + } else { + if let data = data { + do { + let decoded = try JSONDecoder().decode(T.self, from: data) + completion(decoded, nil) + } catch { + completion(nil, error) + } + } + } + } + task.resume() + return task + } } diff --git a/RequestKit/Router.swift b/RequestKit/Router.swift index 72e2029..9a98964 100644 --- a/RequestKit/Router.swift +++ b/RequestKit/Router.swift @@ -6,7 +6,7 @@ public enum Response { } public enum HTTPMethod: String { - case GET = "GET", POST = "POST" + case GET, POST } public enum HTTPEncoding: Int { @@ -134,6 +134,37 @@ public extension Router { task.resume() return task } + + public func load(_ session: RequestKitURLSession = URLSession.shared, expectedResultType: T.Type, completion: @escaping (_ json: T?, _ error: Error?) -> Void) -> URLSessionDataTaskProtocol? { + guard let request = request() else { + return nil + } + + let task = session.dataTask(with: request) { data, response, err in + if let response = response as? HTTPURLResponse { + if response.wasSuccessful == false { + let error = NSError(domain: self.configuration.errorDomain, code: response.statusCode, userInfo: nil) + completion(nil, error) + return + } + } + + if let err = err { + completion(nil, err) + } else { + if let data = data { + do { + let decoded = try JSONDecoder().decode(T.self, from: data) + completion(decoded, nil) + } catch { + completion(nil, error) + } + } + } + } + task.resume() + return task + } } fileprivate extension CharacterSet { diff --git a/RequestKitTests/TestHelper.swift b/RequestKitTests/TestHelper.swift index 71aa59e..c146cd7 100644 --- a/RequestKitTests/TestHelper.swift +++ b/RequestKitTests/TestHelper.swift @@ -19,4 +19,11 @@ internal class Helper { options: JSONSerialization.ReadingOptions.mutableContainers) return dict! } + + internal class func codableFromFile(_ name: String, type: T.Type) -> Any { + let bundle = Bundle(for: self) + let path = bundle.path(forResource: name, ofType: "json")! + let data = try! Data(contentsOf: URL(fileURLWithPath: path)) + return try! JSONDecoder().decode(T.self, from: data) + } } From c706faace4f88b4253990f86e8f560f822ef957f Mon Sep 17 00:00:00 2001 From: Piet Brauer Date: Wed, 6 Dec 2017 17:09:17 +0100 Subject: [PATCH 3/5] Use `load` in `loadJSON` deprecate method --- RequestKit/Router.swift | 36 ++++++------------------------------ 1 file changed, 6 insertions(+), 30 deletions(-) diff --git a/RequestKit/Router.swift b/RequestKit/Router.swift index 9a98964..dbefb9c 100644 --- a/RequestKit/Router.swift +++ b/RequestKit/Router.swift @@ -39,7 +39,9 @@ public protocol Router { func urlQuery(_ parameters: [String: Any]) -> [URLQueryItem]? func request(_ urlComponents: URLComponents, parameters: [String: Any]) -> URLRequest? - func loadJSON(_ session: RequestKitURLSession, expectedResultType: T.Type, completion: @escaping (_ json: T?, _ error: Error?) -> Void) -> URLSessionDataTaskProtocol? + func loadJSON(_ session: RequestKitURLSession, expectedResultType: T.Type, completion: @escaping (_ json: T?, _ error: Error?) -> Void) -> URLSessionDataTaskProtocol? + func load(_ session: RequestKitURLSession, expectedResultType: T.Type, completion: @escaping (_ json: T?, _ error: Error?) -> Void) -> URLSessionDataTaskProtocol? + func request() -> URLRequest? } @@ -104,35 +106,9 @@ public extension Router { } } - public func loadJSON(_ session: RequestKitURLSession = URLSession.shared, expectedResultType: T.Type, completion: @escaping (_ json: T?, _ error: Error?) -> Void) -> URLSessionDataTaskProtocol? { - guard let request = request() else { - return nil - } - - let task = session.dataTask(with: request) { data, response, err in - if let response = response as? HTTPURLResponse { - if response.wasSuccessful == false { - let error = NSError(domain: self.configuration.errorDomain, code: response.statusCode, userInfo: nil) - completion(nil, error) - return - } - } - - if let err = err { - completion(nil, err) - } else { - if let data = data { - do { - let JSON = try JSONSerialization.jsonObject(with: data, options: .mutableContainers) as? T - completion(JSON, nil) - } catch { - completion(nil, error) - } - } - } - } - task.resume() - return task + @available(*, deprecated, message: "Plase use `load` method instead") + public func loadJSON(_ session: RequestKitURLSession = URLSession.shared, expectedResultType: T.Type, completion: @escaping (_ json: T?, _ error: Error?) -> Void) -> URLSessionDataTaskProtocol? { + return load(session, expectedResultType: expectedResultType, completion: completion) } public func load(_ session: RequestKitURLSession = URLSession.shared, expectedResultType: T.Type, completion: @escaping (_ json: T?, _ error: Error?) -> Void) -> URLSessionDataTaskProtocol? { From 799a4abaf1fce0847d0b92e85becaf35dbfaba9f Mon Sep 17 00:00:00 2001 From: Piet Brauer Date: Fri, 22 Dec 2017 10:05:20 +0100 Subject: [PATCH 4/5] Remove Objective-C inference --- RequestKit.xcodeproj/project.pbxproj | 4 ---- 1 file changed, 4 deletions(-) diff --git a/RequestKit.xcodeproj/project.pbxproj b/RequestKit.xcodeproj/project.pbxproj index 89cc268..56ab826 100644 --- a/RequestKit.xcodeproj/project.pbxproj +++ b/RequestKit.xcodeproj/project.pbxproj @@ -879,7 +879,6 @@ LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks"; SKIP_INSTALL = YES; SWIFT_OPTIMIZATION_LEVEL = "-Onone"; - SWIFT_SWIFT3_OBJC_INFERENCE = On; SWIFT_VERSION = 4.0; }; name = Debug; @@ -897,7 +896,6 @@ LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks"; SKIP_INSTALL = YES; SWIFT_OPTIMIZATION_LEVEL = "-Owholemodule"; - SWIFT_SWIFT3_OBJC_INFERENCE = On; SWIFT_VERSION = 4.0; }; name = Release; @@ -911,7 +909,6 @@ PRODUCT_BUNDLE_IDENTIFIER = com.nerdishbynature.RequestKitTests; PRODUCT_NAME = "$(TARGET_NAME)"; SWIFT_OPTIMIZATION_LEVEL = "-Onone"; - SWIFT_SWIFT3_OBJC_INFERENCE = On; SWIFT_VERSION = 4.0; }; name = Debug; @@ -925,7 +922,6 @@ PRODUCT_BUNDLE_IDENTIFIER = com.nerdishbynature.RequestKitTests; PRODUCT_NAME = "$(TARGET_NAME)"; SWIFT_OPTIMIZATION_LEVEL = "-Owholemodule"; - SWIFT_SWIFT3_OBJC_INFERENCE = On; SWIFT_VERSION = 4.0; }; name = Release; From 39c65fcbd4c505617fa78911b4d3a05d2bc8b057 Mon Sep 17 00:00:00 2001 From: Piet Brauer Date: Fri, 22 Dec 2017 10:05:39 +0100 Subject: [PATCH 5/5] Add custom dateDecodingStrategy option --- RequestKit/Router.swift | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/RequestKit/Router.swift b/RequestKit/Router.swift index dbefb9c..51193e4 100644 --- a/RequestKit/Router.swift +++ b/RequestKit/Router.swift @@ -40,7 +40,7 @@ public protocol Router { func urlQuery(_ parameters: [String: Any]) -> [URLQueryItem]? func request(_ urlComponents: URLComponents, parameters: [String: Any]) -> URLRequest? func loadJSON(_ session: RequestKitURLSession, expectedResultType: T.Type, completion: @escaping (_ json: T?, _ error: Error?) -> Void) -> URLSessionDataTaskProtocol? - func load(_ session: RequestKitURLSession, expectedResultType: T.Type, completion: @escaping (_ json: T?, _ error: Error?) -> Void) -> URLSessionDataTaskProtocol? + func load(_ session: RequestKitURLSession, dateDecodingStrategy: JSONDecoder.DateDecodingStrategy?, expectedResultType: T.Type, completion: @escaping (_ json: T?, _ error: Error?) -> Void) -> URLSessionDataTaskProtocol? func request() -> URLRequest? } @@ -111,7 +111,7 @@ public extension Router { return load(session, expectedResultType: expectedResultType, completion: completion) } - public func load(_ session: RequestKitURLSession = URLSession.shared, expectedResultType: T.Type, completion: @escaping (_ json: T?, _ error: Error?) -> Void) -> URLSessionDataTaskProtocol? { + public func load(_ session: RequestKitURLSession = URLSession.shared, dateDecodingStrategy: JSONDecoder.DateDecodingStrategy? = nil, expectedResultType: T.Type, completion: @escaping (_ json: T?, _ error: Error?) -> Void) -> URLSessionDataTaskProtocol? { guard let request = request() else { return nil } @@ -130,7 +130,11 @@ public extension Router { } else { if let data = data { do { - let decoded = try JSONDecoder().decode(T.self, from: data) + let decoder = JSONDecoder() + if let dateDecodingStrategy = dateDecodingStrategy { + decoder.dateDecodingStrategy = dateDecodingStrategy + } + let decoded = try decoder.decode(T.self, from: data) completion(decoded, nil) } catch { completion(nil, error)