Tudo bem, esta é uma pergunta bastante ampla e definitivamente não sou especialista, mas farei o meu melhor aqui.
TL;DR
routes
são controladores que informam qual lógica executar quando um usuário navega em seu navegador para um determinado caminho em seu aplicativo, incluindo quais visualizações renderizar e quais dados enviar para essas visualizaçõesmodels
são apenas isso - modelos de dados em seu aplicativomodule.exports =
informa a um arquivo o que exatamente ele "exporta", que é o código que precisa ser executado ou acessível a partir do arquivo principal do aplicativo.require(..)
inclui um módulo. Você pode definir isso em uma variável para poder chamar funções de módulo mais tarde, ou simplesmente executar uma função se isso for tudomodule.exports
retorna.
A combinação dessas técnicas pode ajudá-lo a criar uma estrutura sólida para qualquer um dos seus aplicativos.
Resposta longa
Express fornece uma estrutura sólida para estruturar seu aplicativo Node.js. O Node é completamente independente do Express, mas devido à popularidade do Express, eles praticamente andam de mãos dadas. Uma vez instalado, o Express pode ser usado para gerar um projeto web de scaffold (com opções) para você construir em cima, se desejar.
Controladores
Um projeto gerado criará
/routes/index.js
, que (se você entende de MVC) é essencialmente seu principal controlador . Uma rota em express é escrita assim:app.get('/path', function(req, res, next){ .. } );
Vamos detalhar:nossa variável de aplicativo (app) está sendo informada de que em uma solicitação GET para
'/path'
para executar uma função de retorno de chamada anônima com req, res, next
variáveis (solicitação, resposta, retorno de chamada, respectivamente). Acho útil pensar nisso como um manipulador de eventos personalizado. É importante observar neste ponto que também podemos chamar
app.post
com a mesma sintaxe para postagens em uma URL em vez de gets. Em nosso retorno de chamada anônimo, lidamos com todos os dados recebidos e renderizamos uma visualização para o usuário. É aqui que a maior parte da minha lógica de negócios acaba, então, na verdade, faz sentido NÃO usar funções anônimas aqui. Aqui está um exemplo de um retorno de chamada básico que exibe apenas uma página inicial:
app.get('/', function(req, res, next){
//some business logic
res.render('views/home');
});
Quando o usuário tenta GET o caminho do índice do nosso aplicativo (
/
), nós simplesmente renderizamos nosso home
view que, da raiz do nosso projeto, é armazenada em um views
pasta. Mas e se quisermos modularizar isso para que não declaremos todas as nossas rotas em nosso
app.js
principal ou server.js
? Usamos
module.exports = ..
em nossos módulos para dizer ao nosso servidor o que exatamente incluir. No meu controlador, eu exporto uma única função que recebe o aplicativo como argumento e usa isso para definir nossas rotas assim:Controllers/User.js
module.exports = function(app){
app.get('/users', function(req, res){
var users = req.db.collection('users').find();
if (!users) {
console.log("no users found");
res.redirect('/');
} else {
res.render('users/index', {users : users});
}
});
};
Não se preocupe com o
req.db
código, anexo o banco de dados à solicitação em meu aplicativo, mas isso não é feito por padrão. Simplesmente entenda que estou recebendo uma lista de 'usuários' aqui e redirecionando o usuário para o índice do meu aplicativo, se não houver nenhum. Modelos
O Mongoose nos fornece uma ótima interface para escrever modelos. Com o mangusto, escrever modelos é um processo de três etapas:
- Definir um esquema
- Definir a lógica do modelo
- Gere e exporte o modelo
Aqui está um exemplo de um
User
modelo:Modelos/User.js
var mongoose = require('mongoose'),
userSchema = new mongoose.Schema({
name: { type: String, required: true },
joinDate: {type: Date, default: date.now }
}),
User = mongoose.model('user', userSchema);
module.exports = user;
Aplicativo de servidor
module.exports
é usado para nos ajudar a definir alguma modularidade para nossa base de código. Quando executamos um aplicativo de nó, estamos executando um único arquivo JavaScript (você já viu esse arquivo com server.js
ou app.js
). Para evitar que esse arquivo fique muito grande com vários modelos e rotas, usamos
require(module)
para incluir código de outros arquivos JS. module
no nosso caso seria um caminho para o módulo que queremos exigir. Se você tiver a seguinte estrutura de documentos:| Controllers
- User.js
| Models
- User.js
| Views
app.js
Para incluir seu controlador de usuário de
app.js
, você escreveria:require('./Controllers/User')
. Como nossos módulos controladores simplesmente exportam funções, podemos chamar essa função imediatamente após nossa instrução require simplesmente adicionando parênteses no final (com quaisquer parâmetros necessários). Incluindo meus controladores fica assim:require('./Controllers/User')(app)
Estou passando o aplicativo real, porque meu módulo (abaixo) simplesmente exporta uma função que adiciona lógica de negócios às rotas do meu aplicativo. Isso só precisa ser chamado e nunca usado, então não capturo meu controlador como uma variável para chamar métodos posteriormente.
Incluir modelos é um pouco diferente, pois podemos querer realizar alguma operação que nosso modelo define. Podemos fazer isso alterando um pouco nosso código require:
var User = require('./Models/User');
Agora podemos chamar métodos do nosso modelo User sempre. O Mongoose nos oferece muitas funcionalidades básicas de graça:
User.find({}, function(err, users){ .. });
A função acima irá encontrar todos os nossos usuários e, em seguida, executar uma função anônima com um potencial
err
(é nulo se não houver problemas) e, em seguida, uma lista de nossos usuários no formato JSON. Bem bacana. A combinação de todos esses conceitos é como você cria um aplicativo da Web básico usando Express e Node.js. Por favor, deixe-me saber nos comentários se houver algo que eu possa esclarecer sobre como eu uso o Express. Este é um conhecimento muito superficial, e sugiro pesquisar a documentação e examinar os plug-ins para estender os recursos de seus aplicativos. Boa sorte!