Aplicações de tempo real com Meteor.js
-
Upload
rafael-sales -
Category
Technology
-
view
1.993 -
download
5
description
Transcript of Aplicações de tempo real com Meteor.js
Rafael Sales
Real-Time AppsWith Meteor
DBDBCPU
WEBPresentation
HTTP
DBDBCPU
WEBPresentation
HTTP
DBDB CPUCloud
Data
?CPU
DBDBCPU
WEBPresentation
HTTP
DBDB CPUCloud
Data
?CPU
DBDB CPU
Client/Server
Data
RPC, NFS...
CPU
Como seria esse protocolo?
• APIs são assinaturas de conjuntos de dados
• Cache local dos dados no cliente
• Chamada de métodos ao servidor (RPC)
• Cliente pode simular métodos do servidormodificando seu cache local de dados
Meteor é uma plataforma open-source para criar aplicações web modernas
Real-time
Reactive programming
JavaScript
Real-time
Reactive programming
JavaScript
Inclusive a API do Banco de Dados
Mesma API disponível no cliente e servidor
Cliente e servidor escritos em JavaScript
Só JavaScript
Inclusive a API do Banco de Dados
Mesma API disponível no cliente e servidor
Cliente e servidor escritos em JavaScript
Só JavaScript
// código compartilhadoif (Meteor.isServer) { // código do servidor}if (Meteor.isClient) { // código do cliente}
// código compartilhadoif (Meteor.isServer) { // código do servidor}if (Meteor.isClient) { // código do cliente}
API do Banco de Dados no cliente?
API do Banco de Dados no cliente?
Messages = new Meteor.Collection("messages"); Messages.insert({ text: "Hello world!" }); Messages.find();
Messages = new Meteor.Collection("messages"); Messages.insert({ text: "Hello world!" }); Messages.find();
O cliente faz assinatura de um conjunto dedados que deseja manter-se atualizado
Sincronizaçãode dados
O servidor irá manter tais conjuntosatualizados nos clientes
Sem mais...
function getLastMessages() { $.get('/last-messages', callback);}
E como faz?
/server/chat.jsMeteor.publish("messages-to-me", function () { return Messages.find({ to: myId });});
/client/chat.jsMeteor.subscribe("messages-to-me");
automaticamente atualizadosquando o BD é alterado
Partes atualizáveis são escritas com templates
Atualização da página em tempo real
Sem mais...
$.get('/messages', function(responseBody) { $('#messages').html(responseBody);});
JavaScript haters
Sem mais...$.get('/messages', function(messages) { var list = $('ul'); list.empty();
$.each(messages, function(index, msg) { var newItem = $('<li/>', { text: msg.text }); list.append(newItem); });});
JavaScript Lovers
E como faz?/client/index.html
<template name="container"> <ul> {{#each messages}} <li> {{text}} </li> {{/each}} </ul></template>
/client/chat.jsTemplate.container.messages = function() { return Messages.find();};
Alterações de dados efetuadas no cliente refletema UI ao mesmo tempo que são enviadas ao servidor
Compensaçãode latência
Cópia dos dados dos clientes e o UI são corrigidoscaso o servidor rejeite as alterações
Sem mais...
$.post('/messages/create', parameters, function(newMsg) { var li = $('<li/>', { text: newMsg.text }); $('ul').append(li);});
=> alteração no código => build do JS => envia para cliente e atualiza
Hot Code Pushes
Aplicação e suas dependências empacotadas
Pacote da aplicaçãoindependente
Executa em ambientes que suportam node.js
DDP - Distributed Data Protocol
Interoperabilidade
Injetam código no cliente e/ou servidor
Smart Packages
É possível substituir pacotes padrão,como o de templating (Handlebars.js)
Meteorite: package manager for Atmosphere
Exemplo: Leaderboard
<template name="leaderboard"> <div class="leaderboard"> {{#each players}} {{> player}} {{/each}} </div>
{{#if selected_name}} <div class="details"> <div class="name">{{selected_name}}</div> <input type="button" class="inc” value="Give 5 points" /> </div> {{else}} <div class="none">Click a player to select</div> {{/if}}</template>
HTML
<template name="leaderboard"> <div class="leaderboard"> {{#each players}} {{> player}} {{/each}} </div>
{{#if selected_name}} <div class="details"> <div class="name">{{selected_name}}</div> <input type="button" class="inc” value="Give 5 points" /> </div> {{else}} <div class="none">Click a player to select</div> {{/if}}</template>
HTML
<template name="player"> <div class="player {{selected}}"> <span class="name">{{name}}</span> <span class="score">{{score}}</span> </div></template>
<template name="player"> <div class="player {{selected}}"> <span class="name">{{name}}</span> <span class="score">{{score}}</span> </div></template>
JSPlayers = new Meteor.Collection(“players");
if (Meteor.isServer) { Meteor.startup(function () { if (Players.find().count() === 0) { var names = ["Ada Lovelace", "Grace Hopper", "Marie Curie", "Carl Friedrich Gauss", "Nikola Tesla", "Claude Shannon"];
for (var i = 0; i < names.length; i++) Players.insert({ name: names[i], score: Random.floor(Random.fraction()*10)*5 }); } });}
JSPlayers = new Meteor.Collection(“players");
if (Meteor.isClient) { Template.leaderboard.players = function() { return Players.find({}, { sort: { score: -1, name: 1 }}); };
Template.leaderboard.selected_name = function() { player = Players.findOne(Session.get("selected_player")); return player && player.name; }; Template.leaderboard.events({ 'click input.inc': function() { Players.update(Session.get("selected_player"),
{ $inc: { score: 5 }}); } }); Template.player.events({ 'click': function() { Session.set("selected_player", this._id); } });}
meteor.com
github.com/meteor/meteor