Skip to content

Commit

Permalink
criando o projeto
Browse files Browse the repository at this point in the history
  • Loading branch information
fabiosperotto committed Feb 2, 2023
0 parents commit 397fa83
Show file tree
Hide file tree
Showing 17 changed files with 739 additions and 0 deletions.
5 changes: 5 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
node_modules
build
npm-debug.log
.env
.DS_Store
13 changes: 13 additions & 0 deletions LICENSE.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
Copyright (c) <2023>, <fabiosperotto> <https://github.com/fabiosperotto/nodejs-minimal-server>

Permission to use, copy, modify, and distribute this software for any
purpose with or without fee is hereby granted, provided that the above
copyright notice and this permission notice appear in all copies.

THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
48 changes: 48 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@

# Minimal Node.js Server
Projeto para fins de estudos acadêmicos de como implementar uma aplicação web funcional com [Node.js](https://nodejs.org/) com o mínimo possível de dependências. É uma framework mínimo para o desenvolvimento de sites. O propósito é para que desenvolvedores(as) tenham contato com aplicações web com Node.js antes de desenvolver aplicações profissionais com Express, Axios ou outros frameworks, do ecossistema do Node.js.


## Instalação
Eftuar o download do projeto na última versão e:
```bash
$ npm install
```


## Estrutura
A estrutura deste framework mínimo procura se orientar pela arquitetura [MVC](https://pt.wikipedia.org/wiki/MVC):
- /app: possui implementações de controllers, models e alguns helpers para auxiliar no processamento de dados;
- /views: contém as páginas HTML da aplicação.
- routes.js: implementa uma parte do processamento de rotas da aplicação, chamando os controllers;
- server.js: configurações e ativação da aplicação.



## Como utilizar
O presente projeto já possui páginas de exemplos. Para criar uma página:
1. Crie o seu HTML no diretório /views, os arquivos possuem a extensão .ejs;
2. Crie uma entrada no arquivo routes.js para trar a requisição HTTP echame um controller responsável;
3. Crie o controller responsável em /app/controllers que finaliza o processamento da requisição + verbo HTTP e retorna a view deseja (criada no passo 1).



## Gerenciamento de Template
Para o presente projeto é utilizado para o gerenciamento de template o [EJS](https://ejs.co/). Em /app/helpers/pageProcess.js possui um exemplo de como realizar um HTTP response realizando a chamada do EJS para informar dados ao HTML. A partir deste arquivo, é possível trocar facilmente para outros gerenciadores de template.


## Sessões
Para o gerenciamento de sessões é utilizado o componente [client-sessions](https://github.com/mozilla/node-client-sessions). Configure a sessão e os cookies conforme exemplo em server.js. Depois poderá criar e acessar objetos em sessão, além de realizar a destruição da mesma. Verifique exemplos em /app/controllers/user.js


## Compatibilidade
- Node.js 12+;


## Contribuições
Não é necessário abrir uma issue para realizar discussões antes de entregar o seu pull request. Mas é importante apenas para deixar registrado para outros que está trabalhando em alguma funcionalidade. Sugestões de melhoria para este projeto:
- Mecanismo para retornar página de 404 quando alguma requisição inexistente for solicitada;
- Melhor tratamento de erros;
- Melhoria de qualidade de código ou da arquitetura de toda a aplicação;
- Melhoria nas documentações;
- Outros, fique a vontade em contribuir.
54 changes: 54 additions & 0 deletions app/controllers/site.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
const view = require('../helpers/pageProcess');
const helper = require('../helpers/dataProcess');

const routerSite = function (request, response){

dados = {};
if(request.minhaSessao.user){ //recuperando dados de sessao
dados.user = request.minhaSessao.user;
}

//processando rotas:

if(request.url === '/' && request.method === 'GET'){
return view.render(response, 'index', 200, dados);
}

if(request.url === "/contato" && request.method === "GET") {

dados.title = 'Fale Conosco';
return view.render(response, 'fale-conosco', 200, dados);
}

//exemplo de tratamento para requisicoes POST
if (request.url === "/contato" && request.method === "POST") {

//recebendo os dados, pegando dados do corpo da requisicao:
helper.collectDataRequest(request, result => {

console.log(result);
let dados = {};

if( (result.nome === '') || (result.mensagem === '') ){
dados.erro1 = true;
}else{
dados.nome = result.nome;
}

return view.render(response, 'fale-conosco', 200, dados);

});

}

//exemplo de processamento de requisicao com parametros (use expressoes regulares): /post/{id}:
if (request.url.match(/\/post\/([0-9]+)/) && request.method === "GET") {

// console.log(req.url.split("/"));
const id = request.url.split("/")[2]; //pegando o argumento id

}

};

module.exports = routerSite;
55 changes: 55 additions & 0 deletions app/controllers/user.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
const view = require('../helpers/pageProcess');
const helper = require('../helpers/dataProcess');
const crypto = require('crypto');

const routerUser = function (request, response){

if(request.url === "/login" && request.method === "POST"){

helper.collectDataRequest(request, result => {

let dados = {};
//verifica por campos obrigatorios nao preenchidos
if( (result.login === '') || (result.senha === '') ){
dados.erro1 = true;
return view.render(response, 'index', 200, dados);
}

let senha = result.senha;
//para gerar hashes de senhas, abaixo um exemplo para verificacao simples do informado pelo cliente e o que existe no backend (BD, outros)
let hash = crypto.createHash('sha256', 'app-key').update(senha).digest('hex');
//1234 = 03ac674216f3e15c761ee1a5e255f067953623c8b388b4459e13f978d7c846f4
//se a senha nao confere:
if(hash !== '03ac674216f3e15c761ee1a5e255f067953623c8b388b4459e13f978d7c846f4'){
dados.erro2 = true;
return view.render(response, 'index', 200, dados);
}

//se usuario existe, senha confere, exemplo:
if(hash === '03ac674216f3e15c761ee1a5e255f067953623c8b388b4459e13f978d7c846f4'){

let user = {
nome : 'Nome do Usuario',
email: result.login,
logged: true
};
request.minhaSessao.user = user;

response.statusCode = 302;
response.setHeader('Location','/');
response.end();
}

});
}

//session destroy:
if(request.url === "/logout" && request.method === "GET"){

request.minhaSessao.reset();
return view.render(response, 'index', 200, { fimsessao: true });
}

};

module.exports = routerUser;
36 changes: 36 additions & 0 deletions app/helpers/dataProcess.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
const querystring = require('querystring');

/**
* Exemplo de coleta de dados
* @param http.ClientRequest request
*
*/
collectDataRequest = function(request, callback){
let dados = '';
request.on("data", (pedaco) => {
dados += pedaco.toString();
});

request.on("end", () => {

callback(querystring.parse(dados));

});
}

/**
* Verifica se a sessao esta ativa. Redireciona para a pagina se sessao expirou
* @param http.ClientRequest request
* @param http.serverResponse response
* @returns boolean true se sessao ativa, false do contrario
*/
function isSessionActive(request, response){
if(request.minhaSessao.user){
return true;
}
response.statusCode = 302;
response.setHeader('Location','/logout');
response.end();
return false;
}
module.exports = {collectDataRequest, isSessionActive};
25 changes: 25 additions & 0 deletions app/helpers/pageProcess.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
const fs = require('fs');
const ejs = require('ejs');

/**
*
* @param http.serverResponse response
* @param string viewname nome do arquivo HTML, sem extensao
* @param int httpstatus http status code desejado
* @param object data contendo dados a serem inseridos dinamicamente no HTML
*/
function render(response, viewname, httpstatus, data){

//caso nao existir um title para a pagina, setar como default:
if(typeof data.title === 'undefined' ) data.title = 'Titulo da Pagina'; //title html tag

//definicao de qual view a ser chamada pelo nome do aquivo
const template = fs.readFileSync(__dirname + '/../../views/' + viewname + '.ejs');
const html = ejs.render(template.toString(), data);
response.statusCode = httpstatus;
response.setHeader('Content-Type', 'text/html');
response.end(html);

}

module.exports = {render};
Loading

0 comments on commit 397fa83

Please sign in to comment.