Barista is a simple URL router for NodeJS.
In a nutshell
router.get( '/:beverage/near/:location(.:format)' )
.to( 'beverage.byLocation' )
router.first( '/coffee/near/90210', 'GET' )
router.url({
controller: 'beverage',
action: 'byLocation',
beverage: 'coffee',
location: 90210,
format: 'json'
})
Getting Barista
Install via npm, thusly:
npm install barista
Using Barista
var Router = require('barista').Router;
var router = new Router;
Adding routes
A simple example
router.match( '/products', 'GET' )
.to( 'products.index' )
Rails-esque variable names
router.match( '/products/:id', 'GET' )
.to( 'products.show' )
router.match( '/profiles/:username', 'GET' )
.to( 'users.show' )
router.match( '/products/:id(.:format)', 'GET' )
.to( 'products.show' )
Globs (they also capture slashes)
router.get('/timezones/*tzname')
.to( 'timezones.select' )
router.first( '/timezones/America/Toronto', 'GET' )
router.match( '/*path(.:format)' )
.to( 'errors.notFound' )
router.first( '/somewhere/that/four-oh-fours.json', 'GET' )
Match conditions
router.match( '/:beverage/near/:zipcode', 'GET' )
.to( 'beverage.byZipCode' )
.where({
beverage: [ 'coffee', 'tea', 'beer', 'warm_sake' ],
zipcode: /^\d{5}(-\d{4})?$/
})
router.match( '/:beverage/near/:location', 'GET' )
.to( 'beverage.byLocation' )
.where({
location: [ /^\d{5}(-\d{4})?$/, /^[ABCEGHJKLMNPRSTVXY]{1}\d{1}[A-Z]{1} *\d{1}[A-Z]{1}\d{1}$/, 'me' ]
})
Convenience methods
router.get( '/products/:id(.:format)' )
.to( 'products.show' )
router.put( '/products/:id(.:format)' )
.to( 'products.update' )
router.post( '/products' )
.to( 'products.create' )
router.del( '/products' )
.to( 'products.destroy' )
router.options( '/products' )
.to( 'products.options' )
REST Resources
router.resource( 'products' )
is equivalent to:
router.get( '/products(.:format)' )
.to( 'products.index' )
router.get( '/products/add(.:format)' )
.to( 'products.add' )
router.get( '/products/:id(.:format)' )
.to('products.show' )
router.get('/products/:id/edit(.:format)' )
.to( 'products.edit' )
router.post('/products(.:format)' )
.to( 'products.create' )
router.put('/products/:id(.:format)' )
.to( 'products.update' )
router.del('/products/:id(.:format)' )
.to( 'products.destroy' )
Removing Routes
In some cases, you will need to remove routes on a running router. The router.remove( name )
method will work for this, but requires
use of the otherwise unused route.name( name )
method.
Adding a name (currently only used with this functionality)
router.match( '/products/:id', 'GET' )
.to( 'products.show' )
.name('products_show')
Removing a named route
router.remove('products_show')
Resolution & dispatching
The router.first( url, method [, callback] )
method can be used in two ways:
var params = router.first( '/products/15', 'GET' )
OR
router.first( '/products/15', 'GET', function( params ){
})
You can get all the matching routes like so:
var params = router.all( '/products/15', 'GET' )
Route generation
Pass in a params hash, get back a tasty string:
router.url( {
controller: 'products',
action: 'show',
id: 5
} )
router.url( {
controller: 'products',
action: 'show',
id: 5,
format: 'json'
} )
Set the optional second parameter to true
if you want
extra params appended as a query string:
router.url({
controller: 'products',
action: 'show',
id: 5,
format: 'json',
love: 'cheese'
}, true )
Caveats & TODOs
nested optional segments are currently unsupported. e.g. this won't work:
router.get( '/:controller(/:action(/:id(.:format)))' )
nesting routes & resources is also still on the TODO list
Things I forgot...
...might be in the /docs
folder...
...or might not exist at all.
It's broken!
Shit happens.
Write a test that fails and add it to the tests folder,
then create an issue!
Patches welcome :-)
Who are you?
I'm Kieran Huggins, partner at Refactory in Toronto, Canada.