Created
July 2, 2019 15:58
-
-
Save ppth0608/89b73424bd8356646587ec9f1591d244 to your computer and use it in GitHub Desktop.
How to use RxMoya
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import Foundation | |
public struct Clip: Codable, Equatable { | |
public var id: Int | |
public var category: ClipCategory | |
public var title: String | |
public var userTitle: String | |
public var imageURLString: String | |
public var source: String | |
public var urlString: String | |
public var isBookmarked: Bool | |
public var createdDateString: String | |
public var updatedDateString: String | |
public var imageURL: URL? { | |
return URL(string: imageURLString) | |
} | |
public var url: URL? { | |
return URL(string: urlString) | |
} | |
public var createdDate: Date? { | |
return DateFormatter().date(from: createdDateString) | |
} | |
public var updatedDate: Date? { | |
return DateFormatter().date(from: updatedDateString) | |
} | |
public init(category: ClipCategory, urlString: String, userTitle: String) { | |
self.id = 0 | |
self.category = category | |
self.title = "" | |
self.userTitle = userTitle | |
self.imageURLString = "" | |
self.source = "" | |
self.urlString = urlString | |
self.isBookmarked = false | |
self.createdDateString = "" | |
self.updatedDateString = "" | |
} | |
public init() { | |
self.id = 0 | |
self.category = ClipCategory() | |
self.title = "" | |
self.userTitle = "" | |
self.imageURLString = "" | |
self.source = "" | |
self.urlString = "" | |
self.isBookmarked = false | |
self.createdDateString = "" | |
self.updatedDateString = "" | |
} | |
public enum CodingKeys: String, CodingKey { | |
case id | |
case category | |
case title | |
case userTitle = "personalTitle" | |
case source = "sourceOf" | |
case imageURLString = "thumnailLink" | |
case urlString = "url" | |
case isBookmarked = "bookmark" | |
case createdDateString = "createdDate" | |
case updatedDateString = "updatedDate" | |
} | |
public init(from decoder: Decoder) throws { | |
let container = try decoder.container(keyedBy: CodingKeys.self) | |
id = (try? container.decode(Int.self, forKey: .id)) ?? 0 | |
category = (try? container.decode(ClipCategory.self, forKey: .category)) ?? ClipCategory() | |
title = (try? container.decode(String.self, forKey: .title)) ?? "" | |
userTitle = (try? container.decode(String.self, forKey: .userTitle)) ?? "" | |
source = (try? container.decode(String.self, forKey: .source)) ?? "" | |
imageURLString = (try? container.decode(String.self, forKey: .imageURLString)) ?? "" | |
urlString = (try? container.decode(String.self, forKey: .urlString)) ?? "" | |
isBookmarked = (try? container.decode(Bool.self, forKey: .isBookmarked)) ?? false | |
createdDateString = (try? container.decode(String.self, forKey: .createdDateString)) ?? "" | |
updatedDateString = (try? container.decode(String.self, forKey: .updatedDateString)) ?? "" | |
} | |
static public func == (lhs: Clip, rhs: Clip) -> Bool { | |
return lhs.id == rhs.id | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import Moya | |
import RxOptional | |
import RxSwift | |
import Model | |
public struct ClipAPI { | |
enum APIError: Error { | |
case invalidUserID | |
} | |
let provider: MoyaProvider<ClipTarget> | |
let userID: Int? | |
public init(userID: Int?) { | |
provider = MoyaProvider<ClipTarget>() | |
self.userID = userID | |
} | |
public func recentClips(keyword: String = "") -> Observable<[Clip]> { | |
guard let userID = userID else { return .error(APIError.invalidUserID) } | |
return self.provider.rx | |
.request(.recentClipList(userID: userID, keyword: keyword)) | |
.filterSuccessfulStatusCodes() | |
.map([Clip].self, atKeyPath: "posts") | |
.asObservable() | |
} | |
public func clips(for category: ClipCategory) -> Observable<[Clip]> { | |
guard let userID = userID else { return .error(APIError.invalidUserID) } | |
return self.provider.rx | |
.request(.categoryClipList(userID: userID, category: category)) | |
.filterSuccessfulStatusCodes() | |
.map([Clip].self, atKeyPath: "posts") | |
.asObservable() | |
} | |
public func add(with clip: Clip) -> Observable<Clip> { | |
guard let userID = userID else { return .error(APIError.invalidUserID) } | |
return self.provider.rx | |
.request(.addClip(userID: userID, clip: clip)) | |
.filterSuccessfulStatusCodes() | |
.map(Clip.self) | |
.asObservable() | |
} | |
public func bookmark(with clip: Clip) -> Observable<Clip> { | |
guard let userID = userID else { return .error(APIError.invalidUserID) } | |
return self.provider.rx | |
.request(.bookmark(userID: userID, clip: clip)) | |
.filterSuccessfulStatusCodes() | |
.map(Clip.self) | |
.asObservable() | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import Foundation | |
import Moya | |
import Model | |
enum ClipTarget { | |
case recentClipList(userID: Int, keyword: String) | |
case categoryClipList(userID: Int, category: ClipCategory) | |
case addClip(userID: Int, clip: Clip) | |
case bookmark(userID: Int, clip: Clip) | |
} | |
extension ClipTarget: TargetType { | |
var baseURL: URL { return URL(string: "http://localhost:8080")! } | |
var path: String { | |
switch self { | |
case .recentClipList: return "/posts" | |
case .categoryClipList(_, let category): return "/categories/\(category.id)/posts" | |
case .addClip: return "/posts" | |
case .bookmark(_, let clip): return "/post/\(clip.id)/bookmark" | |
} | |
} | |
var method: Moya.Method { | |
switch self { | |
case .recentClipList: return .get | |
case .categoryClipList: return .get | |
case .addClip: return .post | |
case .bookmark: return .put | |
} | |
} | |
var headers: [String : String]? { | |
var headers = [String : String]() | |
headers["Content-type"] = "application/json" | |
switch self { | |
case .recentClipList(let userID, _): | |
headers["UserID"] = "\(userID)" | |
case .categoryClipList(let userID, _): | |
headers["UserID"] = "\(userID)" | |
case .addClip(let userID, _): | |
headers["UserID"] = "\(userID)" | |
case .bookmark(let userID, _): | |
headers["UserID"] = "\(userID)" | |
} | |
return headers | |
} | |
var task: Task { | |
switch self { | |
case .recentClipList(_, let keyword): | |
if keyword.isNotEmpty { | |
return .requestParameters(parameters: [ | |
"keyword": keyword, | |
"page": "0", | |
"size": "100" | |
], encoding: URLEncoding.queryString) | |
} | |
return .requestParameters(parameters: [ | |
"page": "0", | |
"size": "100" | |
], encoding: URLEncoding.queryString) | |
case .categoryClipList: | |
return .requestParameters(parameters: [ | |
"page": "0", | |
"size": "100" | |
], encoding: URLEncoding.queryString) | |
case .addClip(_ , let clip): | |
return .requestParameters(parameters: [ | |
"url": clip.urlString, | |
"personalTitle": clip.userTitle, | |
"category": [ | |
"id": clip.category.id, | |
] | |
], encoding: JSONEncoding.default) | |
case .bookmark: | |
return .requestPlain | |
} | |
} | |
var sampleData: Data { | |
return "".data(using: .utf8)! | |
} | |
} | |
private extension String { | |
var urlEscaped: String { | |
return addingPercentEncoding(withAllowedCharacters: .urlHostAllowed)! | |
} | |
var utf8Encoded: Data { | |
return data(using: .utf8)! | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment