Ios 如何使用json上传图像?

Ios 如何使用json上传图像?,ios,swift,multipartform-data,nsurlsession,nsmutableurlrequest,Ios,Swift,Multipartform Data,Nsurlsession,Nsmutableurlrequest,我试图上传一个带有json数据的图像。我只是遵循并实现了这个机制。但是我得到了错误 { status code: 400, headers { "Cache-Control" = "no-cache, no-store, max-age=0, must-revalidate"; Connection = close; "Content-Language" = en; "Content-Length" = 1033; "Content-Type" = "te

我试图上传一个带有json数据的图像。我只是遵循并实现了这个机制。但是我得到了错误

{ status code: 400, headers {
    "Cache-Control" = "no-cache, no-store, max-age=0, must-revalidate";
    Connection = close;
    "Content-Language" = en;
    "Content-Length" = 1033;
    "Content-Type" = "text/html;charset=utf-8";
    Date = "Wed, 27 Jan 2016 10:44:34 GMT";
    Expires = 0;
    Pragma = "no-cache";
    Server = "Apache-Coyote/1.1";
    "X-Content-Type-Options" = nosniff;
    "X-XSS-Protection" = "1; mode=block";
} }`
下面是完整的HTTP请求

Content-Type: multipart/form-data;boundary=Boundary_123456789
Authorization: Basic bihdwbcIUkbcdwjnoNOn
User-Agent: Jersey/2.21.1 (HttpUrlConnection 1.8.0_45)
MIME-Version: 1.0
Host: localhost:8080
Accept: text/html, image/gif, image/jpeg, *; q=.2, */*; q=.2
Connection: keep-alive
Content-Length: 3526

--Boundary_123456789
Content-Type: application/json
Content-Disposition: form-data; name="userDTO"

{"id":"id","name":"name","age":23}
--Boundary_123456789
Content-Type: image/png
Content-Disposition: form-data; filename="sample-image2.png"; modification-date="Fri, 22 Jan 2016 04:56:48 GMT"; size=3308; name="file"

‰PNG

<Binary data>

--Boundary_123456789—
还有扩展

extension NSMutableData {

    func appendString(string: String) {
        let data = string.dataUsingEncoding(NSUTF8StringEncoding, allowLossyConversion: true)
        appendData(data!)
    }
}

我想我在json格式上犯了一些错误。有人能帮忙吗?谢谢

此代码片段将帮助您使用POST方法将UIImage文件上载到web服务

func uploadImageOne(){
    var imageData = UIImagePNGRepresentation(exampleImageView.image)

    if imageData != nil{
        var request = NSMutableURLRequest(URL: NSURL(string:"Your URL")!)
        var session = NSURLSession.sharedSession()

        request.HTTPMethod = "POST"

        var boundary = NSString(format: "---------------------------14737809831466499882746641449")
        var contentType = NSString(format: "multipart/form-data; boundary=%@",boundary)
      //  println("Content Type \(contentType)")
        request.addValue(contentType, forHTTPHeaderField: "Content-Type")

        var body = NSMutableData.alloc()

        // Title
         body.appendData(NSString(format: "\r\n--%@\r\n",boundary).dataUsingEncoding(NSUTF8StringEncoding)!)
        body.appendData(NSString(format:"Content-Disposition: form-data; name=\"title\"\r\n\r\n").dataUsingEncoding(NSUTF8StringEncoding)!)
        body.appendData("Hello World".dataUsingEncoding(NSUTF8StringEncoding, allowLossyConversion: true)!)

        // Image
        body.appendData(NSString(format: "\r\n--%@\r\n", boundary).dataUsingEncoding(NSUTF8StringEncoding)!)
        body.appendData(NSString(format:"Content-Disposition: form-data; name=\"profile_img\"; filename=\"img.jpg\"\\r\n").dataUsingEncoding(NSUTF8StringEncoding)!)
        body.appendData(NSString(format: "Content-Type: application/octet-stream\r\n\r\n").dataUsingEncoding(NSUTF8StringEncoding)!)
        body.appendData(imageData)
        body.appendData(NSString(format: "\r\n--%@\r\n", boundary).dataUsingEncoding(NSUTF8StringEncoding)!)



        request.HTTPBody = body


        var returnData = NSURLConnection.sendSynchronousRequest(request, returningResponse: nil, error: nil)

        var returnString = NSString(data: returnData!, encoding: NSUTF8StringEncoding)

        println("returnString \(returnString)")

    }


}

看来,上传图片不是你的问题-据我所知,它成功了。您应该意识到,上传图像与JSON无关。相反,获得预期格式(JSON)的响应可能是您所寻求的。因此,如果您需要获取一个主体为JSON的响应,那么应该通过设置适当的
Accept
头来明确说明这一点。例如:

Accept:application/json

在代码中:

request.setValue("application/json", forHTTPHeaderField: "Accept")
当您收到响应时,还应首先检查响应的状态代码,然后检查
内容类型
标题(分别是响应的
MIMEType
属性),该标题应与您期望的内容相匹配:
application/json

如果内容类型不是您所期望的,您也可以尝试其他“响应序列化程序”——每个都适合解析其他内容类型,例如
text/plain
等,如您所愿

编辑:

服务器以提示响应,表示多部分请求的第二部分格式不正确。看看它是如何组成的:

        body.appendString("--\(boundary)\r\n")
        body.appendString("Content-Type: \(mimetype)\r\n\r\n")
        body.appendString("Content-Disposition: form-data; filename='sample-image23.png'; modification-date='Fri, 22 Jan 2016 04:56:48 GMT'; size=3308; name='file'\r\n")
        body.appendData(data)
        body.appendString("\r\n")
现在,仔细观察,我们可以看到第二个标题
Content Type
将用两个
CRLF
分隔-但后面还有另一个标题。标题应仅用一个
CRLF
分隔

然后,最后一个标题必须用两个
CRLF
分隔

建议修复:

        body.appendString("--\(boundary)\r\n")
        body.appendString("Content-Disposition: form-data; filename='sample-image23.png'; modification-date='Fri, 22 Jan 2016 04:56:48 GMT'; size=3308; name='file'\r\n")
        body.appendString("Content-Type: \(mimetype)\r\n\r\n")
        body.appendData(data)
        body.appendString("\r\n")
(编辑:删除不正确的描述)

编辑2:

在这一行的上方,这些行中还缺少一个
CRLF

let key = "userDTO"

body.appendString("--\(boundary)\r\n")
body.appendString("Content-Type: application/json")
body.appendString("Content-Disposition: form-data; name=\"\(key)\"\r\n\r\n")
你看到问题了吗<代码>内容类型没有尾随
CRLF


另请参见:

请添加返回错误的代码行。我已确定这是一个JSON解析错误。但是图像无法上传。@iOS您所说的有或有很多不明确之处:您声明这是一个解析错误,但您没有在代码中提到这种情况发生的地方(您有两次可能发生这种情况)。然后您声明,您的上传失败,但您已经发布了请求日志,这表明请求确实成功。因此,您应该首先澄清这些问题,可能会记录您收到的错误和响应。@这意味着“由于语法错误,服务器无法理解该请求。客户端不应在未经修改的情况下重复该请求。”。所以,你的身体可能是畸形的。当您尝试手动设置多部分请求时,这很容易发生。如果仔细查看底部的请求日志,您会看到
--Boundary\u 123456789-
。但是,最后的分隔符应该是
---
,在代码中,它似乎是正确的。但这可能是对罪犯的一种指示。@iOS在获取指示错误的状态代码(例如400)时,服务器可能不会以您请求的MIME类型发送响应(例如,
application/json
。它经常以
text/html
的形式发送此消息。因此,您的json解析器将无法将响应正文解析为json。您看到了吗?非常感谢。再添加一个CRFL修复了此问题。
body.appendString(“内容类型:image/png\r\n\r\n”)
您的最终边界不正确。这可能会导致服务器完全拒绝您的请求。此外,您正在使用现已弃用的
NSURLConnection
。您建议使用同步表单来发出请求,但强烈不鼓励这样做。
let key = "userDTO"

body.appendString("--\(boundary)\r\n")
body.appendString("Content-Type: application/json")
body.appendString("Content-Disposition: form-data; name=\"\(key)\"\r\n\r\n")