如何在 alamofire multipartform 中发送数组参数?

Posted

技术标签:

【中文标题】如何在 alamofire multipartform 中发送数组参数?【英文标题】:How to send array parameter in alamofire multipartform? 【发布时间】:2021-12-28 02:08:07 【问题描述】:

我有一个数组,几个参数

var arr: [String] = [ "a", "b", "c", "d", "e"]
...

let parameters: [String: Any] = [
    "myArray" : self.arr,
    "text"    : self.text
    ...
]

我要上传

AF.upload(mutlipartFormData:  multipart in 
    for (key, value) in parameters 
        if key == "myArray" 
            // This code is problem
            for idx in value as! [String] 
            multipartFormData.append("\(idx)".data(using: .utf8, allowLossyConversion: false)!, withName: "\(key)")
                    
        
    

我尝试了该代码,它仅在 arr 中上传了 1 个元素。我要发送数组

【问题讨论】:

您需要使用分段上传吗?您描述的结构通常是 JSON 有效负载。 【参考方案1】:

您只需要将数组转换为 JSON 字符串。

var arr: [String] = [ "a", "b", "c", "d", "e"]
var strArr = ""
if let theJSONData = try? JSONSerialization.data(
    withJSONObject: arr,
    options: []) 
    let theJSONText = String(data: theJSONData,
                               encoding: .ascii)
    strArr = theJSONText ?? ""
    print("JSON string = \(theJSONText!)")



let param: [String: Any] = [
    "myArray" : strArr,
    "text"    : "text"
]
print(param)

        
Alamofire.upload(multipartFormData: 
    multipartFormData in
    for (key, value) in param 
        multipartFormData.append((value as AnyObject).data(using: String.Encoding.utf8.rawValue)!, withName: key)
    
, to: "apiurl", method: .post, encodingCompletion:  encodingResult in
    switch encodingResult 
    case .success(let upload, _, _):
        upload.responseJSON 
            response in
            print(response.result)
        
        

    case .failure(let encodingError):
            break
    
)        

【讨论】:

它发送字符串,我要发送数组【参考方案2】:

-->你可以像这样创建一个上传表单数据的函数

func makeFormDataAPICallDecodable<T: Codable>(url: String, params: [String: Any], objectType: T.Type,
                                                  success: @escaping(_ responseObject: T) -> Void,
                                                  failure: @escaping (_ error: String) -> Void) 
            // Almofire upload request
            AF.upload(multipartFormData:  multiPartData in
                for (key, value) in params 
                    if value is UIImage 
                        let img = (value as? UIImage)?.jpegData(compressionQuality: 0.5)
                        multiPartData.append(img!, withName: key, fileName: "img_\(name).jpeg", mimeType: "image/jpeg")
                     else if value is NSArray 
                        for childValue in value as? NSArray ?? [] 
                            if childValue is UIImage 
                                let img = (childValue as? UIImage)?.jpegData(compressionQuality: 0.5)
                                multiPartData.append(img!, withName: key, fileName: "profile_image.png", mimeType: "image/jpeg")
                            
                        
                     else if value is NSURL || value is URL 
                        do 
                            guard let pdf: URL = value as? URL else  return 
                            let name = pdf.lastPathComponent
                            let mimeType = pdf.mimeType()
                            let pdfData = try Data(contentsOf: pdf)
                            multiPartData.append(pdfData, withName: key, fileName: name, mimeType: mimeType)
                         catch  print(error) 
                     else 
                        if value is String || value is Int || value is Bool 
                            multiPartData.append("\(value)".data(using: .utf8)!, withName: key)
                        
                    
                
            , to: urlIs,method: .post, headers: headers).responseDecodable(of: FetchAPI<T>.self)  response in
                // preetify data
                if let data = response.data 
                    let str = data.prettyPrintedJSONString!
                    Logger.logResponse(ofAPI: "\(urlIs)", logType: .success, object: str)
                
                // response result
                switch response.result 
                case .success(let data):
                    // check auth token Exp condition
                    if data.statusCode == 401 
                        self.navigateToLogin()
                        return
                    
                    // check flag status
                    if data.flag!  success(data.data!)  else  failure(data.message!) 
                case .failure(let error):
                    failure("Something went wrong.")
                    Logger.log(logType: .error, object: error.localizedDescription)
                
            
         else  failure(ServerAPI.errorMessages.kNoInternetConnectionMessage) 
    

-> 你可以像这样使用它

let params: [String : Any] = [User.CodingKeys.userName.rawValue: data.name!,
                                      User.CodingKeys.email.rawValue: data.email!,
                                      User.CodingKeys.userRole.rawValue: data.userRole!,
                                      User.CodingKeys.phoneNumber.rawValue: data.phoneNumber!,
                                      kPassword: data.password!,
                                      User.CodingKeys.employeeID.rawValue: data.employeeId!,
                                      User.CodingKeys.departmentID.rawValue: data.department!,
                                      kDeviceType:1] // ["Key": value]

makeAPICallDecodable(url: ServerAPI.register, params: params, objectType: User.self, success: 
            response in
            print(response)
        , failure:  error in
            print(error)
        )

-> 参数objectData是你想要响应的对象是一个通用的

【讨论】:

以上是关于如何在 alamofire multipartform 中发送数组参数?的主要内容,如果未能解决你的问题,请参考以下文章

如何在 PlayGround 中安装 Alamofire

如何在 Alamofire 中实现自签名证书?

如何在 alamofire 中同步上传图片?

你如何在 Alamofire 5 中实现 RequestAdapter?

如何在 swift 中在 alamofire 中打印错误 html?

Alamofire 完成工作后如何加载视图?