如何在Alamofire multipart上传中发送字符串数组[String]和字符串(多种类型)的参数?

时间:2018-03-23 10:39:00

标签: ios swift alamofire

我正在使用alamofire分段上传进行网络通话,其中我发送的图像数据和参数是关键值对。但是,值可以是String类型或[String]。它是有效的,如果所有参数都是String,但当参数键的类型为[String]时崩溃。这是我的代码:

func childSignUpWithParameters(data:Data?,_ parameters: Parameters,
                             completion: @escaping (Bool, User?, Any?)->Void) {
  let accessToken = "JWT" + " " + (UserDefaults.standard.value(forKey: UserDefaultsKeys.kAuthToken.rawValue) as! String)
  let headers_ =
    ["Authorization": accessToken]
  let url = BaseUrl + APIPathGenerator.addChild.rawValue
  Alamofire.upload(multipartFormData: { (mpData) in
//to add parameters
    for (key, value) in parameters {
      mpData.append((value as! String).data(using: .utf8)!, withName: key)
    }

//to add image data:
    if let image = data {
      mpData.append(image,
                    withName: "image",
                    fileName: "file.jpeg",
                    mimeType: "image/jpeg")
    }
  }, usingThreshold: UInt64.init(),
     to: url,
     method: .post, headers: headers_, encodingCompletion: { (encodingResult) in
      switch encodingResult {
      case .success(let upload, _, _):

所以问题在于:

   mpData.append((value as! String).data(using: .utf8)!, withName: key)

对于字符串数组,我们不能强制将其强制转换为String。此外,如果我不强制施放它我得到错误,类型Any的值没有成员数据。没有.data我在.utf8中得到错误。

3 个答案:

答案 0 :(得分:2)

mpData.append((value as! String).data(using: .utf8)!, withName: key)

使用(value as! String)您告诉编译器您100%确定valueString。显然情况并非如此,因为你说它也可以是[String]。您必须以某种方式将该数组编码为Data对象。现在很难向您提出任何建议,因为正确的解决方案取决于服务器期望数据编码的方式。但也许我能够指出你正确的方向。

例如,让我们考虑一下这个字符串数组:

let array = ["a", "b"]

如果应该发送:

["a", "b"]

您可以简单地使用:

mpData.append("\(value)".data(using: .utf8)!, withName: key)

但是,如果您需要对其进行编码,请说:

a, b

然后你必须自己做一些编码:

if let stringValue = value as? String {
    mpData.append(stringValue.data(using: .utf8)!, withName: key)
} else if let arrayString = value as? [String] {
    let stringValue = arrayString.joined(separator: ", ")
    mpData.append(stringValue.data(using: .utf8)!, withName: key)
}

答案 1 :(得分:1)

将参数类型更改为parameters: [String : Any]并附加您的值,如:

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

通话:

self.childSignUpWithParameters(data: /*yourData*/, parameters: self.getParameters(), ...

func getParameters() -> [String: Any]{
    let params = ["key2": "value1",
                  "key1": "value2"
    return params
}

使用Any你不需要为特定类型烦恼,无论你发送什么值,它都会在循环中使用强制转换\(value)"成功地运送到服务器。

答案 2 :(得分:0)

请尝试使用此代码..

func CompleteShipmentAPI(){

        let imgData = UIImageJPEGRepresentation(signatureImageView.image!, 0.25)!

        let ShipID:NSNumber =  mdicShipmentDetails.value(forKey: "id") as! NSNumber

        // userDetails
        let paramerers:Parameters = ["ship_id":ShipID.stringValue]

        print(paramerers)

        MBProgressHUD.showAdded(to: self.view, animated: true)

        let headers: HTTPHeaders = [
            "x-api-key": AUTH_API_KEY
        ]
        let isImageOnProducts:NSNumber = mdicShipmentDetails.value(forKey: "isImageOnProducts") as! NSNumber
        let isDigitalSignature:NSNumber = mdicShipmentDetails.value(forKey: "isDigitalSignature") as! NSNumber

        Alamofire.upload(multipartFormData: { multipartFormData in
            if isImageOnProducts.stringValue == "1"{
                //SHOW
                 multipartFormData.append(imgData, withName: "product_img",fileName: "product.jpg", mimeType: "image/jpg")
            }
            if isDigitalSignature.stringValue == "1"{
                //SHOW
                multipartFormData.append(imgData, withName: "shipment_sign",fileName: "signature.jpg", mimeType: "image/jpg")
            }

            for (key, value) in paramerers {
                multipartFormData.append((value as AnyObject).data(using: String.Encoding.utf8.rawValue)!, withName: key )
            }
        },to:BASE_URL+kPOST_COMPLETE_API, headers:headers){ (result) in
            switch result {
            case .success(let upload, _, _):

                upload.uploadProgress(closure: { (progress) in
                    print("Upload Progress: \(progress.fractionCompleted)")
                })

                upload.responseString { response in

                    MBProgressHUD.hide(for: self.view, animated: true)

                    if let strResponse:String  = response.result.value  {
                        print(strResponse)



                    }

                }

            case .failure(let encodingError):
                print(encodingError)
                MBProgressHUD.hide(for: self.view, animated: true)
            }
        }
    }