New revolutionary framework
- First of its kind
- Beautifully written
- Extensively Documented
- Super Easy to learn
Why use Meteor?
Realtime Apps
- Update all connected clients effortlessly
- Realtime by default
Rapid Prototyping
- Roll out your MVP when everyone is setting their build systems
- All you need is meteor
- Compatible with variety of 3rd party JS libraries
Fast Iteration
- Flexibility to do things your way
- Create modular apps with packages
- Make rapid iteration your second nature
Highly opinionated
- All your js and CSS is minified and concatenated
- All templates are compiled to JS and minified and concatenated with rest of JS
- All JS files are wrapped in IEFs
- Globals for exports
Yet very flexible
- Modular to its core
- Based on simple but powerful principles
What makes Meteor so special?
Realtime Apps by default
FullStack Framework
All you need is Meteor
if (Meteor.isClient) {
console.log("Logging on Client");
}
if (Meteor.isServer) {
console.log("Logging on Server");
}
if (Meteor.isCordova) {
console.log("Logging on Phonegap");
}
Database Everywhere
Todos = new Mongo.Collection('todos'); // runs on both client and server
if (Meteor.isServer) {
//runs only on server
Meteor.startup(function() {
Todos.insert({body: 'Very important thing to do', done: false});
});
}
if (Meteor.isClient) {
//runs only on client
var todos = Todos.find({done: false}).forEach(function(todo) {
Todos.update({_id: todo._id}, {$set: {done: true} });
});
Reactive
&
Declarative
Escape from Callback Hell
Out of the box compatibility with 3rd party JS
- npm
- bower
- Jquery Plugins
- d3
- svg
Packages
- Core to write modular code
- Provide a way around almost all meteor's opinions
- Easy to write and test
Package.describe({
summary: "My awesome package or a sub app, or whatever",
version: "0.0.1",
name: "username:package",
git: 'https://github.com/username/package'
});
Tutorial:
Simple Notice Board App
Finished Product
- Allow user login with email/password
- Create and delete notices
- Likes for Notices
- Realtime - All clients see new updates immediately
- An iOS app
App Structure
client - Loaded on client only
client/compatibility - Isn't wrapped in IEFs
server - Loaded on server only
lib - Loaded first in directory
public - For static assets on client
private - For static assets on server
tests - For tests, not loaded anywhere
Code Load Order
- Code in deepest directory
- Code in 'lib' directory
- Code sorted by filename
- Code with name matching 'main.*'
Blaze
- Client side champ
- Responsible for reactively change Templates
- Independent of Templating Engine used
Spacebars
- Default templating engine of meteor
- "Inspired" by handlebars
- Flexible and brain dead simple
<template name="noticeList">
<ul>
{{#each notices}}
<li>
<span class="notice">{{body}}</span>
<span class="delete"><i class="glyphicon glyphicon-trash"></i></span>
<span class="like ">
<i class="glyphicon glyphicon-heart"></i>
<span class="like-count">{{likeCount}}</span>
</span>
</li>
{{/each}}
</ul>
</template>
Interaction with Templates
Helpers - Template data providers, arbitrary methods etc
Events - Well, event handlers
Template.noticeList.helpers({
notices: function() {
return Notices.find({}, {sort: {like_count: -1}});
}
});
Template.noticeList.events({
"click .like": function(e) {
Notices.update(this._id, {$inc: {like_count: 1}});
},
"click .delete": function(e) {
Notices.remove(this._id);
}
});
Database Connectivity
Create Collection
Use it
Notices = new Mongo.Collection('notices');
Notices.find({}, {sort: {like_count: -1}});
Notices.insert({
body: e.currentTarget.value,
like_count: 0
});
Notices.update("some_id", {$inc: {like_count: 1}});
Notices.remove("some_id");
Database Security
Allow / Deny callbacks for Collections
- All the changes to data (from client) pass through deny and allow callbacks (in that order)
- If any deny callback returns true, or any allow callback returns false, the change is prohibited
Notices.allow({
insert: function(userId, doc) {
return true;
},
update: function(userId, doc) {
return true;
},
remove: function(userId, doc) {
return true;
}
});
Database Control
Control what and how much goes to Clients
Publishers / Subscribers
- Publish the data you want for the users you want
- Publishes Live Queries : The data on client updates when it changes on server
Meteor.publish('all_notices', function() {
return Notices.find();
});
Template.noticeList.created = function() {
Meteor.subscribe('all_notices');
};
Authentication
- Official packages for adding authentication with various mediums
- Add auth with email, Facebook, Twitter etc with minimal effort
//SIGN UP
Accounts.createUser({
email: email,
password: password
}, function(err) {
if (err) {
console.log("Creating user", err);
}
});
//LOG IN
Meteor.loginWithPassword(
email,
password,
function(err) {
if (err) {
console.log("Login:", err);
}
})
Mobile Apps
- Create a basic cordova app with one command
- Easily add cordova plugins
- Use same codebase across various platforms
$ meteor add-platform ios
$ meteor build ios
Digging a Little Deeper
DDP
- Distributed Data Protocol
- Really simple protocol to allow talking over sockets consistent
- It just defines names for messages sent over sockets
- Allows writing your own client or server (or both) for meteor
Alternative Metor Clients
Say Thank You DDP!
Android
iOS
Xamarin
Javascript
Others
Tracker
Man behind reactivity
- Weighs about 1 KB
- Say hello to TRP (Transparent Reactive Programming) in Javascript
- Allows interaction between reactive data providers and consumers with no boilerplate
- e.g interaction between the data from the database and HTML templates in Meteor
Live Query
- Make a query for some data, and get the updates whenever that data changes
- At present only support Mongodb for production use
Fibers
Synchronous (like) Development for Nodejs
- Non blocking Synchronous Javascript on Server
- Actually, asynchronous code but without callbacks
- Completely abstracted by Meteor's APIs
- Don't worry, we can still use async code with little to no extra work
Some Common Pitfalls
Load order
Or lack of control over it
- Unconfigurable load order
- Rename or put files in sub-dirs to control their load order
No fixed Structure for Code
- Not enough opinion in this regard
- server, client, lib are decided, but what goes inside them is upto the dev
- Provides flexibility, but have seen people doing abusing this
Namespacing
- Everything (global) in App namespace
- Globals in a file are exported to app namespace
- Can cause confusion combined with lack of control on load order
Globals revived
Getting over
Pitfalls
Use packages
- Divide app into modular packages
- Use umbrella packages for dependency management
- Allow control over code load order, exports, and easy testing
Create a Global Namespace
Use models
- Use meteor's `transform` to create classes for your data
- Put reusable code with the data
- Keep the code DRY
Make use of Code Sharing
- Use common code for validation on both client and server
- Create structural units for your code
- e.g share validation code
- Can keep them as static functions with your models
Thank You
Happy Hacking with Meteor :)
@bitspook