お久しぶりです。最近プログラミング熱が熱いモノトーンです。
今日は Swift 4.1 以降で追加されている .convertFromSnakeCase
利用時における挙動について解説します。
import Foundation extension Decodable { static func decode(json data: Data) throws -> Self { let decoder = JSONDecoder() decoder.keyDecodingStrategy = .convertFromSnakeCase return try decoder.decode(Self.self, from: data) } }
のように,お手軽 JSON デコーダー環境を仕込むのは当たり前だと思います。
RxSwift を使いながら
guard let model = try? Model.decode(json: data) else { observer(.error(ClientError.invalidModel)) return } observer(.success(model))
のようにするのが理想かなーっと。ちなみに Model.decode(xml: Data)
みたいな API 生やせば色々なフォーマットにお手軽対応できるので,引数の json:
は必ず要求する設計にしています。
それは置いて置くとして,.convertFromSnakeCase
を使っているときの問題。プロパティー名を変更したいと思ったんだけど毎回エラーが発生するんですよね。どうやら仕組み上
.convertFromSnakeCase
にしたがって変換され,CodingKeys
に camel case の名前を用いて割り当てられる
というプロセスをたどっているらしいです。ですので,
⭕️
struct SampleEntity: Codable { let id: String let pageUrl: String let subPageUrl: String private enum CodingKeys: String, CodingKey { case id case pageUrl case subPageUrl = "pageUrl2" } }
って感じになると思います。CodingKeys
を使っているときは,camel case に変換されないと思って,
❌
struct SampleEntity: Codable { let id: String let pageUrl: String let subPageUrl: String private enum CodingKeys: String, CodingKey { case id case pageUrl = "page_url" case subPageUrl = "page_url2" } }
みたいな書き方をすると,一致する key がないとしてデコードに失敗する,っぽい。挙動をちゃんと確かめたわけじゃないので,アレですが……w 多分あってるかと。