Is there any way to decode from Any type JSON Object using JSONDecoder?


(Masaki Haga) #1

Hi Swift-Users,

I was wondering if there is any way to decode JSON from Any type JSON
Object using `JSONDecoder`, not from Data type object.

Currently, `JSONDecoder` has only one decode function which decodes Data
type object to `Decodable`. Inside the function, it serializes Data object
to Any Type JSON Object using `JSONSerialization` and pass it into
`_JSONDecoder(referencing:, options:)` (Refer JSONEncoder.swift#874).

As discussed in some of other threads such as "SE-0166: Swift Archival &
Serialization", the default implementation of JSONDecoder or Decodable
protocol doesn’t allow to decode from one format to another format (such as
snake-case to camel-case), we need to implement custom CodingKey enums.
However, in our project, to parse the server API JSON response with
snake-case, declaring custom CodingKey enums for all the pre-existing
models is almost impossible and very inefficient, so I decided to covert
all the JSON keys from snake-case to camel-case, and then pass it into
`JSONDecoder.decode`. To achieve this, we need to convert the Data object
resulted from `URLSession.task` to Any type JSON Object using
`JSONSerialization`, do the conversion from snake-case to camel-case and
then convert back to Data type and then pass to `JSONDecoder.decode` which
looks very redundant because the function uses `JSONSerialization` inside
of it as mentioned above. If there is a function like below, we can get rid
of this redundant call of `JSONSerialization`.

func decode<T : Decodable>(_ type: T.Type, from JSONObject: Any) throws -> T

Sorry if I am misunderstanding the new API but is there any way to decode
`Decodable` directly from Any type JSON Object?

If not, I think adding the function aforementioned and giving an ability to
opt-out this JSON serialization call would give more flexibility to the API
in my humble opinion.

Thank you for reading.

All the best,
- Masaki