O documento apresenta uma introdução ao framework JavaScript Backbone.js, discutindo seu propósito de separar as responsabilidades entre modelo, vista e roteador, e como ele pode ser usado para estruturar projetos com maior responsividade. Também aborda tópicos como estruturação de projetos com Backbone, uso de views, modelos, coleções e roteadores, além de testabilidade do framework.
4. Backbone.js
• Componente Javascript
– Pode ser usado com CoffeeScript ou TypeScript
• MV* - Separação de responsabilidades entre modelo,
view, e roteador (mais ou menos um MVC)
• Um dos frameworks JS mais usados no mundo
• Bem documentado
• Open source (hospedado no github)
6. BackboneJS x <algum server>
• Prós
– Maior responsividade da aplicação
– Mais cara de aplicação, menos cara de site
– Código de interface concentrado mais perto do navegador
– Interfaces mais ricas
• Contras
– Ferramental ainda em evolução
– Curva de aprendizado
– Hoje ainda é mais lento para desenvolver
7. Cenário
• Maior responsividade da aplicação
• Testabilidade
• Documentação dos componentes
• Estabilidade dos componentes
• Rodar na internet e na intranet
• Navegadores modernos
• Milhares de usuários
9. Separação da IG e comportamento
• Uso do Backbone.js e Mustache.js, depois substituído
por Handlebars (uma extensão do Mustache)
• Backbone.js provê a ideia de views e templates,
facilitando a manipulação da view
12. Consumidor da view
require [
'views/AppView'
],
(AppView) ->
appView = new AppView
el:$("#app-container")
appView.render()
13. Separação do código da app e das bibliotecas
• Uso de RequireJS para modularização (usando AMD)
• Separação das pastas da aplicação entre:
– Bibliotecas
– Aplicação
– Testes
19. Backbone.js não existe sozinho
• Dependência direta do Underscore (ou Lo-Dash)
• Para manipulação da view utiliza jQuery (ou Zepto)
– Recomendamos também o Handlebars para templates
20. Roteadores (Backbone.Router)
• Intercepta as urls e encaminha para um método
• Cuida do histórico (back, forward, etc)
• Geralmente só há um roteador na app (grande
potencial para problemas se você ignorar essa regra)
• Pode ficar bem grande
• Geralmente passa o controle para alguma view
22. Views
• Não é bem uma view, é mais ou menos um controller
• Em geral busca os dados em algum model ou
collection, e renderiza o html (com um template ou
não)
• Intercepta os eventos do html e se comunica com o
model ou collection, que por sua vez, falam com o
servidor
25. Modelos (Backbone.Model)
• Representam o modelo de negócio, e também os
dados a serem exibidos/editados
• Tem conexão direta com o servidor, um modelo sabe
se recuperar no server
• Representam uma única entidade
27. Coleções (Backbone.Collection)
• Representam uma coleção de entidades do modelo
• Permitem obter diversas entidades de uma única vez,
com ou sem filtros na consulta
• Permite criar, excluir, atualizar entidades
30. Backbone é bastante testável
• Testes de unidade com diversos frameworks possíveis,
como QUnit, Jasmine e outros (usamos Jasmine com
Jasmine-JQuery)
• Os testes não batem no server, não há necessidade de
rodar o lado do servidor para os testes passarem
• Faça testes de unidade!
• Faça também testes de integração dirigindo o browser
31. Testando a renderização da view
define ['views/ListaEventosItemView'], (ListaEventosItemView) ->
element = $("<div></div>")
subject = null
model = new Backbone.Model()
model.set
"Id":7
"Nome":"Evento 1"
"Data":"2013-03-14T12:56:59.0934901-03:00"
"QuantidadeVagas":100
describe 'Lista Eventos Item View', ->
beforeEach ->
subject = new ListaEventosItemView { el:element, model:model }
describe 'Ao renderizar', ->
beforeEach ->
subject.render()
it 'deve exibir o id do evento', ->
expect(subject.$el.html()).toContain('7')
it 'deve exibir o nome do evento', ->
expect(subject.$el.html()).toContain('Evento 1')
it 'deve exibir a data do evento já formatada', ->
expect(subject.$el.html()).toContain('3/14/2013')
32. Mockando Ajax
describe 'Ao salvar o modelo com sucesso', ->
beforeEach ->
spyOn($, "ajax").andCallFake (parametros) ->
parametros.success
Id:1
Nome:"Evento 1"
Data:"2013-03-14T12:56:59.0934901-03:00"
QuantidadeVagas:100
it 'deve redirecionar para a listagem de eventos', ->
$("#salvar", subject.el).click()
expect(subject.exibirLista).toHaveBeenCalled()
$el = Um objeto Jquery (ou Zepto) cacheado para o elemento da view. Uma referência à mão para não precisar pesquisar o elemento no DOM toda hora
AMD - Asynchronous Module DefinitionEspecifica um mecanismo para definição de módulos, de forma que esses módulos e suas referências possam ser carregadas assincronamente.O AMD veio do desejo de ter um formato que fosse melhor que “escrever um monte de tags script com dependências implícitas onde você precisa manualmente pedir”.
O atributo data-main é um atributo especial que o RequireJS checará para iniciar o carregamento dos scripts.
O jQuery não está especificado no shim porque o jQuery suporta AMD (existe a definição do módulo no arquivo jQury.js)
Jasmine-Jquery = é uma extensão do Jasmine (facilita osasserts e a manioulação do HTML, CSS
Um SPY faz um mock de qualquer função e rastreia as chamadas a elas e todos os parâmetros/argumentos enviados