Skip to content

Commit

Permalink
Add: fs option & tests. Closes pillarjs#160
Browse files Browse the repository at this point in the history
	* Add: new option to specify which file system to use to serve files by default.
	* Add: exported erros for basic file system interface check
	* Add: basic tests via global injection
  • Loading branch information
hinell committed Apr 11, 2019
1 parent 09c2f2d commit f98ad6a
Show file tree
Hide file tree
Showing 4 changed files with 61 additions and 6 deletions.
2 changes: 1 addition & 1 deletion HISTORY.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
unreleased
==========

* Add `fs` option
* deps: depd@~2.0.0
- Replace internal `eval` usage with `Function` constructor
- Use instance methods on `process` to check for listeners
Expand Down
9 changes: 9 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -119,6 +119,15 @@ Serve files relative to `path`.
Byte offset at which the stream starts, defaults to 0. The start is inclusive,
meaning `start: 2` will include the 3rd byte in the stream.

##### fs

**Default**: [require('fs')](https://nodejs.org/api/fs.html)

File system to serve files by default.
```js
send(req, path, { fs: mockedFileSystem })
```

#### Events

The `SendStream` is an event emitter and will emit the following events:
Expand Down
25 changes: 20 additions & 5 deletions index.js
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,6 @@ var encodeUrl = require('encodeurl')
var escapeHtml = require('escape-html')
var etag = require('etag')
var fresh = require('fresh')
var fs = require('fs')
var mime = require('mime')
var ms = require('ms')
var onFinished = require('on-finished')
Expand Down Expand Up @@ -84,6 +83,10 @@ function send (req, path, options) {
return new SendStream(req, path, options)
}

var errors = {}
errors.INVALID_OPTION_FS_STAT = new TypeError('Invalid option: Incompatible file system interface: fs.stat() method is expected')
errors.INVALID_OPTION_FS_CRTSTRM = new TypeError('Invalid option: Incompatible file system interface: fs.createReadStream() method is expected')
send.errors = errors
/**
* Initialize a `SendStream` with the given `path`.
*
Expand All @@ -102,6 +105,18 @@ function SendStream (req, path, options) {
this.path = path
this.req = req

// Dynamically import `fs` if not it is not provided by config
this.fs = opts.fs || require('fs')

// Checking if provided "fs" is compatible
if (typeof this.fs.stat !== 'function') {
throw errors.INVALID_OPTION_FS_STAT
}

if (typeof this.fs.createReadStream !== 'function') {
throw errors.INVALID_OPTION_FS_CRTSTRM
}

this._acceptRanges = opts.acceptRanges !== undefined
? Boolean(opts.acceptRanges)
: true
Expand Down Expand Up @@ -718,7 +733,7 @@ SendStream.prototype.sendFile = function sendFile (path) {
var self = this

debug('stat "%s"', path)
fs.stat(path, function onstat (err, stat) {
this.fs.stat(path, function onstat (err, stat) {
if (err && err.code === 'ENOENT' && !extname(path) && path[path.length - 1] !== sep) {
// not found, check extensions
return next(err)
Expand All @@ -739,7 +754,7 @@ SendStream.prototype.sendFile = function sendFile (path) {
var p = path + '.' + self._extensions[i++]

debug('stat "%s"', p)
fs.stat(p, function (err, stat) {
self.fs.stat(p, function (err, stat) {
if (err) return next(err)
if (stat.isDirectory()) return next()
self.emit('file', p, stat)
Expand Down Expand Up @@ -767,7 +782,7 @@ SendStream.prototype.sendIndex = function sendIndex (path) {
var p = join(path, self._index[i])

debug('stat "%s"', p)
fs.stat(p, function (err, stat) {
self.fs.stat(p, function (err, stat) {
if (err) return next(err)
if (stat.isDirectory()) return next()
self.emit('file', p, stat)
Expand All @@ -793,7 +808,7 @@ SendStream.prototype.stream = function stream (path, options) {
var res = this.res

// pipe
var stream = fs.createReadStream(path, options)
var stream = this.fs.createReadStream(path, options)
this.emit('stream', stream)
stream.pipe(res)

Expand Down
31 changes: 31 additions & 0 deletions test/send.js
Original file line number Diff line number Diff line change
Expand Up @@ -1418,6 +1418,37 @@ describe('send(file, options)', function () {
})
})
})

describe('fs', function () {
var FS_STAT = send.errors.INVALID_OPTION_FS_STAT
var CRTSTRM = send.errors.INVALID_OPTION_FS_CRTSTRM
it('must provide fs.stat()', function (done) {
try {
send(void 0, '', { fs: { createReadStream: function () {} } })
} catch (err) {
if (err === FS_STAT) {
done()
} else {
done(new Error('Must throw INVALID_OPTION_FS_STAT'))
}
return
}
done()
})
it('must implement fs.createReadStream()', function (done) {
try {
send(void 0, '', { fs: { stat: function () {} } })
} catch (err) {
if (err === CRTSTRM) {
done()
} else {
done(new Error('Must throw INVALID_OPTION_FS_CRTSTRM'))
}
return
}
done()
})
})
})

describe('send.mime', function () {
Expand Down

0 comments on commit f98ad6a

Please sign in to comment.