public
Created — forked from isaacs/server.js

  • Download Gist
server.js
JavaScript
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89
// test with:
// curl -X POST -d '{ "to" : "isaacs", "from" : "arlolra", "body" : "emoji 🍨 🍩 🍪"}' http://127.0.0.1:1337
 
var http = require("http")
 
// messages should be relatively short.
var maxLength = 1024
 
var server = http.createServer(function (req, res) {
// requests come in as json
// need to parse the json to get from, to, and body fields.
// JSON is probably generated by some native C JSON encoder
// on a device, or in some other language, or perhaps from
// another node program (in which case, it'll already be broken).
 
var chunks = []
var msgLen = 0
req.on("data", onData)
req.on("end", onEnd)
 
function onData (chunk) {
chunks.push(chunk)
msgLen += chunk.length
if (msgLen > maxLength) {
// DoS protection.
res.writeHead(413, {"content-type":"application/json"})
res.end(JSON.stringify({ok: false, error: "Request entity too large"}))
req.removeListener("data", onData)
req.removeListener("end", onEnd)
}
}
 
function onEnd () {
var message
switch (chunks.length) {
case 0: message = new Buffer(0); break
case 1: message = chunks[0]; break
default:
message = new Buffer(msgLen)
var i = 0
chunks.forEach(function (c) {
c.copy(message, i)
i += c.length
})
break
}
var i = 0, code = ''
for (; i < msgLen; i++) {
code += String.fromCharCode(message[i])
}
 
// so, now message is the full message
// it's a buffer, but we need to interpret it as JSON
// this is where the Bad Thing happens.
// if there were any characters outside the 2-byte plane,
// then they're going to now get turned into 2 garbage characters.
 
try {
message = JSON.parse(code)
} catch (ex) {
console.error(ex)
res.writeHead(400, {"content-type":"application/json"})
res.end(JSON.stringify({ok:false, error:"Bad JSON"}))
return
}
 
// in real life, this console.error would be replaced with
// some nifty routing message passing thingie
// console.error("From: %s\nTo: %s\n\n%s",
// message.from, message.to, message.body);
 
var mb = message.body
, len = mb.length
, buf = new Buffer(len + 1)
 
for (i = 0; i < len; i++) {
buf[i] = mb.charCodeAt(i)
}
buf[i] = 10
process.stdout.write(buf)
 
res.writeHead(200, { "content-type": "application/json" })
res.end(JSON.stringify({ ok: true }) + "\n")
}
})
 
server.listen(1337)

Please sign in to comment on this gist.

Something went wrong with that request. Please try again.