【问题标题】:How can I post request with order of json in swift with alamofire?如何使用 alamofire 以 json 的顺序快速发布请求?
【发布时间】:2020-05-10 14:21:33
【问题描述】:

我的应用需要一种付款方式,并且我必须使用 JSON 数据发布请求以与 API 通信。一切对我来说似乎都是正确的。我在我的代码中找不到任何错误,但我认为 JSON 没有按顺序发布。这很重要吗?因为响应说失败,但我找不到其他任何东西。如果 JSON 顺序很重要,我该怎么做?我是 swift 新手,请帮助我。 这是我的代码:

 func mainRequestForPayment() {

      )

        let headers: HTTPHeaders = [
            "accept": "application/json",
            "content-type": "application/json",
            "authorization": "\(self.authValue)",
            "x-iyzi-rnd": "\(self.randomString)",
            "cache-control": "no-cache"
        ]


        let url = "MY_URL"

        let parameters: [String: Any] = [
        "locale": "tr",
        "conversationId": "123456789",
        "price": "1.1",
        "paidPrice": "1.1",
        "installment": 1,
        "paymentChannel": "WEB",
        "basketId": "B67832",
        "paymentGroup": "PRODUCT",
        "paymentCard": [
            "cardHolderName": "CARD_HOLDER_NAME",
            "cardNumber": "CARD_NUMBER",
            "expireYear": "CARD_YEAR",
            "expireMonth": "01",
            "cvc": "123",
            "registerCard": 0
        ],
        "buyer": [
            "id": "BY789",
            "name": "John",
            "surname": "Doe",
            "identityNumber": "74300864791",
            "email": "email@email.com",
            "gsmNumber": "+905350000000",
            "registrationAddress": "Nidakule Göztepe, Merdivenköy Mah. Bora Sok. No:1",
            "city": "Istanbul",
            "country": "Turkey",
            "zipCode": "34732",
            "ip": "85.34.78.112"
        ],
        "shippingAddress": [
            "address": "Nidakule Göztepe, Merdivenköy Mah. Bora Sok. No:1",
            "zipCode": "34742",
            "contactName": "Jane Doe",
            "city": "Istanbul",
            "country": "Turkey"
        ],
        "billingAddress": [
            "address": "Nidakule Göztepe, Merdivenköy Mah. Bora Sok. No:1",
            "zipCode": "34742",
            "contactName": "Jane Doe",
            "city": "Istanbul",
            "country": "Turkey"
        ],
        "basketItems": [
            [
                "id": "BI101",
                "price": "0.3",
                "name": "Binocular",
                "category1": "Collectibles",
                "category2": "Accessories",
                "itemType": "PHYSICAL"
            ],
            [
                "id": "BI102",
                "price": "0.5",
                "name": "Game code",
                "category1": "Game",
                "category2": "Online Game Items",
                "itemType": "VIRTUAL"
            ],
            [
                "id": "BI103",
                "price": "0.2",
                "name": "Usb",
                "category1": "Electronics",
                "category2": "Usb / Cable",
                "itemType": "PHYSICAL"
            ]
        ],
        "currency": "TRY"
            ]


        Alamofire.request(url, method: .post, parameters: parameters , encoding: JSONEncoding.default, headers: headers)
            .responseJSON { (response) in
                print(parameters)
                switch response.result {
                case .success(let value):
                    let swiftyJson = JSON(value)
                    print ("return as JSON using swiftyJson is: \(swiftyJson)")
                case .failure(let error):
                    print ("error: \(error)")
                }

        }


    }

我看不到我的错在哪里?还有什么方法可以在发布请求中下订单吗?谢谢大家。

我得到了回应:

return as JSON using swiftyJson is: {
  "conversationId" : "123456789",
  "locale" : "tr",
  "errorCode" : "1000",
  "status" : "failure",
  "systemTime" : 1579858355103,
  "errorMessage" : "Invalid signature"
}

【问题讨论】:

  • 您能否在此处发布您的示例 API 请求参数?
  • 参数字典的 order 无关紧要,因为字典无论如何都是无序的。
  • @HardikS 这些是我的示例请求参数。
  • @vadian Okey 如果订单对发布请求不重要,您能看到我关于该代码的错误吗?
  • 代码本身似乎是正确的,无论是标题(都是字符串插值变量非可选字符串吗?)或参数键和值可能是错误的。你得到什么错误?

标签: ios json swift xcode alamofire


【解决方案1】:

JSON 顺序通常并不重要,因为 JSON 规范并未将其定义为 JSON 对象的要求,但一些设计不佳的后端确实需要它。您确实需要检查正在与之通信的后端的要求。

此外,Swift 的 Dictionary 类型是任意排序的,并且该顺序可能会在您的应用程序运行之间以及用于编译代码的 Swift 版本之间发生变化。

最后,Swift 的 JSONEncoder 和 Apple 的 JSONSerialization 类型都无法要求严格的排序。最多,JSONSerialization 提供.sortedKeys 选项,这将为您提供有保证的(字母顺序)顺序,但它可能不是您声明参数的顺序。使用备用Encoder,如果您有Codable types(我推荐它而不是 SwiftyJSON),可能会给你更好的顺序保证,但你应该只关心它是否是你的后端的要求。

顺便说一句,我建议您为您的HTTPHeaders 值使用静态HTTPHeader 属性,而不是使用原始字符串,这样更方便。例如:

let headers: HTTPHeaders = [.accept("application/json"),
                            .contentType("application/json")]

【讨论】:

  • 我要问一个问题,我的json体有问题,对吗?
  • 这完全取决于您与之通信的服务器的要求。
【解决方案2】:

使用这个类

/////////////////////////////////////////////////// /p>

导入基础

导入 UIKit

导入 Alamofire

类 ServicesClass_New : NSObject {

var delegate : ServicesClassDelegate!

typealias CompletionBlock = (_ result : Dictionary<String, Any>?, _ error : Error?) -> Void
typealias CompletionDataBlock = (_ result : Data?) -> Void
typealias ProgressBlock = (_ progressData : Progress) -> Void

//MARK: Shared Instance

static let sharedInstance : ServicesClass = {
    let instance = ServicesClass()
    return instance
}()

static func getDataFromURlWith(url:String,parameters:Dictionary<String, Any>?, requestName:String,completionBlock : @escaping CompletionBlock)
{

    print("net available")
    Alamofire.request(url, method: .get, parameters: parameters, encoding: URLEncoding.default, headers: nil).responseJSON { (response) in

        switch(response.result) {
        case .success(_):
            if let data = response.result.value
            {
                //print(response.result.value!)
                //print(data)

                var dic : Dictionary<String,Any> = Dictionary()

                if data as? Array<Dictionary<String,Any>> != nil
                {
                    dic["data"] = data as? Array<Dictionary<String,Any>>
                    completionBlock(dic,nil)
                }
                else
                {
                    completionBlock(data as? Dictionary<String,Any>,nil)
                }
            }

            break

        case .failure(_):
            print(response.result.error!)
            completionBlock(nil ,response.result.error!)
            break

        }
    }

}

static func postDataFromURL(url:String,parameters:Dictionary<String, Any>?, requestName:String,completionBlock : @escaping CompletionBlock)
{
    print("net available")
    //application/json 
    //multipart/form-data
    let hders : HTTPHeaders = [ "Content-Type" : "application/json"] as [String : String]

    Alamofire.request(url, method: .post, parameters: parameters, encoding: JSONEncoding.default, headers: hders).responseJSON { response in

        switch(response.result) {
        case .success(_):
            if let dict = response.result.value
            {
                let data = dict as! Dictionary<String,Any>

                // print(response.result.value!)
                // print(data)
                completionBlock(data as Dictionary,nil)
            }

            break

        case .failure(let error):
            print((error as NSError).localizedDescription)
            completionBlock(nil ,response.result.error!)
            print("\(error.localizedDescription)")

            break

        }
    }
}

static func downloadFile(strUrl : String, progressBlock : @escaping ProgressBlock, completionBlock : @escaping CompletionDataBlock)
{
    let utilityQueue = DispatchQueue.global(qos: .utility)

    Alamofire.request(URL.init(string: strUrl)!).downloadProgress(queue: utilityQueue, closure: { (progress) in

        progressBlock(progress)
    })
        .responseData { (response) in

            if let data = response.result.value
            {
                completionBlock(data)
            }
            else
            {
                completionBlock(nil)
            }
    }

}

static func uploadData(url:String,parameters:Dictionary<String, Any>,requestName:String,arrImg:[UIImage],arrVideos:[URL],completionBlock : @escaping CompletionBlock)
{

    print("net available")

    let hders = [

        "Content-Type": "application/json"
    ]

    Alamofire.upload(multipartFormData:
        {
            MultipartFormData in

            for img in arrImg
            {
                let imageData = UIImageJPEGRepresentation(img , 0.8)!
                MultipartFormData.append(imageData, withName: "image" , fileName:"file\(index).jpg", mimeType:"image/jpeg")
            }

            index = 0
            for video in arrVideos
            {
                index = index + 1
                var videoData : Data = Data()
                do
                {
                    videoData = try Data.init(contentsOf: URL.init(fileURLWithPath: video.path))
                    MultipartFormData.append(videoData, withName: "video", fileName:"file\(index).mp4",mimeType: "video/mp4")
                }
                catch
                {

                }
            }
            for (key, value) in parameters
            {
                MultipartFormData.append((value as! String).data(using: String.Encoding.utf8)!, withName: key)
            }

    }, to:url,method:.post,headers:hders, encodingCompletion: {
        encodingResult in

        //["content-type" : "application/json"]
        switch encodingResult
        {
        case .success(let upload, _, _):
            print("image uploaded")
            upload.responseJSON { response in

                if let JSON = response.result.value
                {
                    print("JSON: \(JSON)")
                }

                if let dict = response.result.value
                {
                    let data = dict as! Dictionary<String,Any>

                    print(response.result.value!)
                    print(data)

                    completionBlock(data as Dictionary,nil)

                }
            }

            break

        case .failure(let encodingError):
            completionBlock(nil ,encodingError)
            break
        }
    } )

}

}

/// 在你想调用 API 的地方调用协议。 //有多种方法,例如:GET,POST ....

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2016-06-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-07-22
    • 2016-12-25
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多