1

So here is my problem, I must upload an image in my swift application to a server that use rails. I got almost everything set up, except that the rails api must receive the file data in a variable document[:file]

here is the function I use to encode my image with alamofire:

static func getDocumentCreateUploadData(parameters: [String : AnyObject], imageData: NSData) -> (uploadData:NSMutableData, contentType:String) {
    let boundaryConstant = "NET-POST-boundary-\(arc4random())-\(arc4random())";
    let contentType = "multipart/form-data;boundary="+boundaryConstant

    let uploadData = NSMutableData()

    // add image
    uploadData.appendData("\r\n--\(boundaryConstant)\r\n".dataUsingEncoding(NSUTF8StringEncoding)!)
    uploadData.appendData("Content-Disposition: form-data; name=\"file\"; filename=\"file.png\"\r\n".dataUsingEncoding(NSUTF8StringEncoding)!)
    uploadData.appendData("Content-Type: image/png\r\n\r\n".dataUsingEncoding(NSUTF8StringEncoding)!)
    uploadData.appendData(imageData)

    // add parameters
    for (key, value) in parameters {
        uploadData.appendData("\r\n--\(boundaryConstant)\r\n".dataUsingEncoding(NSUTF8StringEncoding)!)
        uploadData.appendData("Content-Disposition: form-data; name=\"\(key)\"\r\n\r\n\(value)".dataUsingEncoding(NSUTF8StringEncoding)!)
    }
    uploadData.appendData("\r\n--\(boundaryConstant)--\r\n".dataUsingEncoding(NSUTF8StringEncoding)!)

    return (uploadData, contentType)
}

And then I call my api with

var imageParameters = [
     "documents": [
          "documentable_type": "Profile",
          "documentable_id": user.profile.id!
     ]
]
let data = Router.getDocumentCreateUploadData(imageParameters, imageData: imageData)
let urlRequest = Router.CreateDocument(contentType: data.contentType)
Alamofire.upload(urlRequest, data.uploadData).validate().responseSwiftyJSON({ (request, response, json, error) in
    if error != nil {
       ...

What I would like to know is how can I encode the image so that it respect the api specification.

{
    "documents" : {
        "file": the_file,
        "documentable_type": the_documentable_type,
        "documentable_id": the_documentable_id
    }
}

Is there a way to achieve this?

Thank in advance.

1 Answer 1

1

I simply misundertood the api, I didn't needed the root document in my upload call

All I needed to do was remove the document root but here is the way I did it :

    let imageParameters = [
        "documentable_type": "Comment",
        "organization_id": organizationId,
        "member_id": memberId,
        "user_id": user.id
    ]

    let uuid = NSUUID().UUIDString

    composeBarView.enabled = false
    ProgressHUDManager.uploadingStatus()

    Alamofire.upload(
        Router.CreateDocument,
        multipartFormData: { multipartFormData in
            multipartFormData.appendBodyPart(data: imageData!, name: "file", fileName: "\(uuid).jpg", mimeType: "image/jpeg")
            for (key, value) in imageParameters {
                multipartFormData.appendBodyPart(data: value.dataUsingEncoding(NSUTF8StringEncoding)!, name: key)
            }
        },
        encodingCompletion: { encodingResult in
            // Handle result
        }
    )

The API Evolved so the code is new but I hope it can help

Sign up to request clarification or add additional context in comments.

2 Comments

Could you upload the final code which worked for you?
@Rao here you go, I modified my answer so that you can see :)

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.