36 years old, from Vic (Catalonia, Spain)
Multimedia Engineer
Project Manage | Agile Lead | Hybrid Mobile App Dev @ Medialab Barcelona
Professor @ La Salle University Barcelona Campus
Yes, we do. Plus many other really good frameworks.
There is no silver bullet for constraints like:
MVC
RESTful CRUD actions
Traditional server side DB
Something that
Meteor is for NodeJS
whereas
Rails is for Ruby
A
Your customer should not. Well, not yet at least.
Meteor is currently at v0.7.2, which means:
Their guess: More than a month, less than a year. There are several (eleven?) people working full time on it. Meteor is definitely going to mature faster than any framework you could afford to build in-house, unless you're Google or Facebook.
Geoff Schmidt — @immir |
Matt DeBergalis — @debergalis |
Nick Martin — @n1mmy |
David Greenspan — @DavidLG |
Avital Oliver |
David Glasser — @glasser |
Jade Wang — @qiqing |
Kara Yu — @kara_yu |
Alice Yu — @yaliceme |
Slava Kim — @imslavko |
Emily Stark — @estark37 |
source: discovermeteor.com
source: discovermeteor.com
Meteor allows developers to build applications without worrying about the complexities of client-server connectivity.
source: meteorhacks.com
DDP (Distributed Data Protocol) is the protocol Meteor uses to communicate between client and server. All client-side subscription data, method calls and MongoDB operations are communicated as DDP messages. This is a very lightweight protocol. These messages can be inspected with a handy tool called ddp-analyzer.
While there is no official documentation, Meteor can handle HTTP Requests similar to other traditional applications. For example, file uploads to a Meteor app are sent as HTTP Requests.
Although Meteor runs on a single port, internally it works as two separate servers:
source: meteorhacks.com
The HTTP server is used to serve static files and HTTP requests. Meteor uses the connect Node.js module for this purpose.
The DDP server handles all publications, MongoDB operations, RPC and Meteor methods. Easy to read, it uses EJSON.
Meteor uses SockJS as the transport protocol. Nowadays, the DDP server is a SockJS server customized for Meteor.
Write your entire app in pure JavaScript. All the same APIs are available on the client and the server — including database APIs! — so the same code can easily run in either environment.
Don’t specify CSS, JS, or even HTML files to be included on any page. They are all just combined together, which sounds a little odd, but it makes things even quicker and easier to develop.
Meteor minifies and concatenates all JavaScript (including templates, which are pre-compiled as JavaScript) and CSS files for you in production, and serves them as static files—and not minified or combined in dev, for easier debugging.
Setting up user accounts is super easy, you can add support for a variety of common user account systems and there’s even a default login widget that you can reuse.
The interface itself even lets you seamlessly setup the app tokens for twitter, facebook, or other oauth services.
Email.send({
from: from,
to: to,
subject: subject,
text: text
});
on the server.
Just write your templates. They automatically update when data in the database changes. No more boilerplate redraw code to write. Supports any templating language.
Write your client code as if it were running
on the server and had direct access to the database.
No more loading your data from REST endpoints.
You can connect anything to Meteor, from native mobile apps to legacy databases to Arduinos.
Just implement the simple Distributed Data Protocol (DDP).
When a user makes a change, their screen updates immediately — no waiting for the server.
If the server rejects their request or executes it differently, the client is patched up with what actually happened.
Whenever you save changes in your project,
any web pages that are viewing your app
will automatically refresh.
(no more hitting refresh button in your browser after making changes)
When you push a new version, the new code
is seamlessly injected into each browser frame
in which the app is open.
Continuous Delivery Vn+1
One command to compile your entire application into a tarball.
Unpack it anywhere there's node.js, MongoDB and handlebars installed, run one command, and you're on the air.
You're never locked into a particular hosting provider; you have all the code for the platform.
+ any NPM package too
Meteor's Smart Packages are actually little programs that can inject code into the client or the server, or even hook into the bundler to preprocess your source.
Great care has been taken to give the core Meteor packages the minimal set of dependencies, so you can use your favorite templating, testing, or DOM manipulation frameworks.
Works offline - Persists the changes once network is restored
Built in Redundancy - Works on all popular browsers
and IE 7 +
Community - Incredible community already forming
Open Source - Open source, extremely well funded
https://github.com/meteor/meteor/tree/master
https://trello.com/b/hjBDflxp/meteor-roadmap
Meteor is not only for experts - Suitable for web beginners
The Perfect Match For Lean Startups - Certainly for rapid prototyping or building MVPs
$ parts install meteor
$ meteor create <app_name>
$ cd <app_name>
$ git init
$ git remote add <short_name> https://github.com/SalleMeteor/<app_name>.git
$ git remote -v
$ git pull <short_name> master
$ git add -A
$ git commit -m "<message_to_record>"
$ git push <short_name> master
$ git status
$ git clone <git_repository_URL>
$ curl https://install.meteor.com | /bin/sh
$ meteor create myapp
$ cd myapp
$ meteor
=> Meteor server running on: http://localhost:3000/
$ meteor create --example leaderboard
$ meteor create --example parties
$ meteor create --example todos
$ meteor create --example wordplay
$ meteor create myapp
$ meteor reset
$ meteor update
$ meteor help
...
Meteor's Command line tool is similar to rake (ruby) or jake (nodejs). This does all the background work of collecting, reading, compiling (pre-processing coffee/scss/less files) and minifying.
The command line tool also lets you perform app specific actions like interacting with your database, deploying/bundling you app, viewing logs, adding/removing packages, etc.
Packages are modules (or chunks) of pre-written code that you can use in your applications. There are 5 types of packages:
Small JavaScript programs that can inject code into the client or the server.
Can be used to add functionality to app (send emails, add user accounts) or extend the build process (precompile coffeescript or less files).
Examples: jQuery, Underscore, Backbone, Bootstrap, Accounts, Email...$ meteor list $ meteor list --using $ meteor add <package_name> $ meteor remove <package_name>
...
You can write an entire app in just one file, but it's not recommended.
Meteor provides you an efficient way to structure and organize your files. There are no script tags, no loader libraries and no dependency management.
Just put files in appropriate folders and Meteor will pick it up automatically.
Meteor provides us with isClient and isServer checks to separate out what part of the code needs to be executed on the server and what needs to be executed inside the browser.
if (Meteor.isClient) {
someFunction = function() {
// your code goes here
};
...
}
if (Meteor.isServer) {
Meteor.startup(function() {
// code to run on server at startup
});
...
}
$git clone https://github.com/SachaG/Void.git
Meteor has a set of rules that dictate the order in which files are executed. Instead of using dependency management, you should organize your files according to these rules:
HTML files in a Meteor app are different from regular HTML files. There is no <!doctype>, no <script> tags and no css imports.
There are three root level tags:
<head></head>
<body></body>
<template></template>
Templates are regular HTML expressions, but with the ability to embed expressions (variables, values of properties, etc.).
Today, the only templating system that has been packaged for Meteor is Handlebars.
Without Handlebars
$("div").text(name + "is " + age + " years old.");
With Handlebars
<div>{{ name }} is {{ age }} years old.</div>
<body>
{{> hello}}
</body>
<template name="hello">
<h1>Hello World!</h1>
</template>
<template> is a root level tag that Meteor provides us to create templates. Template names should be unique.
{{#if currentUser }}
<p>Secret View</p>
{{else}}
<p>Access Denied</p>
{{/if}}
{{#unless newUser}}
<p>Welcome back</p>
{{else}}
<p>Good to have you here</p>
{{/unless}}
{{#each contacts}}
<p>Name: {{fullName}}</p>
{{/each}}
Inside the each block, the value of this is set to the currently iterated object. There is no need to call this.fullNameTo interact with templates with javascript, Meteor converts all template sections into JavaScript functions that are accessible via a global Template namespace.
To provide data to templates, add functions on
Template.template_name
object.
In HTML file | In Javascript file |
---|---|
|
|
|
|
To respond to user inputs, we need to listen for events like click, double click, keypress, etc. The event and the target element is specified as a string value by a space. This forms the key of the object. The callback function that gets executed when this event occurs is defined as the value.
Template.hello.events({
"click input": function(e, t) {
alert("You clicked the input.");
}
});
Reactive Programming - results will be automatically recalculated whenever data associated with that piece of code changes.
Reactive Data Sources (DS) - is any provider of data that follows Meteor’s contract for providing reactivity.
Deps.autorun(function () {
Meteor.subscribe("messages", Session.get("currentRoomId"));
});
// Causes the function passed to Deps.autorun to be re-run, so
// that the 'messages' subscription is moved to the room "home".
Session.set("currentRoomId", "home");
// Client side: show the number of players online.
var frag = Meteor.render(function () {
return "<p>There are " + Players.find({online: true}).count() +
" players online.</p>";
});
document.body.appendChild(frag);
// Server side: find all players that have been idle for a while,
// and mark them as offline. The count on the screen will
// automatically update on all clients.
Players.update({idleTime: {$gt: 30}}, {$set: {online: false}});
// List the titles of all of the posts that have the tag
// "frontpage". Keep the list updated as new posts are made, as tags
// change, etc. Display the selected post differently.
var frag = Meteor.renderList(
Posts.find({tags: "frontpage"}),
function(post) {
var style = Session.equals("selectedId", post._id) ? "selected" : "";
// A real app would need to quote/sanitize post.name
return '<div class="' + style + '">' + post.name + '</div>';
});
document.body.appendChild(frag);
// Select a post. This will cause only the selected item and the
// previously selected item to update.
var somePost = Posts.findOne({tags: "frontpage"});
Session.set("selectedId", somePost._id);
Deps.autorun(function () {
if (Meteor.status().connected) {
console.log("connected");
} else {
console.log("disconnected");
}
});
Session.set("currentTask", "Learn Meteor");
Session.set("currentPage", "documentationPage");
...
Session.get("currentTask"); // output: "Learn Meteor"
Session.get("currentPage"); // output: "documentationPage"
...
Session.equals("currentTask", "Learn Meteor"); // output: true
Synchronized Collections (anywhere):
Contacts = new Meteor.Collection("contacts");
Unsynchronized (local) Collections (client only):
Contacts = new Meteor.Collection(null);
Contacts.insert({ name: "Marc" });
Contacts.find();
Contacts.find({ name: "Marc" });
Contacts.findOne({ name: "Marc" });
Contacts.update({ name: "Marc" }, { $set: { name: "Joan" }});
Contacts.remove({ name: "Marc" });
Reset Database from CLI$ meteor reset
accounts-base, accounts-password, accounts-facebook, accounts-github, accounts-google, accounts-meetup, accounts-twitter, accounts-weibo, etc.
accounts-ui
$ meteor add accounts-base accounts-password accounts-ui
<template name="header">
{{loginButtons}}
</template>
{{#if currentUser}}
<h1>Logged in</h1>
{{/if}}
Meteor.user();
Meteor.userId();
Accounts.ui.config({
passwordSignupFields: 'USERNAME_ONLY'
});
$ meteor remove autopublish
$ meteor remove insecure
Meteor.publish("myContacts", function(name) { //return Contacts.find(); // to get all contacts
return Contacts.find({ username: name }); });
Meteor.subscribe("myContacts", "cramrov");
Contacts.allow({ insert: function(userId, doc) { return !!userId }, update: function(userId, doc) { if(userId && doc.userId == userId) return true; return false; }, remove: function(userId, doc) { if(userId && doc.userId == userId) return true; return false; } });
Contacts.deny({ remove: function (userId, doc) { //can't remove locked contacts return doc.locked; } });
Meteor.methods({
foo: function (arg1, arg2) {
// .. do stuff ..
if (you want to throw an error)
throw new Meteor.Error(404, "Can't find my pants");
return "some return value";
},
bar: function () {
// .. do other stuff ..
return "baz";
}
});
// async call
Meteor.call('foo', 1, 2, function (error, result) { ... } );
// sync call
var result = Meteor.call('bar');
check(username, String);
$ meteor deploy myapp.meteor.com
$ meteor deploy www.myapp.com // CNAME pointing to origin.meteor.com
$ meteor bundle myapp.tgz
$ demeteorizer [options]
$ ./bundle-static.py
"Meteorite is a Meteor version manager and package manager. It provides an easy way to run different versions of meteor, use non-core packages, and to install packages from the
Atmosphere ( atmosphere.meteor.com ) package repository."
Meteorite adds the mrt command.
$ npm install -g meteorite
OR
$ sudo -H npm install -g meteorite (if you need root permissions)
$ mrt create myapp
$ mrt add <package_name>
$ mrt remove <package_name>
$ mrt run --production
...and the Meteor-Style-Guide too
discovermeteor.com/translations
Best Learning Resources for Meteor.js
+ easy to start with
+ fast development
+ open platform
+ the (mobile) web is a big market
+ one language for front and back end
- still in rapid development / no stable release yet
- may be too high level for some (complex) cases
- still needs more packages -> Atmosphere
- scalability is important
Try it out and you will see its awesomeness!
Thanks for listening!
Questions?
marcr@salleurl.edu