简体   繁体   English

在 Swift 中将 socket.io 数据转换为 JSON

[英]Converting socket.io data to JSON in Swift

I'm writing a socket.io client and I'm having trouble getting the emitted data into any usable format.我正在编写socket.io客户端,但无法将发出的数据转换为任何可用格式。

My handler is:我的处理程序是:

socket.on("foriEvent") { data, ack in
    print(data)
}

which prints:打印:

[  
   {  
      "foriEvent":{  
         "eventType":"location",
         "state":"moving",
         "latitude":"60.4413407",
         "longitude":"22.2476208",
         "accuracy":"20",
         "ts":1510653600189
      }
   }
]

I have a Struct that "looks" like that data, and I would like to use something like this where the from object is of type Data .我有一个Struct是“看上去”像这些数据,我想用这样的事情,其中从对象类型的Data

let decoder = JSONDecoder()
let foriEvent = try decoder.decode(ForiEvent.self, from: data)

Currently I'm using the following to get a Data object, but when I send it to decoder.decode, I get the following error message:目前我正在使用以下内容来获取 Data 对象,但是当我将它发送到decoder.decode 时,我收到以下错误消息:

return try JSONSerialization.data(withJSONObject: json, options: JSONSerialization.WritingOptions.prettyPrinted)
 error trying to convert data to JSON typeMismatch(Swift.Dictionary<Swift.String, Any>, Swift.DecodingError.Context(codingPath: [], debugDescription: "Expected to decode Dictionary<String, Any> but found an array instead.", underlyingError: nil))

Could it be my struct?可能是我的结构吗? What should it look like?它应该是什么样子? The Struct looks like this right now:Struct现在看起来像这样:

struct ForiEvent : Codable {
    var eventType: String?
    var state : String?
    var latitude: String?
    var longitude : String?
    var accuracy : String?
    var timeStamp : CLong?
}

struct ForiData : Codable {
    var foriEvent : ForiEvent?
}

I use swiftyjson for this.我为此使用了 swiftyjson。 It does a great job.它做得很好。

You haven't defined what type the data is but if it is a string which it looks like it is from the print command that you have then you can do this.您还没有定义数据的类型,但如果它是一个字符串,它看起来像是来自您拥有的打印命令,那么您可以执行此操作。

    guard let dataFromString = data[0].data(using: String.Encoding.utf8, allowLossyConversion: false) else {return}
    var swiftyJson:JSON!
    do {
        swiftyJson = try JSON(data: dataFromString)
    } catch {
        print("Error JSON: \(error)")
    }

This will give you the data in JSON format which you can very easily parse using swiftyjson into the custom type you have outlined above.这将为您提供 JSON 格式的数据,您可以使用 swiftyjson 非常轻松地将其解析为您在上面概述的自定义类型。 The reason that Codable might not be working is because your JSON is returned as an array of JSON. Codable 可能无法正常工作的原因是您的 JSON 作为 JSON 数组返回。

Try this试试这个

let tempVar = swiftyJson["foriEvent"]["eventType"].string
print("test \(tempVar)") 

I think there is no need to implement any third party (BTW I'm not againsed to SwiftyJson or any other).我认为没有必要实施任何第三方(顺便说一句,我不反对 SwiftyJson 或任何其他)。 You can do it as:你可以这样做:

//Here is the new struct for your ForiEvent
struct ForiEvent {
var eventType: String?
var state : String?
var latitude: String?
var longitude : String?
var accuracy : String?
var timeStamp : CLong?

init(dict: [String:Any]) {
    if let obj = dict["eventType"] {
        eventType = "\(obj)"
    }

    if let obj = dict["state"] {
        state = "\(obj)"
    }

    if let obj = dict["latitude"] {
        latitude = "\(obj)"
    }

    if let obj = dict["longitude"] {
        longitude = "\(obj)"
    }

    if let obj = dict["accuracy"] {
        accuracy = "\(obj)"
    }

    if let obj = dict["timeStamp"] as? CLong {
        timeStamp = obj
    }
}
}

//You data as [[String:Any]] returend from on complitionhandler
let dictArray:[[String:Any]] = [[
"foriEvent":[
    "eventType" : "location",
    "state":"moving",
    "latitude":"60.4413407",
    "longitude":"22.2476208",
    "accuracy":"20",
    "ts":1510653600189
]
]
]

print(dictArray)


// How to Use it:
var foriEventArray = [ForiEvent]()
for eventData in dictArray {
if let eventDict = eventData["foriEvent"] as? [String:Any] {
    foriEventArray.append(ForiEvent(dict: eventDict))
}
}
print(foriEventArray)

Using SwiftyJSON is easiest way to handle json使用 SwiftyJSON 是处理 json 的最简单方法

Use this example使用这个例子

socket.on("foriEvent") { data, ack in
   // because 'data' is type of [Any] so we can use 'JSON.init(AnyObject)'
   let json:JSON = JSON(data[0])//JSON.init(parseJSON: cur)
    // variable json is ready for use as this json["foriEvent"]
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM