Skip to content
Browse files

eNode will serialise error objects to strings by default. Facility pr…

…ovided for easy custom error serialisation functions.
  • Loading branch information...
1 parent 0cd65b0 commit 5a887ebede2ab25728878292a27ca63b343b9590 @timoxley committed Jan 30, 2012
Showing with 164 additions and 11 deletions.
  1. +19 −3 lib/client.js
  2. +18 −0 lib/helpers.js
  3. +16 −2 lib/server.js
  4. +1 −1 package.json
  5. +12 −0 tests/helpers.js
  6. +91 −1 tests/integration.js
  7. +7 −4 tests/server.js
View
22 lib/client.js
@@ -4,6 +4,8 @@ var url = require('url')
var _ = require('underscore')
+var helpers = require('./helpers')
+
var EventEmitter = require('events').EventEmitter
var Client = function(api) {
@@ -28,6 +30,13 @@ Client.prototype.connect = function(host, callback) {
connection: connection
}
var args = Array.prototype.splice.call(arguments, 0) // copy args
+ var cb = args.pop()
+
+ var errorFriendlyCallback = function() {
+ var callbackArgs = self.serializeErrors(arguments)
+ cb.apply(self, callbackArgs)
+ }
+ args.push(errorFriendlyCallback)
args.push(meta)
value.apply(this, args)
}
@@ -38,11 +47,10 @@ Client.prototype.connect = function(host, callback) {
_(this).extend(wrappedAPI)
}).connect(host, function(remote, connection) {
-
+
self.connection = connection
connection.emit('up', remote);
})
-
this.up.once('remote', function() {
self.up.once('up', function(remote) {
self.ready = true
@@ -53,6 +61,14 @@ Client.prototype.connect = function(host, callback) {
return this
}
+Client.prototype.serializeErrors = function(args) {
+ return helpers.serializeErrors(args, this.serializeError)
+}
+
+Client.prototype.serializeError = function(error) {
+ return helpers.serializeError(error)
+}
+
Client.prototype.shutdown = function(callback) {
if (typeof callback !== 'function') callback = function(){}
var self = this
@@ -62,7 +78,7 @@ Client.prototype.shutdown = function(callback) {
})
return
}
-
+
if (!this.up.closed && self.connection != null) {
self.up.close()
if (!self.up.conn) {
View
18 lib/helpers.js
@@ -0,0 +1,18 @@
+'use strict'
+
+var util = require('util')
+
+exports.serializeErrors = function(args, serializeError) {
+ // ensure args is always an array (e.g. convert arguments objects)
+ var arrayArgs = Array.prototype.slice.call(args, 0)
+ serializeError = serializeError || exports.serializeError
+ return arrayArgs.map(function(item) {
+ if (util.isError(item)) return serializeError(item)
+ return item
+ })
+}
+
+exports.serializeError = function(error) {
+ return error.toString()
+}
+
View
18 lib/server.js
@@ -3,9 +3,10 @@
var dnode = require('dnode')
var upnode = require('upnode')
var _ = require('underscore')
-
var EventEmitter = require('events').EventEmitter
+var helpers = require('./helpers')
+
var Server = module.exports = exports = function(api) {
this.connections = []
this._api = api || {}
@@ -25,11 +26,16 @@ Server.prototype.listen = function(host, callback) {
if (typeof value === 'function') {
wrappedAPI[name] = function() {
var meta = {
- callback: callback,
remote: remote,
connection: connection
}
var args = Array.prototype.slice.call(arguments, 0) // copy args
+ var cb = args.pop()
+ var errorFriendlyCallback = function() {
+ var callbackArgs = self.serializeErrors(arguments)
+ cb.apply(self, callbackArgs)
+ }
+ args.push(errorFriendlyCallback)
args.push(meta)
value.apply(this, args)
}
@@ -59,6 +65,14 @@ Server.prototype.listen = function(host, callback) {
return this
}
+Server.prototype.serializeErrors = function(args) {
+ return helpers.serializeErrors(args, this.serializeError)
+}
+
+Server.prototype.serializeError = function(error) {
+ return helpers.serializeError(error)
+}
+
Server.prototype.shutdown = function(callback) {
if (typeof callback !== 'function') callback = function(){}
var self = this
View
2 package.json
@@ -2,7 +2,7 @@
"author": "Tim Oxley <secoif@gmail.com> (unit.io)",
"name": "enode",
"description": "Easier interface to dnode.",
- "version": "0.0.3",
+ "version": "0.1.0",
"repository": {
"url": ""
},
View
12 tests/helpers.js
@@ -0,0 +1,12 @@
+var helpers = require('../lib/helpers')
+var assert = require('assert')
+
+describe('helpers', function() {
+ describe('serialiseErrors', function() {
+ it('should serialise Error objects found in array', function() {
+ var args = [1, 2, new Error('success')]
+ var result = helpers.serializeErrors(args)
+ assert.deepEqual(result, [1, 2, 'Error: success'])
+ })
+ })
+})
View
92 tests/integration.js
@@ -91,6 +91,51 @@ describe('handing an API', function() {
})
})
})
+ it('can send error args', function(done) {
+ var connectionId
+ var api = {
+ say: function(callback, meta) {
+ callback(new Error('success'))
+ }
+ }
+ server = new Server(api).listen(PORT)
+ server.once('connect', function(remote, connection) {
+ connectionId = connection.id
+ })
+ client = new Client().connect(PORT)
+ client.once('ready', function(remote, connection) {
+ remote.say(function(err, value) {
+ assert.equal(err, 'Error: success')
+ done()
+ })
+ })
+ })
+ it('can use custom error serialisation', function(done) {
+ var connectionId
+ var api = {
+ say: function(callback, meta) {
+ callback(new Error('success'))
+ }
+ }
+ server = new Server(api).listen(PORT)
+ server.once('connect', function(remote, connection) {
+ connectionId = connection.id
+ })
+ client = new Client().connect(PORT)
+ server.serializeError = function(error) {
+ return {
+ message: error.message,
+ name: error.name
+ }
+ }
+
+ client.once('ready', function(remote, connection) {
+ remote.say(function(err, value) {
+ assert.deepEqual(err, {name: 'Error', message: 'success'})
+ done()
+ })
+ })
+ })
})
describe('server', function() {
it('can call client methods', function(done) {
@@ -134,7 +179,7 @@ describe('handing an API', function() {
connectionId = connection.id
})
})
- it('can send args', function(done) {
+ it('can use custom error serialisation', function(done) {
var connectionId
var api = {
say: function(word, callback) {
@@ -153,6 +198,51 @@ describe('handing an API', function() {
connectionId = connection.id
})
})
+ it('can send error args', function(done) {
+ var connectionId
+ var api = {
+ say: function(word, callback) {
+ callback(new Error('success'))
+ }
+ }
+ server = new Server().listen(PORT)
+ server.once('connect', function(remote, connection) {
+ remote.say('cows.', function(err, value) {
+ assert.equal(err, 'Error: success')
+ server.shutdown(done)
+ })
+ })
+ client = new Client(api).connect(PORT)
+ client.once('ready', function(remote, connection) {
+ connectionId = connection.id
+ })
+ })
+ it('can use custom error serialisation', function(done) {
+ var connectionId
+ var api = {
+ say: function(callback) {
+ callback(new Error('success'))
+ }
+ }
+ server = new Server().listen(PORT)
+ server.once('connect', function(remote, connection) {
+ remote.say(function(err, value) {
+ assert.deepEqual(err, {name: 'Error', message: 'success'})
+ server.shutdown(done)
+ })
+ })
+ client = new Client(api).connect(PORT)
+ client.serializeError = function(error) {
+ return {
+ message: error.message,
+ name: error.name
+ }
+ }
+ client.once('ready', function(remote, connection) {
+ connectionId = connection.id
+ })
+
+ })
})
})
View
11 tests/server.js
@@ -6,9 +6,9 @@ var Client = require('../lib/client')
var dnode = require('dnode')
var _ = require('underscore')
-var PORT = 5000
+var PORT = 6000
-var isPortTaken = function(PORT, callback) {
+var isPortTaken = function(port, callback) {
var net = require('net')
var tester = net.createServer()
tester.once('error', function (err) {
@@ -24,7 +24,7 @@ var isPortTaken = function(PORT, callback) {
})
tester.close()
})
- tester.listen(PORT)
+ tester.listen(port)
}
describe('server', function() {
@@ -89,8 +89,10 @@ describe('server', function() {
})
describe('listening on a port', function() {
it('will use callback when listening on port', function(done) {
- server = new Server().listen(PORT, function() {
+ server = new Server().listen(PORT, function(err) {
+ assert.ok(!err)
isPortTaken(PORT, function(err, isTaken) {
+ console.log(err)
assert.ok(!err)
assert.ok(isTaken)
done()
@@ -101,6 +103,7 @@ describe('server', function() {
server = new Server().listen(PORT)
server.on('ready', function() {
isPortTaken(PORT, function(err, isTaken) {
+ console.log(err)
assert.ok(!err)
assert.ok(isTaken)
done()

0 comments on commit 5a887eb

Please sign in to comment.
Something went wrong with that request. Please try again.