• This repository has been archived on 25/Aug/2019
  • Stars
    star
    386
  • Rank 108,906 (Top 3 %)
  • Language
    Swift
  • License
    MIT License
  • Created almost 8 years ago
  • Updated about 6 years ago

Reviews

There are no reviews yet. Be the first to send feedback to the community and the maintainers!

Repository Details

Micro framework for easily parsing JSON in Swift with rich error messages in less than 100 lines of code

JSON

Version Build Status Swift Version Carthage compatible

Micro framework for easily parsing JSON in Swift with rich error messages in less than 100 lines of code.

infomercial voice 🎙 Are you tried of parsing JSON and not knowing what went wrong? Do you find complicated frameworks with confusing custom operators a hassle? Are you constantly wishing this could be simpler? Well now it can be, with JSON! Enjoy the Simple™

Usage

Let’s say we have a simple user struct:

struct User {
    let name: String
    let createdAt: Date
}

Deserializing Attributes

We can add JSON deserialization to this really easily:

extension User: JSONDeserializable {
    init(json: JSON) throws {
        name = try json.decode(key: "name")
        createdAt = try json.decode(key: "created_at")
    }
}

(JSON is simply a typealias for [String: Any].)

Notice that you don’t have to specify types! This uses Swift generics and pattern matching so you don’t have to worry about this. The interface for those decode functions look like this:

func decode<T: JSONDeserializable>(key: String) throws -> T
func decode<T: JSONDeserializable>(key: String) throws -> [T]
func decode(key: String) throws -> Date
func decode(key: String) throws -> URL

There’s a specialized verion that returns a Date. You can supply your own functions for custom types if you wish.

Here’s deserialization in action:

let json = [
    "name": "Sam Soffes",
    "created_at": "2016-09-22T22:28:37+02:00"
]

let sam = try User(json: json)

Optional Attributes

Decoding an optional attribute is easy:

struct Comment {
    let body: String
    let publishedAt: Date?
}

extension Comment {
    init(json: JSON) throws {
        body = try json.decode(key: "body")

        // See how we use `try?` to just get `nil` if it fails to decode?
        // Easy as that!
        publishedAt = try? json.decode(key: "published_at")
    }
}

Deserializing Nested Dictionaries

Working with nested models is easy. Let’s say we have the following post model:

struct Post {
    let title: String
    let author: User
}

extension Post: JSONDeserializable {
    init(json: JSONDictionary) throws {
        title = try json.decode(key: "title")
        author = try json.decode(key: "author")
    }
}

We can simply treat a nested model like any other kind of attribute because there’s a generic function constrainted to JSONDeserializable and User in our example conforms to that.

Deserializing Enums

Enums that are RawRepresentable, meaning they have an underlying type and no associated values, will deserialize with any additional work! Let’s say we have the following enum:

enum RelationshipStatus: String {
    case stranger
    case friend
    case blocked
}

We could simply deserialize it like this assuming our User example earlier now has a property for it:

let json = [
    "name": "Sam Soffes",
    "created_at": "2016-09-22T22:28:37+02:00",
    "releationship_status": "friend"
]

extension User: JSONDeserializable {
    init(json: JSON) throws {
        name = try json.decode(key: "name")
        createdAt = try json.decode(key: "created_at")
        relationshipStatus = try json.decode("relationship_status")
    }
}

If your enum isn’t RawRepresentable, see the next section for providing a custom decode method for it.

Deserializing Custom Types

You can also define custom decode function for custom types very easily. We’ll use TimeZone as an example:

extension Dictionary where Key : StringProtocol {
    func decode(key: Key) throws -> TimeZone {
        // Get the JSON representation of it. Here, it’s a string.
        let string: String = try decode(key: key)

        // Initialize TimeZone with the identifier you decoded already.
        guard let timeZone = TimeZone(identifier: string) else {
            throw JSONDeserializationError.invalidAttribute(key: String(key))
        }

        return timeZone
    }
}

Then you can do try json.decode(key: "timezone") like normal and it will throw the appropriate errors for you or decode a valid TimeZone value.

How cool is that‽

More Repositories

1

SAMKeychain

Simple Objective-C wrapper for the keychain that works on Mac and iOS
Objective-C
5,397
star
2

sstoolkit

A collection of well-documented iOS classes for making life easier
Ruby
3,320
star
3

cheddar-ios

Cheddar for iOS
Objective-C
3,005
star
4

Countdown

Mac screensaver for counting down to a date
Swift
959
star
5

RateLimit

Simple utility for only executing code every so often.
Swift
919
star
6

SSPullToRefresh

Simple and highly customizable pull to refresh view
Objective-C
886
star
7

Clock.saver

Simple clock screensaver written in Swift
Swift
794
star
8

HotKey

Simple global shortcuts in macOS
Swift
759
star
9

GradientView

Easily use gradients in UIKit for iOS & tvOS
Swift
626
star
10

Motivation

Mac screen saver that terrifyingly shows your age
Swift
558
star
11

SyntaxKit

TextMate-style syntax highlighting
Swift
469
star
12

ssdatakit

Eliminate your Core Data boilerplate code
Objective-C
454
star
13

Crypto

Swift CommonCrypto wrapper
Swift
329
star
14

hue

Work with Philips Hue from Ruby
Ruby
311
star
15

ssmessagesviewcontroller

iOS Messages.app style table view controller
Objective-C
283
star
16

X

Easier cross platform Mac & iOS development with Swift
Swift
278
star
17

cheddar-mac

Cheddar for Mac
Objective-C
256
star
18

valio

Valio Con 2014 Schedule
Swift
255
star
19

cheddarkit

Objective-C framework that powers Cheddar for iOS and Cheddar for Mac
Objective-C
239
star
20

ISO8601

ISO8601 date parser and writer
Swift
220
star
21

Cache

Swift caching library
Swift
212
star
22

sscatalog

Deprecated demo of SSToolkit
Objective-C
195
star
23

SAMTextView

Add a placeholder to UITextView.
Objective-C
194
star
24

SAMCategories

A collection of useful Foundation and UIKit categories.
Objective-C
179
star
25

SAMBadgeView

Simple badge view for iOS
Objective-C
179
star
26

bully

Simple Pusher Objective-C client
Objective-C
172
star
27

coins

Bitcoin value tracker
Swift
165
star
28

Color

Color utilities for macOS, iOS, tvOS, and watchOS
Swift
156
star
29

quesadilla

Entity-style text parsing
Ruby
143
star
30

SAMSoundEffect

Play a sound effect
Objective-C
135
star
31

unmarkdown

Convert HTML to Markdown. Sometimes you just need to go the other way.
Ruby
132
star
32

WhatColorIsIt

Time of day as a color as a Mac screen saver
Swift
127
star
33

Diff

Simple diff library in pure Swift
Swift
120
star
34

soff.es

My old website
CSS
95
star
35

apple_push_notification

Rails plugin for Apple Push Notifications
Ruby
94
star
36

Mixpanel

Unofficial Swift Mixpanel client
Swift
93
star
37

contrast

Contrast for macOS
Swift
90
star
38

awfulrecruiters.com

Previously, a list of third-party recruiter domains
CSS
89
star
39

CommonCrypto

CommonCrypto Swift module
89
star
40

markdownr.com

A nifty markdown notepad
Ruby
89
star
41

Canvas

Hacking on the remains of Canvas. Nothing to see yet.
Swift
86
star
42

ssoauthkit

Handy iOS library for connecting to OAuth 1.0 providers and working with Twitter authentication
Objective-C
84
star
43

bar

My Cocktail Menu
Swift
77
star
44

lagunitas

A Ruby gem for inspecting iOS IPAs
Ruby
71
star
45

grater

CSS grids as easy to use as a cheese grater
Ruby
69
star
46

sspersonviewcontroller

Clone of Apple's ABPerson view controller in AddressBookUI.framework to allow for better customization.
Objective-C
68
star
47

sstableviewcell

A fast table view cell based on ABTableViewCell
Objective-C
66
star
48

SAMCircleProgressView

Determinate, circular progress view.
Objective-C
66
star
49

dotfiles

~soffes
Shell
62
star
50

ZoomIn

Safari extension for opening Zoom right away
Swift
61
star
51

SAMCoreImageView

Fast image view for CIImage's
Objective-C
58
star
52

json-benchmarks

Benchmarks of various JSON frameworks on iOS
Objective-C
58
star
53

spotlight-tools

Spotlight Tools for macOS
Swift
57
star
54

SAMCubicSpline

Cubic splines made easy.
Objective-C
57
star
55

SAMWebView

Push UIWebView to its limits
Objective-C
55
star
56

Pugs

Simple pug photo viewer for iOS
Swift
51
star
57

SAMTextField

Handy UITextField additions like insetting text.
Objective-C
50
star
58

ssindicatorlabel

Label + indicator
Objective-C
48
star
59

SharedWebCredentials

Swift library for easily working with Shared Web Credentials for iOS
Swift
48
star
60

sublime

My Sublime Text 3 configuration
47
star
61

words

Example Thesaurus app written in Swift
Swift
47
star
62

soffes.blog

Jekyll but more complicated than it needs to be because reasons
Ruby
46
star
63

playground

A simple Ruby gem for converting Markdown into Swift playgrounds
CSS
46
star
64

MarkdownKit

Fancy Markdown input with TextKit powered by CommonMark
C
43
star
65

home

Home Assistant configuration
YAML
42
star
66

binary_plist

Easily add the Apple Binary Plist format to your Rails controllers
Ruby
42
star
67

SAMLabel

A simple subclass of UILabel with vertical alignment and text insets.
Objective-C
40
star
68

whisky-fire

A glorious screen saver of Nick Offerman drinking whisky
Swift
35
star
69

findi

Find your iPhone through Apple's API's.
Ruby
33
star
70

coins-android

Coins for Android
Java
30
star
71

pizzazz

A simple, pure Ruby implementation of JSON code coloring
Ruby
30
star
72

universal-ipad-iphone-example

Example universal iPad/iPhone app
Objective-C
30
star
73

no-itunes

Joke invisible app to kill iTunes as soon as it launches
Swift
27
star
74

iphone-plist

iPhone plist tutorial
Objective-C
27
star
75

SAMContentMode

UIContentMode & CGRect Maths
Objective-C
27
star
76

fat

I'm fat.
JavaScript
24
star
77

SAMLoadingView

Simple loading views
Objective-C
20
star
78

Snake

Snake implemented in SwiftUI for macOS
Swift
19
star
79

Heads

Bust out of windows prototype
Swift
18
star
80

k-and-r

Code examples and exercises from the K&R
C
18
star
81

hire

Hire Me
CSS
17
star
82

SAMHUDView

Kinda okay HUD for iOS.
Objective-C
16
star
83

hands

Simple Poker Gem
Ruby
16
star
84

blog

Content for my blog
Ruby
16
star
85

useshares.com

Website for Shares iPhone app
CSS
15
star
86

tweets

All of my tweets.
JavaScript
14
star
87

tweets-from

Simple iPhone application using MapKit to visualize Twitter timeline locations.
Objective-C
14
star
88

shares-support

Supporting Files & Artwork for Shares
Ruby
14
star
89

van

Home Assistant configuration for my van
JavaScript
13
star
90

tomatomovies

Simple tweets when good new movies hit the theaters with their rating.
Ruby
13
star
91

SAMAddressBar

Clone of Safari's address bar from long ago.
Objective-C
13
star
92

sstoolk.it

SSToolkit Website
Ruby
13
star
93

langtons-ant

Langton’s Ant macOS screen saver written in Swift
Swift
12
star
94

samandellen.com

This is our little website
HTML
12
star
95

wwdchike.com

June 12th, 2016 — 2pm at Lands End
HTML
12
star
96

usewhiskey.com

Whiskey Website
SCSS
12
star
97

discover

Ruby Gem for discovering UPNP devices with SSDP
Ruby
11
star
98

shares-l10n

Localization files for Shares
Ruby
11
star
99

getcoinsapp.com

Website for Coins
CSS
11
star
100

private-json-test

JSON parsing example with private iPhone frameworks
Objective-C
9
star