API를 통해 들어온 데이터를 Codable 을 통해 Model 에 Mapping 시키고
다시 해당 데이터를 Realm에 바로 넣는 방법에 대해 알아 보겠습니다.
예시 Json Data 구조 입니다.
{
"string_data": "18C",
"array_data1": [
{
"language_code": "en",
"name": "English"
},
{
"language_code": "ja",
"name": "Japanese"
}
],
"array_in_object": {
"array_data2" : [
{
"title": "test1",
"name": "test1 입니다."
},
{
"title": "test2",
"name": "test2 입니다."
}
]
}
}
이제 모델들을 정의 해보겠습니다.
import Foundation
import RealmSwift
class ExampleModel: Object, Decodable {
@objc dynamic var stringData: String?
var arrayData1 = List<ArrayData1Content>() //List 구조는 @objc dynamic 를 생략한다.
@objc dynamic var arrayInObject : ArrayInObjectModel?
private enum CodingKeys: String, CodingKey {
case stringData = "string_data"
case arrayData1 = "array_data1"
case arrayInObject = "array_in_object"
}
// CodingKeys 부분을 보면
case stringData = "string_data" 에서
"string_data" 이부분은 실제 Json data의 key 값이고
stringData 은 key 값을 대신해서 쓸 값입니다.
= "string_data" 를 사용하지 않으면 case stringData 의 값을 key 값으로
매핑 하니 유의 하시기 바랍니다.
public required convenience init(from decoder: Decoder) throws {
self.init()
let container = try decoder.container(keyedBy: CodingKeys.self)
let arrayData1Decode =
try container.decodeIfPresent([ArrayData1Content].self, forKey: .arrayData1) ??[ArrayData1Content()]
arrayData1.append(objectsIn: arrayData1Decode)
//중요한 부분 입니다. Json data 에 List 형태의 데이터가 있을 경우 위와 같이 Decode 를 해주어야 합니다.
let arrayInObjectDecode = try container.decodeIfPresent(ArrayInObjectModel.self, forKey: .arrayInObject)
arrayInObject = arrayInObjectDecode
///해당 부분은 List Data 가 안에 포함이 되어있지만 Object 이므로 위와 같이 Decode를 합니다.
/// @objc dynamic var arrayInObject : ArrayInObjectModel? <<<< 선언부를 유심히 보면 List 가 아니므로
/// @objc dynamic 을 붙여준걸 알수 있습니다. 이렇게 붙여야 다음 모델에서 해당 데이터를 사용해 매핑이 가능합니다.
}
}
class ArrayData1Content: Object, Decodable {
@objc dynamic var languageCode: String?
@objc dynamic var name: String?
private enum CodingKeys: String, CodingKey {
case languageCode = "language_code"
case name = "name"
}
}
class ArrayInObjectModel: Object, Decodable {
var arrayData2 = List<ArrayData2Content>()
private enum CodingKeys: String, CodingKey {
case arrayData2 = "array_data2"
}
public required convenience init(from decoder: Decoder) throws {
self.init()
let container = try decoder.container(keyedBy: CodingKeys.self)
let arrayData2Decode = try container.decodeIfPresent([ArrayData2Content].self, forKey: .arrayData2) ?? [ArrayData2Content()]
arrayData2.append(objectsIn: arrayData2Decode)
}
}
class ArrayData2Content : Object, Decodable {
@objc dynamic var title: String?
@objc dynamic var name: String?
private enum CodingKeys: String, CodingKey {
case title = "title"
case name = "name"
}
}
다음은 API 통신을 통해서 Json을 디코딩 해주고 Realm에 데이터를 넣어 주는 부분입니다.
Alamofire 사용방법은
https://sweetcoding.tistory.com/52?category=732018 를 참고 하세요.
do {
let result = try JSONDecoder().decode(ExampleModel.self, from: value)
addLanguagePack(result)
} catch {
}
Realm 사용 방법은
https://sweetcoding.tistory.com/51?category=732018 를 참고 하세요.
func addLanguagePack(_ result : ExampleModel) {
DispatchQueue(label: "background").async {
autoreleasepool {
let realm = try! Realm()
try? realm.write {
realm.add(result)
}
}
}
}
'공부방 > iOS' 카테고리의 다른 글
Tip of update data in swift realm (0) | 2019.07.31 |
---|---|
How to use realm browser (Realm browser 사용 방법 ) (0) | 2019.07.26 |
AsyncSubject, PublishSubject, BehaviorSubject, ReplaySubject (0) | 2019.07.24 |
iOS Firebase Analytics apply (iOS Firebase Analytics 적용) (0) | 2019.07.15 |
iOS Alamofire Apply (iOS Alamofire 적용) (0) | 2019.07.12 |
행복한 코딩을 위하여!
포스팅이 좋았다면 "좋아요❤️" 또는 "구독👍🏻" 해주세요!