Multer & SwiftHTTP

Uploading Swiftly to Node.JS

For a small demo app I was building, I needed to upload a file from my app to my server to be saved locally. Straight forward, especially since this was just for a demo. What was frustrating though is I realized that trying to do this quickly with built-in code on both ends felt like it took way more than I wanted to get into (granted, never really did this before with these platforms so there’s that, too, I suppose).

So a few searches later, I came across two tools that simplified it to just a few lines of code on either side.

On the Swift side, SwiftHTTP simplified the POST call to a single function call that uses it’s own Upload class and a callback. That’s all I wanted to do. Done.

On the Node.js side, I was already using express to get a server running. What’s cool is express offers Multer as a solution. Multer says it’s really for forms that could use uploading, but it’s file uploading setup is simple enough to single-out. How it works is that for the Request object, they extend it to not only have a body object, but also a file object. So all you need to do is specify that you’re looking for a file in your post parameters and bam, you have your file.

Easy enough! In 20 lines of code across two platforms I had file uploading working.

Resources to Get Started

Tech Details

My implementation

Fastest way is to follow the install instructions for both. From there, here’s the code I used:

SwiftHTTP

func upload() {
        do {
            let opt = try HTTP.POST("http://localhost:3000/photo", parameters: ["photo": Upload(fileUrl: photoFileURL),"title": titleString])
            opt.start { response in
                self.performSegue(withIdentifier: "finishRecording", sender: nil)
            }
        } catch let error {
            print("got an error creating the request: \(error)")
        }
    }

Multer

app.post('/photo', upload.single('photo'), function (req, res, next) {
  var tmp_path = req.file.path;
  var target_path = 'uploads/' + req.file.originalname;
  var src = fs.createReadStream(tmp_path);
  var dest = fs.createWriteStream(target_path);
  src.pipe(dest);
  src.on('end', function() { 
    console.log("UPLOAD COMPLETE")
    res.send("complete"); 
  });
  src.on('error', function(err) { res.send("error"); });
})