A Swift App that Calls JSON Web Services

In this article I introduce a small iOS 8 app written in Swift, named SwiftPlaces. I wrote the app in order to get more experience with the language and try out some new features in iOS 8, such as Adaptive Layout.

The source code is available on GitHub.
https://github.com/ijoshsmith/swift-places

SwiftPlaces allows the user to search for places by postal code and then view details about a place, including its current weather. It is a universal app, meaning it runs on the iPad…

…and on the iPhone…

iPhone

I made use of the new support in iOS 8 for using UISplitViewController on the iPhone, as well as the iPad. Due to the Adaptive Layout features in iOS 8 it was only necessary to create one storyboard to cover both device types, which is great news!

There are too many bits and pieces I find interesting to review here, so I suggest you download the code from GitHub and check it out in Xcode 6. Here are a few things to keep an eye out for…

Web services

The app calls two Web services from www.geonames.org, namely postalCodeSearchJSON and findNearByWeatherJSON. I wrote a simple class that fetches JSON from a server, named JSONService. Both of the Web services listed above are consumed via that class, which provides closure-based completion handling and the ability to specify which NSOperationQueue the closures run on. Here is an example of fetching a list of places with a given postal code, taken from SearchViewController.

postal-code-search

The success closure uses my custom marshal operator function (~>) to move between a background thread and the main thread, as explained here. This allows the app to create data model objects out of JSON, eliminate duplicate entities, and sort them by name on a background thread, leaving the main thread to only display those objects in a UITableView.

Note: I realize that some postal codes include letters, but it seems that the geonames Web service that I’m using doesn’t support them. I didn’t investigate the matter more than a few failed attempts at using Canadian postal codes. A happy side effect of this is the fun way I show an error message if the user tries to search for something other than a number. Check out UISearchBar+ErrorMessage.swift for details.

JSON processing

I decided to write the JSON-to-model conversion code in Objective-C, because Swift’s type safety is at odds with such an inherently “type unsafe” task. There has been quite a lot of activity and debate around JSON processing in Swift, but I found it was just plain easier to write that code in Objective-C. The following code is from Model Builders.m:

There is quite a bit more to explore in the project, so I encourage you to grab the code and check it out. If you know of a better way to use Swift or iOS 8 features than what I’m doing, please tell me about it in a comment.

This entry was posted in iOS8, Swift. Bookmark the permalink.

8 Responses to A Swift App that Calls JSON Web Services

  1. Thanks for sharing Josh, the marshal operator looks really good in this context.

    Regarding JSON, it’s a real shame that you had to revert to Objective-C in order to avoid the raft of conversion and unwrapping required in Swift.

    When I hit a similar problem I opted to use the NSDictionary valueForKeyPath method to navigate to the location I required within the JSON model, then at that point cast the value to a strongly typed Swift object:

    https://github.com/ColinEberhardt/ReactiveSwiftFlickrSearch/blob/master/ReactiveSwiftFlickrSearch/Model/FlickrSearchImpl.swift#L36

    Something of a hybrid approach.

    I know there are quite a few Swift JSON libraries on GitHub, but this is the sort of problem I’d really like to solve for myself.

    • Josh Smith says:

      That seems like a reasonable approach to me. Navigating to the collection of interest using Swift got ugly fast, which is why I wrote that code in Objective-C. Maybe next time I’ll try your approach. Thanks Colin!

  2. Pingback: Dew Drop – July 30, 2014 (#1825) | Morning Dew

  3. Pingback: MarkdownLog - The Daily Six Pack: July 31, 2014

  4. Thanks for posting this example. It is really helpful to see a working code. Your work is appreciated!

  5. Mark Patterson says:

    Yay! I’ve finally seen this work. For a few days I was getting an NSURL something error. I was just gathering some data to post it all to you. But then it worked. It’s a neat little app.

    • Josh Smith says:

      That’s good news, Mark. Though I’m confused by this networking error you saw. A friend of mine also gets an error every time the app tries to make a network call. Did something change on your computer or network before the error went away?

Comments are closed.