Easiest way to automate image upload to cloudinary using nodejs

Cloudinary is a cloud service that offers a solution to a project’s entire image management pipeline by which we can easily upload images & videos to the cloud. It offers comprehensive APIs and administration capabilities and is easy to integrate with any mobile or web application.

In today’s article, we are going to write a simple nodejs script to automatically upload images to cloudinary CDN when someone adds a new image to a folder on the local machine or remote server. Run “npm init” command in a folder and the below command to install required npm modules:

npm install --save express chokidar cloudinary

Let us start by spinning up a simple express server:

const express = require('express');
let app = express();
let port = process.env.PORT || 5000;
//start server on specified port
console.log("serve listening on port", port);

We will be using chokidar npm module to listen for changes in image source folder to check if new files are added anywhere inside the folder. You can find an excellent tutorial explaining it’s usage in detail with all available options here: Tutorial.

We set up chokidar to listen for changes as follows:

const express = require('express');
let app = express();
const chokidar = require('chokidar');
const filepath = '/home/saurabh/Pictures/Apps/';
let watcher = chokidar.watch(filepath, {
  ignored: /[\/\\]\./, persistent: true
let log = console.log.bind(console);
let scanComplete = false;
  .on('add', function (path) {
    if (scanComplete) {
     //add image uploading code here   
  .on('addDir', function (path) {
    // log('Directory', path, 'has been added'); 
  .on('error', function (error) { log('Error happened', error); })
  .on('ready', function () {
    log('Initial scan complete. Ready for changes.');
    scanComplete = true;
  .on('raw', function (event, path, details) {
    // log('Raw event info:', event, path, details);

Here we first specify folder path in which we are going to add files on line 4. Then we set up a watcher to watch files in a folder on the next line. Watcher has multiple event listeners on which appropriate callbacks are fired. It will first add all existing files in a folder in the watcher. In order to prevent uploading of existing files to CDN, we first set scanComplete flag to false. When chokidar has finished scanning all files it fires ready event. In that case, we can set scanComplete flag to true so that we can upload the next incoming files to CDN. Whenever a new file is added anywhere inside the source folder the add event is fired and since the initial scan is now complete we can now add new files to CDN.

Now let us focus on setting up upload to cloudinary CDN. First, we need to set up access to cloudinary CDN:

let scanComplete = false;
const cloudinary = require('cloudinary');
  cloud_name: 'yourcloudname',
  api_key: 'your cloudinary api key',
  api_secret: 'api secret key'

You will get the cloudname,api_key and api_secret from the dashboard of cloudinary CDN. Create an account if you don’t have one and go to the dashboard to get all the required credentials. Click on reveal to get api_secret in the dashboard tab.

Next, we will upload files to cloudinary CDN when chokidar watcher detects addition of new file to file path.

.on('add', function (path) {
    if (scanComplete) {
      let pathArray = path.split('/');
      if (!pathArray[pathArray.length - 1].includes("crdownload")) {
        log('File', path, 'has been added');
        // console.log(pathArray.length, pathArray[pathArray.length - 2]);
        let destfolder = pathArray[pathArray.length - 2];
        let destfileName = pathArray[pathArray.length - 1];
        cloudinary.v2.uploader.upload(path, {
          folder: destfolder,
        }, function (error, result) {
          if (error) {
            console.log("error ocurred", error);
          else {
            console.log("result of upload \n", result.secure_url,"\n insecure url: \n",result.url);

When a file is added we first split path in individual names using the split method in line 4.

For example, if file path is ‘/home/saurabh/Pictures/Apps/imgcat1/img1.jpg’ we get pathArray as [‘’,’home’,’saurabh’,’Pictures’,’Apps’,’imgcat1',’img1.jpg’]

Now I download images from chrome due to which it first creates a temporary “.crdownload” file while file download is in progress. In order to prevent uploading of temp files to CDN, we have added an if condition in the next line. Once filedownload is complete I prefer to upload the file in a specific remote folder in cloudinary cdn rather than uploading files directly to the base path. We first get destination folder name which might be imgcat1(second last element in pathArray variable)in the above example and destfileName which is the last element in pathArray variable.

Next, we call the uploader method from cloudinary module to upload the file from path variable that chokidar watcher returns. The second parameter in the upload function is a JSON containing extra parameters which customizing upload to CDN. You can get a detailed list of upload option here: Upload Api Reference

We first specify that we will upload the image inside destfolder at cloudinary CDN. Please create an appropriate folder on the CDN by going to cloudinary dashboard, clicking on media library and creating a new folder to avoid any unwanted issues. Next, we set the “use_filename” flag to true so that filenames are not assigned random names on CDN and specify appropriate tags to have easier indexing and usage of images in future.

You can find the complete source code for the script here: GithubGist

Bonus Tip:

Tip #1: Even if you don’t use cloudinary as your CDN you can still use chokidar module for a variety of purposes like updating file/content metadata when new files are uploaded into a server or run some simple automation tasks based on your needs.

Tip #2: You can also upload video files to cloudinary CDN and if video files using same upload function by following the documentation here: Video Upload Api Reference

Connect Deeper:

If you would like to get notified about upcoming articles then you can follow me on Twitter or LinkedIn

No Comments Yet