> ## Content Index
> Fetch the complete content index at: https://somekindofcode.com/llms.txt
> Use this file to discover other available public pages before exploring further.

# Codables: The Basics
- URL: https://somekindofcode.com/codables-the-basics/
- Published: 2019-04-28T06:04:00.000Z
- Updated: 2026-08-05T14:12:24.000Z
- Description: Codables are a very useful tool if you need to decode from or to different formats like JSON. Get your introduction into Codables here.
- Author: Christopher Beloch
- Tags: guide:codables, Swift, #Import 2026-07-17 02:07

It has been a long time we used stuff like `NSJSONSerialization` or `NSPropertyListSerialization` and dropped the `NS` prefix in favor of Swift. It helped converting data from or to JSON / Property List. Creating an instance of your model classes or serialize them to one of the formats would require writing a lot of additional code to convert the values to the correct data types.

Well, the time of these has come to an end and since Swift 4 we got a hand full of new protocols that allow the compiler to generate all the necessary code in the background. But we will still be able to customize the behaviours. More on that in a later chapter. Let us begin with the basics.

## The Protocols

There are only two (or three) protocols that you really have to care about: `Decodable` and `Encodable`. And `Codable`, but that is only a type alias for `Decodable & Encodable` so it is just a simpler annotation when you want a model do be de- and encodable.

### Decodable

This is the protocol when you want to decode data to your model. When you work with external Web-APIs which are JSON, you will most likely use `Decodable` to work with you model within your app.

### Encodable

For the serialization part, meaning you want to store your model data in a file or send it out to an API, `Encodable` is you protocol of choice. 

## Codable conformant types

Most of the data types you get from the Swift Standard Library are conformant to `Decodable` and `Encodable`. You can find a complete list in the [documentation provided by Apple](https://developer.apple.com/documentation/swift/decodable?ref=somekindofcode.com#conforming-types). I linked the conformant types for `Decodable`, but all of these types also work for Encodable.

As you can see, event objects like `CGPoint` and `CGSize` are listed and completly conform to the `Codable` protocol. But they are represented as an array of float values. `CGRect` is represented as an array of arrays with float values. This may not be the ideal way of representing the data, but it could be enough if you just want to store data in a local file instead of accessing a self-explaining API.

`Date` and `Data` are special snowflakes in the Codable space. At least if you want to use a JSONDe-/Encoder. These Coders special settings to modify the strategy on how a Date will be (de-)serialized. ISO-8601 formatted? UNIX timstamp? No problem at all. You can even add your own strategy. More on this in a later chapter.

## Example

*For convenience I will mostly use JSON in my examples because it is more readable than a full fledged property list.*

Lets take this product list as a short example to introduce you to Codables:

```swift
let jsonString = """
[{
  "title": "Awesome new Book",
  "price": 12.99,
  "currency": "EUR"
},{
  "title": "Fantastic Movie",
  "price": 9,
  "currency": "USD"
}]
"""

```

Our goal is to parse this data that can be extended in the future and work with a `Product` model within my app.

## Model

```swift
struct Product: Codable {
    let title: String
    let price: Double
}

```

Let us leave out the `currency` property at this step. We get back to it in a minute.

## Decode JSON

To decode our `jsonString`, we have to convert it to a `Data` object

```swift
let jsonData: Data = Data(jsonString.utf8)

```

*I'm doing it this way, because `jsonString.data(using: .utf8)` would result in an optional Data (`Data?`) type and I don't want to unwrap it and force unwraps are my most hated lines of code.*

As we use JSON in our example, we need a `JSONDecoder` that is happily provided by Swift. Most decoders have a simple `func decode(_:from:)` function.

```swift
let decoder = JSONDecoder()

do {
    let deserializedData = try decoder.decode(Array<Product>.self, from: jsonData)
} catch {
    print("Decoding Error", error)
}

```

`deserializedData` is now from type `Array<Product>` or `[Product]` if you like the later one more.

If the decoding fails, you'll get an error explaining what went wrong and where. Like a key that is missing or was the wrong data type.

## Recursive De-/Encoding

As I mentioned above, I left the currency value out of the model. Thats because I would like to implement this as an `enum`. You can add any other type to your model as they are recursively conformant to the same Codable protocols. This means that as our `Product` model is `Codable`, our enum has to be `Codable` as well.

## Enums

For an enum to be En- and/or Decodable, it has to have a raw value if we don't want to write the logics for (de)serializing the object. *We will come to that in a later, more advanced guide.* 

Lets add our currency enum:

```swift
struct Product: Codable {
    let title: String
    let price: Double
    let currency: Currency // added the property
}

enum Currency: String, Codable {
    case usDollar = "USD"
    case euro = "EUR"
}

```

This is it. We now have a `currency` property with an enum. One thing to notice: Any other value (like `"GBP"`) will cause the deserialization to fail! And the most sad part is that **it will also fail when** you set currency to be **an optional value**.

## Encode JSON

Encoding works just like decoding. Just instead of a `JSONDecoder` we use a `JSONEncoder`:

```swift
let encoder = JSONEncoder()
do {
    // deserializedData contains our Product array
    let serializedProductsData: Data = try encoder.encode(deserializedData)
    
    // Convert Data to String
    let serializedProductsString: String = String(data: serializedProductsData, encoding: .utf8)
} catch {
    print("Encoding Error", error)
}

```

At this stage we could also convert the data to a plist by using a `PropertyListEncoder`.

*Please note, that you'll lose all properties on the encoding side that hadn't been parsed on the decoding side. If you use the example without the* `currency` property, the encoding will drop that, too.

## Wrap it up

I hope you got a little insight in how to work with Codables without using any Frameworks or fancy code. We will get into it and dive a little deeper in the next guides around this topic and how to handle stuff like the enum issue above and how to work with annoying APIs that you can streamline a little bit with Codables.

I will explain how to write custom (de)serialization for your models and how to solve some issues that can occur.