2017-10-17 4 views
1

コード可能なプロトコルと迅速でJSONオブジェクトモデルをへ:どのようなアーキテクチャ私はRESTのWebアプリのクライアントをコーディングしていると私はこのようになりますJSONを使用

JSON1

{ 
    "device" : "iPhone" 
    "manufacturer" : "Apple" 
    "id" : 42 

    "owner" : "Steve" 
} 

しかし、APIを与えることができます私JSONのこの種も

JSON2

{ 
    "device" : "iPhone" 
    "manufacturer" : "Apple" 
    "id" : 42 

    "latitude" : 3.1415926535 
    "longitude" : 2.7182818284 
} 

だから今私のアプリでは、私は構造体を作成します誰がこのアーキテクチャは動作しますが、それは最高の1またはエレガントではない私には思えるコード可能なプロトコルに

struct MyStruct : Codable { 
    var name: String 
    var manufacturer: String 

    var owner: String? 

    // I prefer to use a property of type Location rather than 2 variables 
    var location: Location? { 
    guard let latitude = latitude, let longitude = longitude else { 
     return nil 
    } 

    return Location(latitude: latitude, longitude: longitude) 
    } 

    // Used to conform to the Codable protocol 
    private var latitude: Double? 
    private var longitude: Double? 
} 

struct Location { 
    var latitude: Double = 0.0 
    var longitude: Double = 0.0 
} 

を準拠しています。あなたはより良いアプローチ が存在するかどうか知っていますか?私が代わりのように2貴様JSONモデルを使用する必要があります。

struct MyStruct1 : Codable { 
    var name: String 
    var manufacturer: String 
    var owner: String 
} 

struct MyStruct2 : Codable { 
    var name: String 
    var manufacturer: String 

    private var latitude: Double 
    private var longitude: Double 
} 

私は、REST APIクライアントに新たなんだとJSONのこの種のは良いアーキテクチャを使用しているようだしません。

+1

私は1つの構造体を使用し、その後のためのoptionalsを使用しますその値は最初の例のように2つのison構造体の間で共有されていません – Marcel

答えて

1

owner,latitude & longitudeプロパティはオプションです。 そして、プロパティの復号化には、decodeIfPresentを使用してください。

あなたがstruct

れたまま
struct UserData: Codable {//Confroms to Codable protocol 
    var id: Int 
    var device: String 
    var manufacturer: String 
    var owner: String? = nil//Making property optional 
    var latitude: Double? = nil//Making property optional 
    var longitude: Double? = nil//Making property optional 
    init(from decoder: Decoder) throws { 
     let values = try decoder.container(keyedBy: CodingKeys.self) 
     id = try values.decode(Int.self, forKey: .id) 
     device = try values.decode(String.self, forKey: .device) 
     manufacturer = try values.decode(String.self, forKey: .manufacturer) 
     owner = try values.decodeIfPresent(String.self, forKey: .owner) 
     latitude = try values.decodeIfPresent(Double.self, forKey: .latitude) 
     longitude = try values.decodeIfPresent(Double.self, forKey: .longitude) 
    } 
} 

例JSONを作成することができます。

let jsonExample = """ 
{ 
    "device" : "iPhone", 
    "manufacturer" : "Apple", 
    "id" : 42, 
    "owner" : "Steve" 
} 
""".data(using: .utf8)! 
    let jsonExample2 = """ 
{ 
    "device" : "iPhone", 
    "manufacturer" : "Apple", 
    "id" : 42, 
    "latitude" : 3.1415926535, 
    "longitude" : 2.7182818284 
} 
""".data(using: .utf8)!. 

用途:

//Decode struct using JSONDecoder 
    let jsonDecoder = JSONDecoder() 
      do { 
       let modelResult = try jsonDecoder.decode(UserData.self,from: jsonExample2) 
       print("owner is \(String(describing: modelResult.owner)) - latitude is \(String(describing: modelResult.latitude)) - longitude is \(String(describing: (modelResult.longitude)))") 
      } catch { 
       print(error) 
      } 
関連する問題