4 [![build status](https://api.travis-ci.org/jprichardson/node-fs-extra.svg)](http://travis-ci.org/jprichardson/node-fs-extra)
5 [![windows Build status](https://img.shields.io/appveyor/ci/jprichardson/node-fs-extra/master.svg?label=windows%20build)](https://ci.appveyor.com/project/jprichardson/node-fs-extra/branch/master)
6 [![downloads per month](http://img.shields.io/npm/dm/fs-extra.svg)](https://www.npmjs.org/package/fs-extra)
7 [![Coverage Status](https://img.shields.io/coveralls/jprichardson/node-fs-extra.svg)](https://coveralls.io/r/jprichardson/node-fs-extra)
10 `fs-extra` adds file system methods that aren't included in the native `fs` module. It is a drop in replacement for `fs`.
12 **NOTE (2016-01-13):** Node v0.10 will be unsupported AFTER Ubuntu LTS releases their next version AND [Amazon Lambda
13 upgrades](http://docs.aws.amazon.com/lambda/latest/dg/current-supported-versions.html) its Node.js runtime from v0.10.
14 I anticipate this will happen around late spring / summer 2016. Please prepare accordingly. After this, we'll make a strong push
21 I got tired of including `mkdirp`, `rimraf`, and `cp -r` in most of my projects.
29 npm install --save fs-extra
36 `fs-extra` is a drop in replacement for native `fs`. All methods in `fs` are unmodified and attached to `fs-extra`.
38 You don't ever need to include the original `fs` module again:
41 var fs = require('fs') // this is no longer necessary
47 var fs = require('fs-extra')
50 or if you prefer to make it clear that you're using `fs-extra` and not `fs`, you may want
51 to name your `fs` variable `fse` like so:
54 var fse = require('fs-extra')
57 you can also keep both, but it's redundant:
60 var fs = require('fs')
61 var fse = require('fs-extra')
66 Most methods are async by default (they take a callback with an `Error` as first argument).
68 Sync methods on the other hand will throw if an error occurs.
73 var fs = require('fs-extra')
75 fs.copy('/tmp/myfile', '/tmp/mynewfile', function (err) {
76 if (err) return console.error(err)
77 console.log("success!")
81 fs.copySync('/tmp/myfile', '/tmp/mynewfile')
82 console.log("success!")
93 - [createOutputStream](#createoutputstreamfile-options)
94 - [emptyDir](#emptydirdir-callback)
95 - [emptyDirSync](#emptydirdir-callback)
96 - [ensureFile](#ensurefilefile-callback)
97 - [ensureFileSync](#ensurefilefile-callback)
98 - [ensureDir](#ensuredirdir-callback)
99 - [ensureDirSync](#ensuredirdir-callback)
100 - [ensureLink](#ensurelinksrcpath-dstpath-callback)
101 - [ensureLinkSync](#ensurelinksrcpath-dstpath-callback)
102 - [ensureSymlink](#ensuresymlinksrcpath-dstpath-type-callback)
103 - [ensureSymlinkSync](#ensuresymlinksrcpath-dstpath-type-callback)
104 - [mkdirs](#mkdirsdir-callback)
105 - [mkdirsSync](#mkdirsdir-callback)
106 - [move](#movesrc-dest-options-callback)
107 - [outputFile](#outputfilefile-data-options-callback)
108 - [outputFileSync](#outputfilefile-data-options-callback)
109 - [outputJson](#outputjsonfile-data-options-callback)
110 - [outputJsonSync](#outputjsonfile-data-options-callback)
111 - [readJson](#readjsonfile-options-callback)
112 - [readJsonSync](#readjsonfile-options-callback)
113 - [remove](#removedir-callback)
114 - [removeSync](#removedir-callback)
116 - [writeJson](#writejsonfile-object-options-callback)
117 - [writeJsonSync](#writejsonfile-object-options-callback)
120 **NOTE:** You can still use the native Node.js methods. They are copied over to `fs-extra`.
125 **copy(src, dest, [options], callback)**
128 Copy a file or directory. The directory can have contents. Like `cp -r`.
131 - clobber (boolean): overwrite existing file or directory
132 - preserveTimestamps (boolean): will set last modification and access times to the ones of the original source files, default is `false`.
133 - filter: Function or RegExp to filter copied files. If function, return true to include, false to exclude. If RegExp, same as function, where `filter` is `filter.test`.
140 var fs = require('fs-extra')
142 fs.copy('/tmp/myfile', '/tmp/mynewfile', function (err) {
143 if (err) return console.error(err)
144 console.log("success!")
147 fs.copy('/tmp/mydir', '/tmp/mynewdir', function (err) {
148 if (err) return console.error(err)
149 console.log('success!')
150 }) // copies directory, even if it has subdirectories or files
153 ### createOutputStream(file, [options])
155 Exactly like `createWriteStream`, but if the directory does not exist, it's created.
160 var fs = require('fs-extra')
162 // if /tmp/some does not exist, it is created
163 var ws = fs.createOutputStream('/tmp/some/file.txt')
167 Note on naming: you'll notice that fs-extra has some methods like `fs.outputJson`, `fs.outputFile`, etc that use the
168 word `output` to denote that if the containing directory does not exist, it should be created. If you can think of a
169 better succinct nomenclature for these methods, please open an issue for discussion. Thanks.
172 ### emptyDir(dir, [callback])
174 Ensures that a directory is empty. Deletes directory contents if the directory is not empty. If the directory does not exist, it is created. The directory itself is not deleted.
178 Sync: `emptyDirSync()`, `emptydirSync()`
183 var fs = require('fs-extra')
185 // assume this directory has a lot of files and folders
186 fs.emptyDir('/tmp/some/dir', function (err) {
187 if (!err) console.log('success!')
192 ### ensureFile(file, callback)
194 Ensures that the file exists. If the file that is requested to be created is in directories that do not exist, these directories are created. If the file already exists, it is **NOT MODIFIED**.
196 Alias: `createFile()`
198 Sync: `createFileSync()`,`ensureFileSync()`
204 var fs = require('fs-extra')
206 var file = '/tmp/this/path/does/not/exist/file.txt'
207 fs.ensureFile(file, function (err) {
208 console.log(err) // => null
209 // file has now been created, including the directory it is to be placed in
214 ### ensureDir(dir, callback)
216 Ensures that the directory exists. If the directory structure does not exist, it is created.
218 Sync: `ensureDirSync()`
224 var fs = require('fs-extra')
226 var dir = '/tmp/this/path/does/not/exist'
227 fs.ensureDir(dir, function (err) {
228 console.log(err) // => null
229 // dir has now been created, including the directory it is to be placed in
234 ### ensureLink(srcpath, dstpath, callback)
236 Ensures that the link exists. If the directory structure does not exist, it is created.
238 Sync: `ensureLinkSync()`
244 var fs = require('fs-extra')
246 var srcpath = '/tmp/file.txt'
247 var dstpath = '/tmp/this/path/does/not/exist/file.txt'
248 fs.ensureLink(srcpath, dstpath, function (err) {
249 console.log(err) // => null
250 // link has now been created, including the directory it is to be placed in
255 ### ensureSymlink(srcpath, dstpath, [type], callback)
257 Ensures that the symlink exists. If the directory structure does not exist, it is created.
259 Sync: `ensureSymlinkSync()`
265 var fs = require('fs-extra')
267 var srcpath = '/tmp/file.txt'
268 var dstpath = '/tmp/this/path/does/not/exist/file.txt'
269 fs.ensureSymlink(srcpath, dstpath, function (err) {
270 console.log(err) // => null
271 // symlink has now been created, including the directory it is to be placed in
276 ### mkdirs(dir, callback)
278 Creates a directory. If the parent hierarchy doesn't exist, it's created. Like `mkdir -p`.
282 Sync: `mkdirsSync()` / `mkdirpSync()`
288 var fs = require('fs-extra')
290 fs.mkdirs('/tmp/some/long/path/that/prob/doesnt/exist', function (err) {
291 if (err) return console.error(err)
292 console.log("success!")
295 fs.mkdirsSync('/tmp/another/path')
299 ### move(src, dest, [options], callback)
301 Moves a file or directory, even across devices.
304 - clobber (boolean): overwrite existing file or directory
305 - limit (number): number of concurrent moves, see ncp for more information
310 var fs = require('fs-extra')
312 fs.move('/tmp/somefile', '/tmp/does/not/exist/yet/somefile', function (err) {
313 if (err) return console.error(err)
314 console.log("success!")
319 ### outputFile(file, data, [options], callback)
321 Almost the same as `writeFile` (i.e. it [overwrites](http://pages.citebite.com/v2o5n8l2f5reb)), except that if the parent directory does not exist, it's created. `options` are what you'd pass to [`fs.writeFile()`](https://nodejs.org/api/fs.html#fs_fs_writefile_file_data_options_callback).
323 Sync: `outputFileSync()`
329 var fs = require('fs-extra')
330 var file = '/tmp/this/path/does/not/exist/file.txt'
332 fs.outputFile(file, 'hello!', function (err) {
333 console.log(err) // => null
335 fs.readFile(file, 'utf8', function (err, data) {
336 console.log(data) // => hello!
343 ### outputJson(file, data, [options], callback)
345 Almost the same as `writeJson`, except that if the directory does not exist, it's created.
346 `options` are what you'd pass to [`jsonFile.writeFile()`](https://github.com/jprichardson/node-jsonfile#writefilefilename-options-callback).
348 Alias: `outputJSON()`
350 Sync: `outputJsonSync()`, `outputJSONSync()`
356 var fs = require('fs-extra')
357 var file = '/tmp/this/path/does/not/exist/file.txt'
359 fs.outputJson(file, {name: 'JP'}, function (err) {
360 console.log(err) // => null
362 fs.readJson(file, function(err, data) {
363 console.log(data.name) // => JP
370 ### readJson(file, [options], callback)
372 Reads a JSON file and then parses it into an object. `options` are the same
373 that you'd pass to [`jsonFile.readFile`](https://github.com/jprichardson/node-jsonfile#readfilefilename-options-callback).
377 Sync: `readJsonSync()`, `readJSONSync()`
383 var fs = require('fs-extra')
385 fs.readJson('./package.json', function (err, packageObj) {
386 console.log(packageObj.version) // => 0.1.3
390 `readJsonSync()` can take a `throws` option set to `false` and it won't throw if the JSON is invalid. Example:
393 var fs = require('fs-extra')
394 var file = path.join('/tmp/some-invalid.json')
395 var data = '{not valid JSON'
396 fs.writeFileSync(file, data)
398 var obj = fs.readJsonSync(file, {throws: false})
399 console.log(obj) // => null
403 ### remove(dir, callback)
405 Removes a file or directory. The directory can have contents. Like `rm -rf`.
413 var fs = require('fs-extra')
415 fs.remove('/tmp/myfile', function (err) {
416 if (err) return console.error(err)
418 console.log('success!')
421 fs.removeSync('/home/jprichardson') //I just deleted my entire HOME directory.
426 **walk(dir, [streamOptions])**
428 The function `walk()` from the module [`klaw`](https://github.com/jprichardson/node-klaw).
430 Returns a [Readable stream](https://nodejs.org/api/stream.html#stream_class_stream_readable) that iterates
431 through every file and directory starting with `dir` as the root. Every `read()` or `data` event
432 returns an object with two properties: `path` and `stats`. `path` is the full path of the file and
433 `stats` is an instance of [fs.Stats](https://nodejs.org/api/fs.html#fs_class_fs_stats).
435 Streams 1 (push) example:
438 var items = [] // files, directories, symlinks, etc
440 .on('data', function (item) {
441 items.push(item.path)
443 .on('end', function () {
444 console.dir(items) // => [ ... array of files]
448 Streams 2 & 3 (pull) example:
451 var items = [] // files, directories, symlinks, etc
453 .on('readable', function () {
455 while ((item = this.read())) {
456 items.push(item.path)
459 .on('end', function () {
460 console.dir(items) // => [ ... array of files]
464 If you're not sure of the differences on Node.js streams 1, 2, 3 then I'd
465 recommend this resource as a good starting point: https://strongloop.com/strongblog/whats-new-io-js-beta-streams3/.
467 **See [`klaw` documentation](https://github.com/jprichardson/node-klaw) for more detailed usage.**
470 ### writeJson(file, object, [options], callback)
472 Writes an object to a JSON file. `options` are the same that
473 you'd pass to [`jsonFile.writeFile()`](https://github.com/jprichardson/node-jsonfile#writefilefilename-options-callback).
477 Sync: `writeJsonSync()`, `writeJSONSync()`
482 var fs = require('fs-extra')
483 fs.writeJson('./package.json', {name: 'fs-extra'}, function (err) {
494 Use [Bluebird](https://github.com/petkaantonov/bluebird). See https://github.com/petkaantonov/bluebird/blob/master/API.md#promisification. `fs-extra` is
495 explicitly listed as supported.
498 var Promise = require('bluebird')
499 var fs = Promise.promisifyAll(require('fs-extra'))
502 Or you can use the package [`fs-extra-promise`](https://github.com/overlookmotel/fs-extra-promise) that marries the two together.
507 If you like TypeScript, you can use `fs-extra` with it: https://github.com/borisyankov/DefinitelyTyped/tree/master/fs-extra
510 ### File / Directory Watching
512 If you want to watch for changes to files or directories, then you should use [chokidar](https://github.com/paulmillr/chokidar).
517 - [mfs](https://github.com/cadorn/mfs) - Monitor your fs-extra calls.
524 Wanna hack on `fs-extra`? Great! Your help is needed! [fs-extra is one of the most depended upon Node.js packages](http://nodei.co/npm/fs-extra.png?downloads=true&downloadRank=true&stars=true). This project
525 uses [JavaScript Standard Style](https://github.com/feross/standard) - if the name or style choices bother you,
526 you're gonna have to get over it :) If `standard` is good enough for `npm`, it's good enough for `fs-extra`.
528 [![js-standard-style](https://cdn.rawgit.com/feross/standard/master/badge.svg)](https://github.com/feross/standard)
531 - First, take a look at existing issues. Those are probably going to be where the priority lies.
532 - More tests for edge cases. Specifically on different platforms. There can never be enough tests.
533 - Really really help with the Windows tests. See appveyor outputs for more info.
534 - Improve test coverage. See coveralls output for more info.
535 - A directory walker. Probably this one: https://github.com/thlorenz/readdirp imported into `fs-extra`.
536 - After the directory walker is integrated, any function that needs to traverse directories like
537 `copy`, `remove`, or `mkdirs` should be built on top of it.
539 Note: If you make any big changes, **you should definitely post an issue for discussion first.**
545 I put a lot of thought into the naming of these functions. Inspired by @coolaj86's request. So he deserves much of the credit for raising the issue. See discussion(s) here:
547 * https://github.com/jprichardson/node-fs-extra/issues/2
548 * https://github.com/flatiron/utile/issues/11
549 * https://github.com/ryanmcgrath/wrench-js/issues/29
550 * https://github.com/substack/node-mkdirp/issues/17
552 First, I believe that in as many cases as possible, the [Node.js naming schemes](http://nodejs.org/api/fs.html) should be chosen. However, there are problems with the Node.js own naming schemes.
554 For example, `fs.readFile()` and `fs.readdir()`: the **F** is capitalized in *File* and the **d** is not capitalized in *dir*. Perhaps a bit pedantic, but they should still be consistent. Also, Node.js has chosen a lot of POSIX naming schemes, which I believe is great. See: `fs.mkdir()`, `fs.rmdir()`, `fs.chown()`, etc.
556 We have a dilemma though. How do you consistently name methods that perform the following POSIX commands: `cp`, `cp -r`, `mkdir -p`, and `rm -rf`?
558 My perspective: when in doubt, err on the side of simplicity. A directory is just a hierarchical grouping of directories and files. Consider that for a moment. So when you want to copy it or remove it, in most cases you'll want to copy or remove all of its contents. When you want to create a directory, if the directory that it's suppose to be contained in does not exist, then in most cases you'll want to create that too.
560 So, if you want to remove a file or a directory regardless of whether it has contents, just call `fs.remove(path)`. If you want to copy a file or a directory whether it has contents, just call `fs.copy(source, destination)`. If you want to create a directory regardless of whether its parent directories exist, just call `fs.mkdirs(path)` or `fs.mkdirp(path)`.
566 `fs-extra` wouldn't be possible without using the modules from the following authors:
568 - [Isaac Shlueter](https://github.com/isaacs)
569 - [Charlie McConnel](https://github.com/avianflu)
570 - [James Halliday](https://github.com/substack)
571 - [Andrew Kelley](https://github.com/andrewrk)
581 Copyright (c) 2011-2016 [JP Richardson](https://github.com/jprichardson)
583 [1]: http://nodejs.org/docs/latest/api/fs.html
586 [jsonfile]: https://github.com/jprichardson/node-jsonfile