Last active
August 29, 2015 14:05
-
-
Save evandertino/e14e213db36b68addd12 to your computer and use it in GitHub Desktop.
A simple Nodejs File server that streams non-requested resources to the client and loads already requested resources from a simple cache
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* | |
* Before executing this script | |
* | |
* 1. Create a dir named content | |
* 2. With an index.html that requests for files e.g css | |
* | |
* This simple server will automatically stream the | |
* requested resource from the content directory to the client | |
* | |
* author: Evander Tino | |
* | |
*/ | |
var http = require('http'); | |
var fs = require('fs'); | |
var path = require('path'); | |
var mimeTypes = { | |
'.js' : 'text/javascript', | |
'.html': 'text/html', | |
'.css' : 'text/css' | |
}; | |
var cache = { | |
store: {}, | |
maxSize: 26214400, //(bytes) 25mb | |
maxAge: 5400 * 1000, //(ms) 1 and a half hours | |
cleanAfter: 7200 * 1000,//(ms) two hours | |
cleanedAt: 0, //to be set dynamically | |
clean: function(now) { | |
if (now - this.cleanAfter > this.cleanedAt) { | |
this.cleanedAt = now; | |
that = this; | |
Object.keys(this.store).forEach(function (file) { | |
if (now > that.store[file].timestamp + that.maxAge) { | |
delete that.store[file]; | |
} | |
}); | |
} | |
} | |
}; | |
http.createServer(function (request, response) { | |
var lookup = path.basename(decodeURI(request.url)) || 'index.html'; | |
var f = 'content/' + lookup; | |
fs.exists(f, function (exists) { | |
if (exists) { | |
var headers = {'Content-Type': mimeTypes[path.extname(f)]}; | |
if (cache.store[f]) { | |
response.writeHead(200, headers); | |
response.end(cache.store[f].content); | |
console.log('loading ' + f + ' from the cache'); | |
return; | |
} | |
var s = fs.createReadStream(f).once('open', function() { | |
response.writeHead(200, headers); | |
this.pipe(response); | |
console.log('streaming ' + f + ' from disk'); | |
}).once('error', function(e) { | |
console.log(e); | |
response.writeHead(500); | |
response.end('Server Error!'); | |
}); | |
fs.stat(f, function(err, stats) { | |
if (stats.size < cache.maxSize) { | |
var bufferOffset = 0; | |
cache.store[f] = {content: new Buffer(stats.size), timestamp: Date.now() }; | |
s.on('data', function(data) { | |
data.copy(cache.store[f].content, bufferOffset); | |
bufferOffset += data.length; | |
}); | |
} | |
}); | |
} else { | |
response.writeHead(404); | |
response.end('Page Not Found'); | |
} | |
}); | |
cache.clean(Date.now()); | |
}).listen(8080); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Hello EvaderTino
I have been reading about node and your code is interesting, i am a beginner and I do not understand somethings, Could you answer me some question please:
thanks