user7195739
user7195739

Reputation:

NodeJS Wait till file is created

Writing a node js application where I want to wait until my file is created. Would like to know if there is any method more faster, accurate and better than mine.

My Code:

const fs = require("fs");
try { // Create files directory if not exists
        if (!fs.existsSync('./files'))
            fs.mkdirSync("./files")
    } catch (e) { logger.error("error:" + e) }

    // Create unique temporary files for each user
    fs.readFile("./file.js", 'utf8', (err, data) => {
        if (err)
            logger.error("error" + err)
        fs.writeFile(`./files/file.js`, data, (err) => {
            if (err)
                logger.error("error" + err)
            logger.warn('successfully created')
        });
        while (!fs.existsSync(`./files/file.js`))
            setTimeout(() => { }, 5000)

        if (fs.existsSync(`./files/file.js`)) {
            setTimeout(async () => {
                // My code that should be executed only once when the file is created..then delete the file
            }, 1000);
        }
    })

What i basically want to acheive is, I want to copy contents of a file and create another unique temporary file for each user. I want to wait until the file is created, if file is created, i want to execute some line of code only once then delete the file.

Thank you.

Upvotes: 2

Views: 12761

Answers (3)

pramod singh
pramod singh

Reputation: 511

async function waitForFileExists(filePath, currentTime = 0, timeout = 5000) {
  if (fs.existsSync(filePath)) return true;
  if (currentTime === timeout) return false;
  // wait for 1 second
  await new Promise((resolve, reject) => setTimeout(() => resolve(true), 1000));
  // waited for 1 second
  return waitForFileExists(filePath, currentTime + 1000, timeout);
}

I have used above method which is time bounded and return if file exists or not using fs library. It returns Promise<boolean>

Upvotes: 2

Alex
Alex

Reputation: 4811

I would recommend to use chokidar library https://github.com/paulmillr/chokidar for file system events. Polling approach is not recommended anyway due to hight CPU usage. fs.watch sometimes doesn't work (for example for mounted network folders, also it works slightly different on different OS).

var watcher = chokidar.watch('your directory', {
  persistent: true
});
watcher.on('add', path => { do what yo want with added files } );

Upvotes: 0

Serge K.
Serge K.

Reputation: 5323

You should put your code inside the writeFile callback like this :

const fs = require("fs");

try { // Create files directory if not exists
  if (!fs.existsSync('./files'))
    fs.mkdirSync("./files")
} catch (e) {
  logger.error("error:" + e)
}

// Create unique temporary files for each user
fs.readFile("./file.js", 'utf8', (err, data) => {
  if (err)
    logger.error("error" + err)

  fs.writeFile(`./files/file.js`, data, (err) => {
    if (err)
      logger.error("error" + err)

    logger.warn('successfully created')
    // Your code that should be executed only once when the file is created..then delete the file
  });
})

If Javascript's asynchronous nature really doesn't suits you, then you could also use writeFileSync.

Upvotes: 2

Related Questions