使用普通Vanilla Swift消费JSON

在设计Web API时,传输介质与API的结构同样重要。 您可以使用XML,JSON,或者如果您穿的是大童裤,则可以使用SOAP。 首选使用JSON,因为它占用空间小,并且可以轻松映射到模型类。 在本文中,我们将探讨不使用任何JSON解析库而使用 JSON响应的不同方法。

让我们从简单而可爱的东西开始! 什么是简单可爱?

宠物小精灵!

我非常喜欢Pokemon,以至于我在Vapor中创建了服务器端Swift API,该API返回了Pokemons的数组。 您可以使用此链接签出API。

计划香草词典:

在第一种方法中,我们将以字典数组的形式使用JSON。 我们使用JSONSerialization类将返回的数据转换为适当的数据结构。 由于我们的JSON API返回了一个字典数组,我们使用[[String:Any]]作为目标数据结构类型。

使用字典的主要问题是键为字符串格式,并且可能会拼写错误。 另一个问题是,如果您使用密钥100个位置,然后又更改了密钥,则必须在所有这100个位置中更新密钥。 解决方案是使用可以表示JSON模型的具体类。

JSON模型类:

代替依赖于字符串键的字典,模型类是一个更好的选择,因为它们是强类型的,并且还提供了一次轻松修改属性的简便方法。 类定义如下所示:

现在,我们可以用以下代码替换字典代码:

比字典更好一点,但是现在我们的回调函数中有太多代码。 我们可以将初始化部分移到自定义Pokemon初始化程序中,如下所示:

这使我们的回调函数更加精简,如下所示:

看起来很棒! 但是我们还没有完成! for循环可以由Swift集合上可用的mapflatMap函数代替。

更好,更简洁!

我们也可以通过调用NSObject对象上可用的setValueForKeys函数来替换我们在init方法中手动执行的键-值映射部分。

由于setValuesForKeys对由Objective-C表示的类型使用键值编码,因此我们不能使用Double! 还是Double? 这就是为什么我们删除了可为空的类型,并使用一些默认值对其进行了初始化的原因。

使用setValueForKeys函数时要小心,因为找不到该键会引发异常。 如果您不受API的控制并且API的所有者以自己的格式发送回JSON,则可能是这种情况。 对于未在接收对象中找到的每个键,将触发未定义键的setValue。

嵌套的JSON:

目前,我们只研究了使用简单的JSON。 但是生活不是那么简单! 让我们看看如何使用嵌套的JSON结构。 我们将使用JSON PlaceHolder网站,该网站返回虚拟JSON数据。 您可以使用此链接查看我们将使用的JSON结构。

我们的用户JSON结构由以下子结构组成。

  • 用户数
  • 地址
  • 地缘
  • 公司

第一步是为每个结构创建自定义类,就像Pokemon初始化程序一样,创建一个将字典作为参数并填充所需属性的初始化程序。

用法如下所示:

而已!

在本文中,我们没有使用任何JSON解析库,而是依靠iOS框架中已经可用的API。 对于不返回复杂嵌套数据的简单应用程序,这很好,但是当您遇到更复杂的应用程序时,最好使用第三方库来帮助您解析JSON响应。

在下一篇文章中,我将介绍一些流行的JSON解析库,以及它们在使用复杂的JSON结构时如何使您的生活更轻松。