通过 PHP 将来自 MySQL 的 JSON 解码为 SwiftUI 中的复杂结构
Posted
技术标签:
【中文标题】通过 PHP 将来自 MySQL 的 JSON 解码为 SwiftUI 中的复杂结构【英文标题】:Decoding JSON coming from MySQL via PHP to a complex Struct in SwiftUI 【发布时间】:2021-12-31 13:24:27 【问题描述】:我通过 php 从 mysql 数据库获得了这个 JSON 文件:
[
"id":1,
"partner":
"id":1,
"name":"Migros Bank",
"image":"migrosbank"
,
"name":"Testkonto 1",
"type":"bank",
"iban":"CH12 1234 1234 1234 1234 1",
"datapoints":[
"id":1,
"depot_id":1,
"date":"2021-12-28",
"amount":5811.490234375
,
"id":2,
"depot_id":1,
"date":"2021-12-29",
"amount":7736.89013671875
]
,
"id":2,
"partner":
"id":1,
"name":"Migros Bank",
"image":"migrosbank"
,
"name":"Testkonto 2",
"type":"bank",
"iban":"CH12 1234 1234 1234 1234 2",
"datapoints":[
"id":3,
"depot_id":2,
"date":"2021-12-28",
"amount":500
,
"id":4,
"depot_id":2,
"date":"2021-12-29",
"amount":1500
]
]
在 SwiftUI 中,我尝试将其解码为一个名为 Depot 的自定义结构,该结构由自定义结构 Partner 的一个实例和自定义结构 Depotstand 的一组实例组成:
import Foundation
import SwiftUI
struct Partner: Hashable, Codable, Identifiable
var id: Int
var name: String
var image: String
var imageName: Image
Image(image)
struct Depotstand: Hashable, Codable, Identifiable
var id: Int
var depot_id: Int
var date: Date
var amount: Double
struct Depot: Hashable, Codable, Identifiable
var id: Int
var partner: Partner
var name: String
var type: String
var iban: String
var datapoints: [Depotstand]
我添加了一个数据模型,从我的网络服务器获取 JSON 数据 - 这部分工作正常 - 然后我尝试将数据解码到自定义结构 Depot,但失败(如果我简化,它可以工作将 JSON/struct 转换为仅简单的 Depot 结构,而不依赖于 Partner 和 Depotstand 实例):
import Foundation
final class ModelDataDepot: ObservableObject
@Published var depots = [Depot]()
init()
let url = URL(string: "https://api.webcoders.ch/index.php")!
URLSession.shared.dataTask(with: url) (data, response, error) in
do
if let data = data
let decodedData = try JSONDecoder().decode([Depot].self, from: data)
DispatchQueue.main.async
self.depots = decodedData
else
print("No Data!")
catch
print("JSON-Error: \(error)")
.resume()
这是我得到的错误,主要包含数据类型错误,但我不知道如何解决这个问题:
JSON-Error: typeMismatch(Swift.Double, Swift.DecodingError.Context(codingPath: [_JSONKey(stringValue: "Index 0", intValue: 0), CodingKeys(stringValue: "datapoints", intValue: nil), _JSONKey(stringValue: "Index 0", intValue: 0), CodingKeys(stringValue: "date", intValue: nil)], debugDescription: "Expected to decode Double but found a string/data instead.", underlyingError: nil))
我已经尝试了一些不同的数据转换,甚至使用 Numberformatters 等,但我无法让它工作......我还检查了 this article 关于将 JSON 数据转换为复杂的 swift 结构,但我无法解决我的问题。
感谢您帮助我!
P.s:我是 SwiftUI 和移动开发的绝对初学者...我的编码背景主要是 PHP、PowerShell 等,所以请耐心等待。 :-)
【问题讨论】:
将var date: String
更改为Depotstand
正如@workingdog 所指出的,json 解码不支持日期。 SO上有一些关于这个的其他线程。
【参考方案1】:
你可以用var date: Date
试试这个:
final class ModelDataDepot: ObservableObject
@Published var depots = [Depot]()
let dataDateFormat: DateFormatter =
let formatter = DateFormatter()
formatter.dateFormat = "yyyy-MM-dd"
return formatter
()
init()
let url = URL(string: "https://api.webcoders.ch/index.php")!
URLSession.shared.dataTask(with: url) (data, response, error) in
do
if let data = data
let decoder = JSONDecoder()
decoder.dateDecodingStrategy = .formatted(self.dataDateFormat) //<-- here
let decodedData = try decoder.decode([Depot].self, from: data)
DispatchQueue.main.async
print("\n-----> decodedData: \(decodedData) \n")
self.depots = decodedData
else
print("No Data!")
catch
print("JSON-Error: \(error)")
.resume()
struct Depotstand: Hashable, Codable, Identifiable
var id: Int
var depot_id: Int
var date: Date
var amount: Double
【讨论】:
谢谢。不知道这种可能性。 @workingdog 非常感谢您的帮助!它现在工作正常。 :-)以上是关于通过 PHP 将来自 MySQL 的 JSON 解码为 SwiftUI 中的复杂结构的主要内容,如果未能解决你的问题,请参考以下文章
将 JSON 编码的 PHP 变量传递给 HighCharts
MySQL 数据从 PHP 到带有 JSON 的 Javascript
使用 php 在 5 秒内将数据保存到 MySQL [关闭]
来自 php mysql 的 Highcharts 钻取 json