SlideShare a Scribd company logo
OSLO
Meteor routing
28 September 2015
Iron Router
> meteor add iron:router
Concepts
• Client and Server
Define a route that only should run on the server, or a route
that should only run on the client
• Reactivity
Route functions and most hooks are run in a reactive
computation
First route
Router.route('/', function () {
this.render('Home');
});
Rendering Templates
<template name="Post">
<h1>Post: {{title}}</h1>
</template>
Router.route('/post/:_id', function () {
this.render('Post');
});
Rendering Templates with Data
Router.route('/post/:_id', function () {
this.render('Post', {
data: function () {
return Posts.findOne({_id: this.params._id});
}
});
});
Layouts
<template name="ApplicationLayout">
<header>
<h1>{{title}}</h1>
</header>
<aside>
{{> yield "aside"}}
</aside>
<article>
{{> yield}}
</article>
<footer>
{{> yield "footer"}}
</footer>
</template>
Router.route('/post/:_id',
this.layout('ApplicationLayout');
// render the Post template into the "main"
// {{> yield}}
this.render('Post');
// render the PostAside into the yield "aside"
// {{> yield "aside"}}
this.render('PostAside', {to: 'aside'});
// render the PostFooter into the yield "footer"
// {{> yield "footer"}}
this.render('PostFooter', {to: 'footer'});
});
Setting Region Data Contexts
Router.route('/post/:_id', function () {
this.layout('ApplicationLayout', {
data: function () { return Posts.findOne({_id: this.params._id}) }
});
this.render('Post', {
data: function () { return Posts.findOne({_id: this.params._id})
});
this.render('PostAside', {
to: 'aside',
data: function () { return Posts.findOne({_id: this.params._id})
});
});
Route Parameters
// given the url: "/post/5?q=s#hashFrag"
Router.route('/post/:_id', function () {
var id = this.params._id;
var query = this.params.query;
// query.q -> "s"
var hash = this.params.hash; // "hashFrag"
});
• Parameters
• Query string
• Hash
Using Links
With JavaScript
Router.go('/one');
With Redirects
Router.route('/one', function () {
this.redirect('/two');
});
Links to Server Routes
Router.route('/download/:filename', function () {
this.response.end('some file contentn');
}, {where: 'server'});
<a href="/download/name">Download File</a>
Named Routes
Access by nameRouter.route('/posts/:_id', function () {
this.render('Post');
}, {
name: 'post.show'
});
Router.routes[‘post.show’];
Router.go(‘post.show');
Router.go('post.show', {_id: 1},
{query: 'q=s', hash: 'hashFrag'});
Template Lookup
The router will by default look for a template named ItemsShow
Router.route('/items/:_id', {name: 'items.show'});
Router.setTemplateNameConverter(function (str) { return str; });
Set the converter
Path and Link Template Helpers
pathFor
<a href="{{pathFor route='post.show' data=getPost query='q=s' hash='frag'}}">Post Show</a>
urlFor
For route /posts/1 would generate http://mysite.com/posts/1
linkTo
The linkTo helper automatically generates the html for an anchor tag along with the route path for the given route, parameters, hash and
query.
{{#linkTo route="post.show" data=getData query="q=s" hash="hashFrag" class="my-cls"}}
Subscriptions
Router.route('/post/:_id', function () {
// add the subscription handle to our waitlist
this.wait(Meteor.subscribe('item', this.params._id));
// OR
this.subscribe('item', this.params._id).wait();
// OR
subscriptions: function() {
// returning a subscription handle or an array of subscription handles
return Meteor.subscribe('item', this.params._id);
},
if (this.ready()) {
this.render();
} else {
this.render('Loading');
}
});
The waitOn Option
Router.route('/post/:_id', {
// this template will be rendered until the subscriptions are ready
loadingTemplate: 'loading',
waitOn: function () {
// return one handle, a function, or an array
return Meteor.subscribe('post', this.params._id);
},
action: function () {
this.render('myTemplate');
}
});
Same effect but automatically short-circuits your route action and any before hooks, and renders a loadingTemplate instead
Server Routing
Router.route('/download/:file', function () {
// NodeJS request object
var request = this.request;
// NodeJS response object
var response = this.response;
this.response.end('file download contentn');
}, {where: 'server'});
Restful Routes
Router.route('/webhooks/stripe', { where: 'server' })
.get(function () {
// GET /webhooks/stripe
})
.post(function () {
// POST /webhooks/stripe
})
.put(function () {
// PUT /webhooks/stripe
})
The waitOn Option
Router.route('/post/:_id', {
// this template will be rendered until the subscriptions are ready
loadingTemplate: 'loading',
waitOn: function () {
// return one handle, a function, or an array
return Meteor.subscribe('post', this.params._id);
},
action: function () {
this.render('myTemplate');
}
});
Same effect but automatically short-circuits your route action and any before hooks, and renders a loadingTemplate instead
Hooks
Hooks that are running in reactive computation, provide a way
to plug into the process of running a route, typically to customize
rendering behavior or perform some business logic
Router.onBeforeAction(function () {
only: [‘admin'],
if (!Meteor.userId()) {
this.render('Login');
} else {
this.next();
}
});
Available Hooks
• onRun
• onRerun
Must call this.next()
• onBeforeAction
Must call this.next()
• onAfterAction
• onStop
Controller
Betefits
• Inheritance
• Organization
PostController = RouteController.extend({
layoutTemplate: 'PostLayout',
template: 'Post',
waitOn: function () {
return Meteor.subscribe('post', this.params._id);
},
data: function () { return Posts.findOne({_id: this.params._id}) },
action: function () {
this.render();
}
});
Iron.Router loading order
1. Route
2. RouteController
3. Router
Reactive State Variables
Router.route('/posts/:_id', {name: 'post'});
PostController = RouteController.extend({
action: function () {
// set the reactive state variable "postId" with a value
// of the id from our url
this.state.set('postId', this.params._id);
this.render();
}
});
controller.state.get('postId')
Legacy Browser Support
http://localhost:3000/items/5?q=s#hashFrag
http://localhost:3000/#/items/5?q=s&__hash__=hashFrag
Router.route('/items/:_id', function () {
var id = this.params._id; // "5"
var query = this.params.query; // {q: "s"}
var hash = this.params.hash; // "hashFrag"
});
Route Options
Router.route('/post/:_id', {
name: 'post.show',
path: '/post/:_id',
controller: 'CustomController',
template: 'Post',
layoutTemplate: 'ApplicationLayout',
yieldRegions: {
'MyAside': {to: 'aside'},
'MyFooter': {to: 'footer'}
},
subscriptions: function() {
this.subscribe('items');
// add the subscription to the waitlist
this.subscribe('item', this.params._id).wait();
},
waitOn: function () {
return Meteor.subscribe('post', this.params._id);
},
//This function can also be used by hooks and plugins.
data: function () {
return Posts.findOne({_id: this.params._id});
},
onRun: function () {},
onRerun: function () {},
onBeforeAction: function () {},
onAfterAction: function () {},
onStop: function () {},
action: function () {
// render all templates and regions for this route
this.render();
}
});
Global Default Options
Router.configure({
layoutTemplate: 'ApplicationLayout',
template: 'DefaultTemplate'
});
Plugins
Router.plugin('dataNotFound', {notFoundTemplate: 'notFound'});
For Specific Routes
Router.plugin('dataNotFound', {
notFoundTemplate: 'NotFound',
except: ['server.route']
// or only: ['routeOne', 'routeTwo']
});
Creating Plugins
Iron.Router.plugins.loading = function (router, options) {
// this loading plugin just creates an onBeforeAction hook
router.onBeforeAction('loading', options);
};
Packages
meteor add multiply:iron-router-progress
meteor add reywood:iron-router-ga
joshowens:accounts-entry
…
Questions?

More Related Content

PDF
Best practice routing in Meteor.js and beyond
PPTX
ngNewRouter
PPTX
Angular js introduction
PPTX
Neoito — Routing and navigation in Angular
PDF
Workshop 13: AngularJS Parte II
PDF
Angular Extreme Performance - V2
PPS
Struts Java I I Lecture 8
PDF
Meteor presentation
Best practice routing in Meteor.js and beyond
ngNewRouter
Angular js introduction
Neoito — Routing and navigation in Angular
Workshop 13: AngularJS Parte II
Angular Extreme Performance - V2
Struts Java I I Lecture 8
Meteor presentation

Similar to Meteor iron:router (20)

PDF
Reactive Application Using METEOR
PPTX
Reactive application using meteor
PDF
ODP
code-camp-meteor
PPTX
Meteor + Ionic Introduction
PPTX
Building a production ready meteor app
PPTX
Meteor Meet-up San Diego December 2014
PDF
The End of Dinosaurs happened because of [a] Meteor
PPTX
Flow router, components and props
PDF
Director x Backbone = :)
PPTX
Meteor Day Talk
PPTX
Plone FSR
PDF
Learn more about React Router & it's properties
PDF
PDF
PDF
Meteor.js Workshop by Dopravo
PDF
Architecture, Auth, and Routing with uiRouter
PDF
Angular js routing options
PDF
The Meteor Framework
Reactive Application Using METEOR
Reactive application using meteor
code-camp-meteor
Meteor + Ionic Introduction
Building a production ready meteor app
Meteor Meet-up San Diego December 2014
The End of Dinosaurs happened because of [a] Meteor
Flow router, components and props
Director x Backbone = :)
Meteor Day Talk
Plone FSR
Learn more about React Router & it's properties
Meteor.js Workshop by Dopravo
Architecture, Auth, and Routing with uiRouter
Angular js routing options
The Meteor Framework
Ad

Recently uploaded (20)

PPTX
TLE Review Electricity (Electricity).pptx
PPTX
Spectroscopy.pptx food analysis technology
PPTX
KOM of Painting work and Equipment Insulation REV00 update 25-dec.pptx
PDF
Heart disease approach using modified random forest and particle swarm optimi...
PDF
Agricultural_Statistics_at_a_Glance_2022_0.pdf
PPTX
Programs and apps: productivity, graphics, security and other tools
PPTX
OMC Textile Division Presentation 2021.pptx
PDF
Encapsulation_ Review paper, used for researhc scholars
PPTX
Group 1 Presentation -Planning and Decision Making .pptx
PDF
Univ-Connecticut-ChatGPT-Presentaion.pdf
PDF
Unlocking AI with Model Context Protocol (MCP)
PDF
Spectral efficient network and resource selection model in 5G networks
PPTX
1. Introduction to Computer Programming.pptx
PDF
Architecting across the Boundaries of two Complex Domains - Healthcare & Tech...
PDF
Per capita expenditure prediction using model stacking based on satellite ima...
PDF
Approach and Philosophy of On baking technology
PDF
August Patch Tuesday
PDF
Empathic Computing: Creating Shared Understanding
PDF
Assigned Numbers - 2025 - Bluetooth® Document
PDF
Profit Center Accounting in SAP S/4HANA, S4F28 Col11
TLE Review Electricity (Electricity).pptx
Spectroscopy.pptx food analysis technology
KOM of Painting work and Equipment Insulation REV00 update 25-dec.pptx
Heart disease approach using modified random forest and particle swarm optimi...
Agricultural_Statistics_at_a_Glance_2022_0.pdf
Programs and apps: productivity, graphics, security and other tools
OMC Textile Division Presentation 2021.pptx
Encapsulation_ Review paper, used for researhc scholars
Group 1 Presentation -Planning and Decision Making .pptx
Univ-Connecticut-ChatGPT-Presentaion.pdf
Unlocking AI with Model Context Protocol (MCP)
Spectral efficient network and resource selection model in 5G networks
1. Introduction to Computer Programming.pptx
Architecting across the Boundaries of two Complex Domains - Healthcare & Tech...
Per capita expenditure prediction using model stacking based on satellite ima...
Approach and Philosophy of On baking technology
August Patch Tuesday
Empathic Computing: Creating Shared Understanding
Assigned Numbers - 2025 - Bluetooth® Document
Profit Center Accounting in SAP S/4HANA, S4F28 Col11
Ad

Meteor iron:router

  • 2. Iron Router > meteor add iron:router
  • 3. Concepts • Client and Server Define a route that only should run on the server, or a route that should only run on the client • Reactivity Route functions and most hooks are run in a reactive computation
  • 4. First route Router.route('/', function () { this.render('Home'); });
  • 5. Rendering Templates <template name="Post"> <h1>Post: {{title}}</h1> </template> Router.route('/post/:_id', function () { this.render('Post'); });
  • 6. Rendering Templates with Data Router.route('/post/:_id', function () { this.render('Post', { data: function () { return Posts.findOne({_id: this.params._id}); } }); });
  • 7. Layouts <template name="ApplicationLayout"> <header> <h1>{{title}}</h1> </header> <aside> {{> yield "aside"}} </aside> <article> {{> yield}} </article> <footer> {{> yield "footer"}} </footer> </template> Router.route('/post/:_id', this.layout('ApplicationLayout'); // render the Post template into the "main" // {{> yield}} this.render('Post'); // render the PostAside into the yield "aside" // {{> yield "aside"}} this.render('PostAside', {to: 'aside'}); // render the PostFooter into the yield "footer" // {{> yield "footer"}} this.render('PostFooter', {to: 'footer'}); });
  • 8. Setting Region Data Contexts Router.route('/post/:_id', function () { this.layout('ApplicationLayout', { data: function () { return Posts.findOne({_id: this.params._id}) } }); this.render('Post', { data: function () { return Posts.findOne({_id: this.params._id}) }); this.render('PostAside', { to: 'aside', data: function () { return Posts.findOne({_id: this.params._id}) }); });
  • 9. Route Parameters // given the url: "/post/5?q=s#hashFrag" Router.route('/post/:_id', function () { var id = this.params._id; var query = this.params.query; // query.q -> "s" var hash = this.params.hash; // "hashFrag" }); • Parameters • Query string • Hash
  • 10. Using Links With JavaScript Router.go('/one'); With Redirects Router.route('/one', function () { this.redirect('/two'); }); Links to Server Routes Router.route('/download/:filename', function () { this.response.end('some file contentn'); }, {where: 'server'}); <a href="/download/name">Download File</a>
  • 11. Named Routes Access by nameRouter.route('/posts/:_id', function () { this.render('Post'); }, { name: 'post.show' }); Router.routes[‘post.show’]; Router.go(‘post.show'); Router.go('post.show', {_id: 1}, {query: 'q=s', hash: 'hashFrag'});
  • 12. Template Lookup The router will by default look for a template named ItemsShow Router.route('/items/:_id', {name: 'items.show'}); Router.setTemplateNameConverter(function (str) { return str; }); Set the converter
  • 13. Path and Link Template Helpers pathFor <a href="{{pathFor route='post.show' data=getPost query='q=s' hash='frag'}}">Post Show</a> urlFor For route /posts/1 would generate http://mysite.com/posts/1 linkTo The linkTo helper automatically generates the html for an anchor tag along with the route path for the given route, parameters, hash and query. {{#linkTo route="post.show" data=getData query="q=s" hash="hashFrag" class="my-cls"}}
  • 14. Subscriptions Router.route('/post/:_id', function () { // add the subscription handle to our waitlist this.wait(Meteor.subscribe('item', this.params._id)); // OR this.subscribe('item', this.params._id).wait(); // OR subscriptions: function() { // returning a subscription handle or an array of subscription handles return Meteor.subscribe('item', this.params._id); }, if (this.ready()) { this.render(); } else { this.render('Loading'); } });
  • 15. The waitOn Option Router.route('/post/:_id', { // this template will be rendered until the subscriptions are ready loadingTemplate: 'loading', waitOn: function () { // return one handle, a function, or an array return Meteor.subscribe('post', this.params._id); }, action: function () { this.render('myTemplate'); } }); Same effect but automatically short-circuits your route action and any before hooks, and renders a loadingTemplate instead
  • 16. Server Routing Router.route('/download/:file', function () { // NodeJS request object var request = this.request; // NodeJS response object var response = this.response; this.response.end('file download contentn'); }, {where: 'server'});
  • 17. Restful Routes Router.route('/webhooks/stripe', { where: 'server' }) .get(function () { // GET /webhooks/stripe }) .post(function () { // POST /webhooks/stripe }) .put(function () { // PUT /webhooks/stripe })
  • 18. The waitOn Option Router.route('/post/:_id', { // this template will be rendered until the subscriptions are ready loadingTemplate: 'loading', waitOn: function () { // return one handle, a function, or an array return Meteor.subscribe('post', this.params._id); }, action: function () { this.render('myTemplate'); } }); Same effect but automatically short-circuits your route action and any before hooks, and renders a loadingTemplate instead
  • 19. Hooks Hooks that are running in reactive computation, provide a way to plug into the process of running a route, typically to customize rendering behavior or perform some business logic Router.onBeforeAction(function () { only: [‘admin'], if (!Meteor.userId()) { this.render('Login'); } else { this.next(); } });
  • 20. Available Hooks • onRun • onRerun Must call this.next() • onBeforeAction Must call this.next() • onAfterAction • onStop
  • 21. Controller Betefits • Inheritance • Organization PostController = RouteController.extend({ layoutTemplate: 'PostLayout', template: 'Post', waitOn: function () { return Meteor.subscribe('post', this.params._id); }, data: function () { return Posts.findOne({_id: this.params._id}) }, action: function () { this.render(); } });
  • 22. Iron.Router loading order 1. Route 2. RouteController 3. Router
  • 23. Reactive State Variables Router.route('/posts/:_id', {name: 'post'}); PostController = RouteController.extend({ action: function () { // set the reactive state variable "postId" with a value // of the id from our url this.state.set('postId', this.params._id); this.render(); } }); controller.state.get('postId')
  • 24. Legacy Browser Support http://localhost:3000/items/5?q=s#hashFrag http://localhost:3000/#/items/5?q=s&__hash__=hashFrag Router.route('/items/:_id', function () { var id = this.params._id; // "5" var query = this.params.query; // {q: "s"} var hash = this.params.hash; // "hashFrag" });
  • 25. Route Options Router.route('/post/:_id', { name: 'post.show', path: '/post/:_id', controller: 'CustomController', template: 'Post', layoutTemplate: 'ApplicationLayout', yieldRegions: { 'MyAside': {to: 'aside'}, 'MyFooter': {to: 'footer'} }, subscriptions: function() { this.subscribe('items'); // add the subscription to the waitlist this.subscribe('item', this.params._id).wait(); }, waitOn: function () { return Meteor.subscribe('post', this.params._id); }, //This function can also be used by hooks and plugins. data: function () { return Posts.findOne({_id: this.params._id}); }, onRun: function () {}, onRerun: function () {}, onBeforeAction: function () {}, onAfterAction: function () {}, onStop: function () {}, action: function () { // render all templates and regions for this route this.render(); } });
  • 26. Global Default Options Router.configure({ layoutTemplate: 'ApplicationLayout', template: 'DefaultTemplate' });
  • 27. Plugins Router.plugin('dataNotFound', {notFoundTemplate: 'notFound'}); For Specific Routes Router.plugin('dataNotFound', { notFoundTemplate: 'NotFound', except: ['server.route'] // or only: ['routeOne', 'routeTwo'] });
  • 28. Creating Plugins Iron.Router.plugins.loading = function (router, options) { // this loading plugin just creates an onBeforeAction hook router.onBeforeAction('loading', options); };
  • 29. Packages meteor add multiply:iron-router-progress meteor add reywood:iron-router-ga joshowens:accounts-entry …