.\" generated with Ronn/v0.7.3 .\" http://github.com/rtomayko/ronn/tree/0.7.3 . .TH "COMPOUND\-ROUTING" "3" "November 2013" "1602 Software" "CompoundJS" . .SH "NAME" \fBcompound\-routing\fR \- compound map drawer . .SH "DESCRIPTION" The purpose of routes is to bind an URL to controller action\. . .SH "FILE" \fBconfig/routes\.js\fR should export \fBroutes(map)\fR function: . .IP "" 4 . .nf exports\.routes = function draw(map) { map\.root(\'dashboard#home\'); map\.namespace(\'admin\', function(admin) { admin\.resources(\'users\'); }); }; . .fi . .IP "" 0 . .SH "EVENT" The \fBroutes\fR event can be used on compound object to define routes: . .IP "" 4 . .nf compound\.on(\'routes\', function(map, compound) { map\.get(\'auth\', \'session#auth\'); }); . .fi . .IP "" 0 . .P It could be useful when you want to define some routes before application initialization\. When app initialized use \fBcompound\.map\fR object\. . .SH "BASIC ROUTING METHODS" To define routes we have map object which have number of methods: . .TP \fBget\fR Define route for GET method\. . .TP \fBpost\fR Define route for POST method\. . .TP \fBput\fR Define route for PUT method\. . .TP \fBdel\fR Define route for DELETE method\. . .TP \fBall\fR Define route for all http methods\. . .P All these methods have following signature: . .IP "" 4 . .nf map\.get(path, handler, middleware, options); . .fi . .IP "" 0 . .P Params meaning: . .TP \fBpath\fR some path, which could contain params, see \fIROUTE PATH PARAMS\fR . .TP \fBhandler\fR string \fBcontrollerName#actionName\fR, see \fIROUTE HANDLER\fR . .TP \fBmiddleware\fR function or array of functions (optional), see \fIMIDDLEWARE\fR . .TP \fBoptions\fR object containing params for route (optional), see \fIROUTE OPTIONS\fR . .SS "ROUTE PATH PARAMS" Path may contain params \- words started with colon ":"\. Parameter is optional when param name followed by question mark "?"\. After matching request param values populated \fBreq\.params\fR object\. . .SS "ROUTE HANDLER" Route handler is a string composed from \fBcontrollerName\fR and \fBactionName\fR separated by \fB#\fR sign\. When route nested inside resource \fBcontrollerName\fR could be optional, in that case resource controller name assumed: . .IP "" 4 . .nf map\.resources(\'posts\', function (post) { // map \'/posts/destroyAll\' // to {controller: \'posts\', action: \'cleanup\'} post\.get(\'destroyAll\', \'#cleanup\', {collection: true}); }); . .fi . .IP "" 0 . .P Route handler could be skipped at all when route nested inside resource, then actionName assumed to equals path: . .IP "" 4 . .nf map\.resources(\'posts\', function (post) { // map \'/posts/:post_id/commentsCount\' // to {controller: \'posts\', action: \'commentsCount\'} post\.get(\'commentsCount\'); }); . .fi . .IP "" 0 . .SS "MIDDLEWARE" You may want to use middleware in routes\. It\'s not recommended, but if you need it you can put it as second argument: . .IP "" 4 . .nf map\.get(\'/admin\', \'admin#index\', authenticate); map\.get(\'/protected/resource\', \'resource#access\', [middleware1, middleware2]); . .fi . .IP "" 0 . .SS "ROUTE OPTIONS" . .TP \fBas\fR Specify custom URL helper name . .IP map\.get(\'/some/action\', \'some#action\', {as: \'myAction\'}); pathTo\.myAction() => \'/some/action\' . .TP \fBsubdomain\fR Check HTTP/1\.1 Host header when matching request, use * as wildcard domain: . .IP map\.get(\'/url\', \'ctl#action\', {subdomain: \'subdomain\.tld\'}); map\.get(\'/url\', \'ctl#action\', {subdomain: \'*\.example\.com\'}); . .P A subdomain match will ignore the first\- and second\-level components of the domain\. This value is hard\-coded into the \fBControllerBridge\fR class\. . .P \fINOTE\fR: This feature relies on \fBHost\fR HTTP/1\.1 header, if your Node process behind a proxy (like Nginx), make sure you\'ve passed this header to CompoundJS\. . .TP \fBvhost\fR Constrains the route match to include the given virtual host name . .IP map\.get(\'/apples/:id\', \'fruit#action\', {vhost: \'\.fruit\.com\'}); map\.get(\'/carrots/:id\', \'vegetable#action\', {vhost: \'vegetables\.com\'}); . .P In the examples above, the \fB/apples/:id\fR route matches \fBhttp://fruit\.com\fR and \fBhttp://*\.fruit\.com\fR, while the \fB/carrots/:id\fR route will only match \fBhttp://vegetables\.com\fR\. . .P Compared to the \fBsubdomain\fR option, the \fBvhost\fR option allows for a more straightforward route constraint on domain name\. . .P \fINOTE\fR: Like the \fBsubdomain\fR feature, this relies on \fBHost\fR HTTP/1\.1 header\. . .SH "URL HELPERS" URL helpers provide you convenient way to work with paths in your app\. When you define route: . .IP "" 4 . .nf map\.get(\'bunny\', \'bunny#show\'); . .fi . .IP "" 0 . .P you can use \fBpathTo\.bunny\fR in your controllers and views, which will generate . .IP "" 4 . .nf /bunny . .fi . .IP "" 0 . .P path for you\. You also can specify another helper name is you want using \fBas\fR param: . .IP "" 4 . .nf map\.get(\'bunny\', \'bunny#show\', {as: \'rabbit\'}); . .fi . .IP "" 0 . .P and now \fBpathTo\.rabbit\fR available\. . .P If your route has param, for example . .IP "" 4 . .nf map\.get(\'profile/:user\', \'users#show\'); map\.get(\'posts/:post_id/comments/:comment_id\', \'comments#show\'); . .fi . .IP "" 0 . .P URL helper will accept parameter (String), so that: . .IP "" 4 . .nf pathTo\.profile(\'Bugs_Bunny\', \'users#show\'); > \'/profile/Bugs_Bunny\' pathTo\.post_comment(2, 2383); > \'/posts/2/comments/2383\' . .fi . .IP "" 0 . .P To learn how to get list of generated url helpers see \fIDEBUGGING\fR section\. . .SH "ADVANCED ROUTING METHODS" . .SS "NAMESPACES" You may wish to organize groups of controllers under a namespace\. The most common use\-case is an administration area\. All controllers within the \fBadmin\fR namespace should be located inside the \fBapp/controllers/\fR directory\. . .P For example, let\'s create an admin namespace: . .IP "" 4 . .nf map\.namespace(\'admin\', function (admin) { admin\.resources(\'users\'); }); . .fi . .IP "" 0 . .P This routing rule will match with \fB/admin/users\fR, \fB/admin/users/new\fR and will create appropriate url helpers: . .IP "" 4 . .nf admin_users GET /admin/users\.:format? admin/users#index admin_users POST /admin/users\.:format? admin/users#create new_admin_user GET /admin/users/new\.:format? admin/users#new edit_admin_user GET /admin/users/:id/edit\.:format? admin/users#edit admin_user DELETE /admin/users/:id\.:format? admin/users#destroy admin_user PUT /admin/users/:id\.:format? admin/users#update admin_user GET /admin/users/:id\.:format? admin/users#show . .fi . .IP "" 0 . .SS "RESOURCES" Resource\-based routing provides standard mapping between HTTP verbs and controller actions: . .IP "" 4 . .nf map\.resources(\'posts\'); . .fi . .IP "" 0 . .P will provide the following routes: . .IP "" 4 . .nf helper | method | path | controller#action posts GET /posts posts#index posts POST /posts posts#create new_post GET /posts/new posts#new edit_post GET /posts/:id/edit posts#edit post DELETE /posts/:id posts#destroy post PUT /posts/:id posts#update post GET /posts/:id posts#show\. . .fi . .IP "" 0 . .P To list all available routes you can run the command \fBcompound routes\fR\. . .P The first column of the table represents the \fBhelper\fR \- you can use this identifier in views and controllers to get the route\. Some examples: . .IP "" 4 . .nf path_to\.new_post # /posts/new path_to\.edit_post(1) # /posts/1/edit path_to\.edit_post(post) # /posts/1/edit (in this example post = {id: 1}) path_to\.posts # /posts path_to\.post(post) # /posts/1\. . .fi . .IP "" 0 . .P \fBOPTIONS\fR . .P If you want to override default routes behaviour, you can use two options: \fBas\fR and \fBpath\fR to specify a helper name and a path you want to have in the result\. . .TP \fB{ as: \'helperName\' }\fR Path helper aliasing: . .IP map\.resources(\'posts\', { as: \'articles\' }); . .P This will create the following routes: . .IP "" 4 . .nf articles GET /posts\.:format? posts#index articles POST /posts\.:format? posts#create new_article GET /posts/new\.:format? posts#new edit_article GET /posts/:id/edit\.:format? posts#edit article DELETE /posts/:id\.:format? posts#destroy article PUT /posts/:id\.:format? posts#update article GET /posts/:id\.:format? posts#show\. . .fi . .IP "" 0 . .TP \fB{ path: \'alternatePath\' }\fR If you want to change the base path: . .IP map\.resources(\'posts\', { path: \'articles\' }); . .P This will create the following routes: . .IP "" 4 . .nf posts GET /articles\.:format? posts#index posts POST /articles\.:format? posts#create new_post GET /articles/new\.:format? posts#new edit_post GET /articles/:id/edit\.:format? posts#edit post DELETE /articles/:id\.:format? posts#destroy post PUT /articles/:id\.:format? posts#update post GET /articles/:id\.:format? posts#show . .fi . .IP "" 0 . .TP \fBBoth "as" and "path" together\fR: . .P If you want to alias both the helper and the path: . .IP "" 4 . .nf map\.resources(\'posts\', { path: \'articles\', as: \'stories\' }); . .fi . .IP "" 0 . .P This will create the following routes: . .IP "" 4 . .nf stories GET /articles\.:format? posts#index stories POST /articles\.:format? posts#create new_story GET /articles/new\.:format? posts#new edit_story GET /articles/:id/edit\.:format? posts#edit story DELETE /articles/:id\.:format? posts#destroy story PUT /articles/:id\.:format? posts#update story GET /articles/:id\.:format? posts#show . .fi . .IP "" 0 . .TP \fBonly\fR If you need routes only for several actions (e\.g\. \fBindex\fR, \fBshow\fR), you can specify the \fBonly\fR option: . .IP map\.resources(\'users\', { only: [\'index\', \'show\'] }); . .TP \fBexcept\fR If you want to have all routes except a specific route, you can specify the \fBexcept\fR option: . .IP map\.resources(\'users\', { except: [\'create\', \'destroy\'] }); . .P \fBNested resources\fR . .P Some resources may have nested sub\-resources, for example \fBPost\fR has many \fBComments\fR, and of course we want to get a post\'s comments using \fBGET /post/1/comments\fR\. . .P Let\'s describe the route for our nested resource: . .IP "" 4 . .nf map\.resources(\'post\', function (post) { post\.resources(\'comments\'); });\. . .fi . .IP "" 0 . .P This routing map will provide the following routes: . .IP "" 4 . .nf $ compound routes post_comments GET /posts/:post_id/comments comments#index post_comments POST /posts/:post_id/comments comments#create new_post_comment GET /posts/:post_id/comments/new comments#new edit_post_comment GET /posts/:post_id/comments/:id/edit comments#edit post_comment DELETE /posts/:post_id/comments/:id comments#destroy post_comment PUT /posts/:post_id/comments/:id comments#update post_comment GET /posts/:post_id/comments/:id comments#show posts GET /posts posts#index posts POST /posts posts#create new_post GET /posts/new posts#new edit_post GET /posts/:id/edit posts#edit post DELETE /posts/:id posts#destroy post PUT /posts/:id posts#update post GET /posts/:id posts#show\. . .fi . .IP "" 0 . .P \fBUsing url helpers for nested routes\fR . .P To use routes like \fBpost_comments\fR you should call helper with param: parent resource or identifier before nested resource: . .IP "" 4 . .nf path_to\.post_comments(post) # /posts/1/comments path_to\.edit_post_comment(post, comment) # /posts/1/comments/10/edit path_to\.edit_post_comment(2, 300) # /posts/2/comments/300/edit . .fi . .IP "" 0 . .P \fBCustom actions in resourceful routes\fR . .P If you need some specific action to be added to your resource\-based route, use this example: . .IP "" 4 . .nf map\.resource(\'users\', function (user) { user\.get(\'avatar\', \'users#avatar\'); // /users/:user_id/avatar user\.get(\'top\', \'users#top\', {collection: true}); // /users/top }); . .fi . .IP "" 0 . .SH "EXAMPLES" To link \fBGET /signup\fR with \fBnew\fR action of \fBusers\fR controller: . .IP "" 4 . .nf map\.get(\'signup\', \'users#new\'); . .fi . .IP "" 0 . .P The following route will link \fBGET /\fR to the \fBindex\fR action of the\fBhome\fR controller: . .IP "" 4 . .nf map\.root(\'home#index\'); . .fi . .IP "" 0 . .SH "DEBUGGING" To debug routes of your compound application you can use \fBcompound routes\fR command (or shortcut \fBcompound r\fR)\. You can also specify optional argument for filtering by helper name or method, for example: . .IP "" 4 . .nf ~: ) compound r post posts GET /posts\.:format? posts#index posts POST /posts\.:format? posts#create new_post GET /posts/new\.:format? posts#new edit_post GET /posts/:id/edit\.:format? posts#edit post DELETE /posts/:id\.:format? posts#destroy post PUT /posts/:id\.:format? posts#update post GET /posts/:id\.:format? posts#show ~: ) compound r GET posts GET /posts\.:format? posts#index new_post GET /posts/new\.:format? posts#new edit_post GET /posts/:id/edit\.:format? posts#edit post GET /posts/:id\.:format? posts#show ~: ) compound r new new_post GET /posts/new\.:format? posts#new . .fi . .IP "" 0 . .SH "CONTRIBUTION" Compound use \fBrailway\-routes\fR npm package to provide routes functionality\. If you spotted an bug or have any suggestions or requests feel free to open issue at github\.com/1602/railway\-routes \fIhttps://github\.com/1602/railway\-routes/issues\fR . .SH "SEE ALSO" compound\-tools(3) compound\-tools(1) compound\-controller(3)