Microserviço profissional para envio de emails com templates personalizáveis, painel administrativo completo e autenticação por API Keys.
📖 Tutorial • 🔐 Autenticação • 🐛 Reportar Bug • 📄 Documentação
- Sobre o Projeto
- Características
- Tecnologias
- Instalação
- Arquitetura de Autenticação
- Configuração
- Como Usar
- Templates
- Painel Administrativo
- Deploy com Docker
- API Endpoints
- Estrutura do Projeto
- Segurança
- Boas Práticas de Segurança
- Troubleshooting
- Contribuindo
- Licença
Mail Sender é um microserviço completo e profissional para envio de emails transacionais, desenvolvido com Node.js, TypeScript e Express. Ele foi projetado para ser facilmente integrado a qualquer aplicação, oferecendo templates flexíveis e personalizáveis em MJML.
- ✅ Fácil Integração - API REST simples e documentada
- ✅ Templates Profissionais - Emails responsivos que funcionam em todos os clientes
- ✅ Totalmente Personalizável - Adapte cores, textos, botões e logos ao seu sistema
- ✅ Seguro - Autenticação por API Keys com hash bcrypt
- ✅ Monitoramento - Painel administrativo com estatísticas em tempo real
- ✅ Pronto para Produção - Deploy fácil com Docker ou Kubernetes
- ✅ Open Source - Código aberto e gratuito
- 🚀 API RESTful completa para envio de emails
- 🔐 Autenticação segura com API Keys (bcrypt hash)
- � Sistema de autenticação JWT para painel administrativo
- �📧 Templates MJML responsivos e profissionais
- 🎨 Altamente personalizável - cores, textos, botões, logos
- 📊 MongoDB para persistência de dados
- ⚡ Performance otimizada para produção
- 🔒 Login seguro com JWT (8 horas de expiração)
- 📈 Dashboard com métricas em tempo real
- 🔑 Gerenciamento de API Keys (criar, listar, revogar, ativar/desativar)
- ✉️ Teste de emails diretamente pelo painel
- 📜 Logs de atividade recentes
- 📱 Interface responsiva para todos os dispositivos
- 🎯 Auto-refresh de estatísticas
- Bem-vindo - Para onboarding de usuários
- Genérico - Para notificações, confirmações, alertas
- Componentes opcionais - botões, listas, tabelas, destaques
- Suporte a HTML em conteúdos
- Cores customizáveis por email
- Logo e branding personalizados
- ✅ Servidor local com hot reload
- ✅ Docker e Kubernetes prontos
- ✅ Variáveis de ambiente configuráveis
- ✅ TypeScript compilado para produção
|
|
|
- Node.js 18 ou superior
- MongoDB (local ou Atlas)
- Conta Gmail com App Password configurada
- Git
git clone https://github.com/RuanLopes1350/mailsender-ts.git
cd mailsender-tsnpm installCrie um arquivo .env na raiz do projeto:
# Servidor
PORT=5015
# MongoDB
DB_URL=mongodb://localhost:27017/mailsender
# Ou MongoDB Atlas:
# DB_URL=mongodb+srv://usuario:senha@cluster.mongodb.net/mailsender
# Email (Gmail)
SENDER_EMAIL=seu-email@gmail.com
SENDER_PASSWORD=sua-senha-ou-app-password
# Segurança
MASTER_KEY=sua-chave-mestra-secreta
JWT_SECRET=sua-chave-jwt-super-secreta-aqui
# Admin Inicial (credenciais do painel administrativo)
ADMIN_USERNAME=admin
ADMIN_PASSWORD=SuaSenhaSegura123- Altere
ADMIN_PASSWORDpara uma senha forte em produção - Nunca commite o arquivo
.envno Git - Use senhas diferentes para
MASTER_KEYeJWT_SECRET
- Acesse Google Account Security App Passwords
- Ative a Verificação em 2 etapas
- Vá em Senhas de app
- Selecione "Outro" e dê um nome (ex: "Mail Sender")
- Copie a senha gerada (16 caracteres)
- Cole no
.envcomoSENDER_PASSWORD
Desenvolvimento (com hot reload):
npm run devProdução:
npm run build
npm starthttp://localhost:5015/painel
Credenciais padrão:
- Usuário:
admin(ou o valor deADMIN_USERNAME) - Senha:
admin(ou o valor deADMIN_PASSWORD)
O Mail Sender implementa dois sistemas de autenticação independentes:
Usado para: Acesso ao painel administrativo e gerenciamento do sistema
Como funciona:
- Admin faz login com username/password
- Servidor valida credenciais e gera um JWT
- JWT é retornado ao cliente com validade de 8 horas
- Cliente envia o JWT no header
Authorization: Bearer <token> - Middleware
authMiddlewarevalida o token em cada requisição
Rotas protegidas por JWT:
GET /api/stats- EstatísticasGET /api/keys- Listar API KeysDELETE /api/keys/:name- Revogar chavePATCH /api/keys/:name/inativar- Desativar chavePATCH /api/keys/:name/reativar- Reativar chaveGET /api/emails/recentes- Listar emails
Payload do JWT:
{
"id": "507f1f77bcf86cd799439011",
"username": "admin",
"iat": 1730419200,
"exp": 1730448000
}Usado para: Integração de aplicações externas para enviar emails
Como funciona:
- Admin gera uma API Key com um nome identificador
- Sistema gera uma chave única e a retorna (hash é armazenado)
- Desenvolvedor usa a chave no header
x-api-key: <chave> - Middleware
apiKeyMiddlewarevalida a chave e identifica o usuário - Chave permanece válida até ser revogada ou desativada
Rotas protegidas por API Key:
POST /api/emails/send- Enviar emailGET /api/emails/meus- Listar meus emails
Formato da API Key:
mail_1234567890abcdef_ghijklmnopqrstuv
- JWT: Sessões temporárias para humanos (admin)
- API Key: Autenticação permanente para máquinas (aplicações)
Isso garante:
- ✅ Segurança granular por tipo de acesso
- ✅ Revogação independente (token expira, key persiste)
- ✅ Rastreabilidade (quem fez o quê)
- ✅ Facilidade de integração
Opção 1: Local
# Instale o MongoDB
# Windows: https://www.mongodb.com/try/download/community
# Linux: sudo apt install mongodb
# Mac: brew install mongodb-community
# Inicie o serviço
mongod
# Use no .env:
DB_URL=mongodb://localhost:27017/mailsenderOpção 2: MongoDB Atlas (Cloud - Grátis)
- Acesse MongoDB Atlas
- Crie uma conta e um cluster gratuito
- Configure o acesso (IP e usuário)
- Copie a connection string
- Use no
.env:
MONGODB_URI=mongodb+srv://usuario:senha@cluster.mongodb.net/mailsenderPor padrão, o sistema usa Gmail. Para usar outros provedores, edite src/config/mail.ts:
Outlook/Hotmail:
host: 'smtp-mail.outlook.com',
port: 587,SendGrid:
host: 'smtp.sendgrid.net',
port: 587,
auth: {
user: 'apikey',
pass: process.env.SENDGRID_API_KEY
}Via Painel:
- Acesse
http://localhost:5015/painel - Vá na aba "🔑 API Keys"
- Digite um nome (ex: "producao")
- Clique em "Gerar Chave"
- Copie e guarde a chave (não será mostrada novamente)
Via API:
curl -X POST http://localhost:5015/keys/generate \
-H "Content-Type: application/json" \
-d '{"name": "meu-app"}'curl -X POST http://localhost:5015/api/emails/send \
-H "Content-Type: application/json" \
-H "x-api-key: SUA_API_KEY" \
-d '{
"to": "destinatario@exemplo.com",
"subject": "Bem-vindo!",
"template": "bemvindo",
"data": {
"nomeSistema": "Meu Sistema",
"nome": "João Silva",
"mostrarBotao": true,
"textoBotao": "Acessar",
"urlBotao": "https://meuapp.com"
}
}'JavaScript/Node.js:
const response = await fetch('http://localhost:5015/api/emails/send', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'x-api-key': 'SUA_API_KEY'
},
body: JSON.stringify({
to: 'usuario@exemplo.com',
subject: 'Bem-vindo!',
template: 'bemvindo',
data: {
nomeSistema: 'Meu App',
nome: 'Maria',
mostrarBotao: true,
textoBotao: 'Começar',
urlBotao: 'https://app.com'
}
})
});
const result = await response.json();
console.log(result);Python:
import requests
response = requests.post('http://localhost:5015/api/emails/send',
headers={
'Content-Type': 'application/json',
'x-api-key': 'SUA_API_KEY'
},
json={
'to': 'usuario@exemplo.com',
'subject': 'Bem-vindo!',
'template': 'bemvindo',
'data': {
'nomeSistema': 'Meu App',
'nome': 'João'
}
}
)
print(response.json())📚 Ver Tutorial Completo com mais exemplos e todos os campos disponíveis.
O sistema oferece 2 templates profissionais e totalmente personalizáveis:
Email de boas-vindas para onboarding de usuários.
Campos principais:
nomeSistema- Nome do seu sistemanome- Nome do usuáriomensagem- Mensagem customizadamostrarBotao- Exibir botão (true/false)textoBotao/urlBotao- Configuração do botãocorPrimaria/corBotao- Cores personalizadaslogoUrl- Logo da empresa
Exemplo:
{
"to": "usuario@exemplo.com",
"subject": "Bem-vindo à Vitrine!",
"template": "bemvindo",
"data": {
"nomeSistema": "Vitrine",
"nome": "João Silva",
"mensagem": "Estamos felizes em tê-lo conosco!",
"mostrarBotao": true,
"textoBotao": "Acessar Plataforma",
"urlBotao": "https://vitrine.com/login"
}
}Template versátil para notificações, confirmações, alertas, etc.
Componentes disponíveis:
- Título e subtítulo
- Mensagem com HTML
- Caixa de destaque
- Lista de itens (bullets)
- Tabela de dados
- Até 2 botões
- Notas e avisos
Exemplo - Confirmação de Pedido:
{
"to": "cliente@exemplo.com",
"subject": "Pedido Confirmado",
"template": "generico",
"data": {
"titulo": "Pedido Confirmado! 🎉",
"nome": "Maria",
"mensagem": "Seu pedido foi confirmado com sucesso.",
"dados": [
{ "label": "Pedido", "valor": "#12345" },
{ "label": "Total", "valor": "R$ 299,90" }
],
"mostrarBotao": true,
"textoBotao": "Rastrear Pedido",
"urlBotao": "https://loja.com/rastreio/12345"
}
}Todos os campos e exemplos completos no TUTORIAL.md
Acesse http://localhost:5015/painel para gerenciar o sistema.
Login Obrigatório:
- O painel agora requer autenticação via JWT
- Após o login, o token é válido por 8 horas
- Use as credenciais configuradas nas variáveis de ambiente
- Estatísticas em tempo real
- Total de emails enviados (sucesso/falha)
- Requisições à API
- Emails recentes
- Auto-refresh a cada 30 segundos
- Gerar novas chaves com nomes personalizados
- Listar todas as chaves ativas
- Ativar/Desativar chaves temporariamente
- Revogar chaves permanentemente com confirmação
- Copiar chaves para clipboard
- Visualizar prefixo, status e data de criação
- Enviar emails de teste diretamente
- Escolher template (bemvindo/generico)
- Editor JSON com exemplos
- Info box dinâmica mostrando campos disponíveis
- Feedback imediato de sucesso/erro
- Últimas 10 requisições
- Método, endpoint e status
- Usuário que fez a requisição
- Códigos de status coloridos
- ✨ Design moderno com gradiente e animações
- 📱 Totalmente responsivo (mobile, tablet, desktop)
- 🎨 Tema claro otimizado para leitura
- 🔄 Atualização automática de dados
- 🎯 Navegação por tabs intuitiva
O projeto inclui configuração completa para deploy com Docker e docker-compose.
# Clone o repositório
git clone https://github.com/RuanLopes1350/mailsender-ts.git
cd mailsender-ts
# Configure o arquivo .env
cp .env.example .env
# Edite o .env com suas configurações
# Suba os containers
docker-compose up -dConfigure no arquivo .env:
DB_URL=mongodb://mongo:27017/mailsender
REDIS_HOST=redis
REDIS_PORT=6379
SENDER_EMAIL=seu-email@gmail.com
SENDER_PASSWORD=app-password
MASTER_KEY=sua-chave-mestra-secreta
JWT_SECRET=sua-chave-jwt-super-secreta
ADMIN_USERNAME=admin
ADMIN_PASSWORD=SuaSenhaSeguraDeProducao123
NODE_ENV=production
Consulte a pasta deploy/ para os manifests de Kubernetes:
deploy-backend.yaml- Deployment do backenddeploy-mongodb.yaml- Deployment do MongoDBdeploy-redis.yaml- Deployment do Redis
O sistema usa dois tipos de autenticação:
-
JWT Token - Para o painel administrativo
Authorization: Bearer SEU_JWT_TOKEN -
API Key - Para desenvolvedores enviarem emails
x-api-key: SUA_API_KEY
| Método | Endpoint | Autenticação | Descrição |
|---|---|---|---|
GET |
/api |
❌ | Health check |
GET |
/api/status |
❌ | Status do servidor |
POST |
/api/login |
❌ | Login admin (retorna JWT) |
POST |
/api/keys/generate |
❌ | Gerar API Key |
GET |
/api/stats |
🔑 JWT | Estatísticas gerais |
GET |
/api/keys |
🔑 JWT | Listar todas as chaves |
DELETE |
/api/keys/:name |
🔑 JWT | Revogar chave |
PATCH |
/api/keys/:name/inativar |
🔑 JWT | Desativar chave |
PATCH |
/api/keys/:name/reativar |
🔑 JWT | Reativar chave |
GET |
/api/emails/recentes |
🔑 JWT | Listar emails recentes |
POST |
/api/emails/send |
🔐 API Key | Enviar email |
GET |
/api/emails/meus |
🔐 API Key | Listar meus emails |
Health Check:
curl http://localhost:5015/apiLogin (obter JWT):
curl -X POST http://localhost:5015/api/login \
-H "Content-Type: application/json" \
-d '{
"username": "admin",
"password": "admin"
}'Resposta do Login:
{
"success": true,
"message": "Login bem sucedido!",
"token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...",
"user": {
"id": "507f1f77bcf86cd799439011",
"username": "admin",
"email": "admin"
}
}Gerar API Key:
curl -X POST http://localhost:5015/api/keys/generate \
-H "Content-Type: application/json" \
-d '{"name": "producao"}'Enviar Email (requer API Key):
curl -X POST http://localhost:5015/api/emails/send \
-H "Content-Type: application/json" \
-H "x-api-key: SUA_API_KEY" \
-d '{
"to": "usuario@exemplo.com",
"subject": "Teste",
"template": "bemvindo",
"data": {
"nomeSistema": "Meu App",
"nome": "João"
}
}'Listar API Keys (requer JWT):
curl http://localhost:5015/api/keys \
-H "Authorization: Bearer SEU_JWT_TOKEN"Desativar API Key (requer JWT):
curl -X PATCH http://localhost:5015/api/keys/producao/inativar \
-H "Authorization: Bearer SEU_JWT_TOKEN"Revogar API Key (requer JWT):
curl -X DELETE http://localhost:5015/api/keys/producao \
-H "Authorization: Bearer SEU_JWT_TOKEN"Sucesso (202):
{
"message": "E-mail enfileirado",
"info": {
"accepted": ["usuario@exemplo.com"],
"messageId": "<abc123@servidor.com>"
}
}Erro - API Key Inválida (401):
{
"message": "API key inválida ou não fornecida"
}Erro - Template Não Encontrado (500):
{
"message": "Falha ao enviar e-mail",
"error": "Template não encontrado"
}mailsender-ts/
├── src/
│ ├── config/
│ │ ├── DbConnect.ts # Conexão MongoDB
│ │ └── redis.ts # Configuração Redis
│ ├── mail/
│ │ ├── index.ts # Serviço de envio
│ │ └── templates/
│ │ ├── bemvindo.mjml # Template de boas-vindas
│ │ └── generico.mjml # Template genérico
│ ├── middleware/
│ │ └── requestLogger.ts # Log de requisições
│ ├── models/
│ │ ├── apiKey.ts # Model de API Keys
│ │ ├── email.ts # Model de emails
│ │ └── request.ts # Model de requisições
│ ├── services/
│ │ ├── emailService.ts # Serviço de emails
│ │ └── requestService.ts # Serviço de requisições
│ └── server.ts # Servidor Express (local)
├── public/
│ ├── index.html # Painel administrativo
│ ├── styles.css # Estilos do painel
│ └── script.js # Lógica do painel
├── .env # Variáveis de ambiente
├── .dockerignore # Arquivos ignorados no Docker
├── package.json # Dependências
├── tsconfig.json # Configuração TypeScript
├── TUTORIAL.md # Tutorial completo de uso
├── README.md # Este arquivo
├── docker-compose.yml # Script YAML para docker
└── dockerfile # Instruções para o docker
npm run dev # Servidor local com hot reload
npm run watch # Servidor com watch mode
npm run build # Compilar TypeScript
npm start # Executar versão compilada
npm run clean # Limpar pasta dist- Crie o arquivo MJML:
src/mail/templates/meutemplate.mjml- Use Handlebars para variáveis:
<mjml>
<mj-body>
<mj-section>
<mj-column>
<mj-text font-size="20px">
Olá {{nome}}!
</mj-text>
<mj-text>
{{{mensagem}}}
</mj-text>
{{#if mostrarBotao}}
<mj-button href="{{urlBotao}}">
{{textoBotao}}
</mj-button>
{{/if}}
</mj-column>
</mj-section>
</mj-body>
</mjml>- Use o template:
{
"template": "meutemplate",
"data": {
"nome": "João",
"mensagem": "Conteúdo aqui",
"mostrarBotao": true,
"textoBotao": "Clicar Aqui",
"urlBotao": "https://exemplo.com"
}
}- Variáveis:
{{nome}},{{email}} - HTML:
{{{conteudo}}}(3 chaves = HTML não escapado) - Condicionais:
{{#if condicao}}...{{/if}} - Loops:
{{#each itens}}{{this}}{{/each}} - Else:
{{#if}}...{{else}}...{{/if}}
- ✅ JWT Authentication - Tokens com expiração de 8 horas
- ✅ Bcrypt - Hash de senhas e API Keys com 15 salt rounds
- ✅ MongoDB - Armazenamento seguro de dados
- ✅ Variáveis de Ambiente - Credenciais não commitadas
- ✅ Validação - Entrada sanitizada em todas as rotas
- ✅ Autenticação Dupla - JWT para admin, API Keys para devs
- ✅ Logs - Rastreabilidade de todas as ações
- ✅ CORS - Configurável por ambiente
- 🔒 Use HTTPS em produção (obrigatório para JWT)
- � Altere as senhas padrão imediatamente
- 🎲 Gere JWT_SECRET forte (mínimo 32 caracteres aleatórios)
- ⏱️ Configure expiração de tokens adequadamente (padrão: 8h)
- �🚦 Implemente rate limiting para prevenir ataques
- 📊 Configure monitoramento (Sentry, DataDog)
- 🔄 Rotacione API Keys periodicamente
- 🛡️ Use WAF (Web Application Firewall)
- 📧 Configure SPF, DKIM e DMARC no domínio
- 🔐 Nunca exponha tokens em logs ou URLs
- 💾 Armazene tokens em localStorage/cookies HTTP-only
- Emails: Total, enviados, falhados
- Requisições: Total de chamadas à API
- API Keys: Quantidade de chaves ativas
- Atividade: Últimas requisições com detalhes
O sistema registra automaticamente:
- Todas as requisições (método, endpoint, status)
- Envios de email (sucesso/falha)
- Uso de API Keys
- Erros e exceções
Acesse os logs em tempo real na aba "📜 Logs Recentes" do painel.
1. Verifique as credenciais:
# Teste a conexão SMTP
node -e "require('./dist/config/mail.js').getTransport().then(t => t.verify().then(console.log))"2. Confira o App Password do Gmail:
- Deve ter 16 caracteres
- Sem espaços
- Verificação em 2 etapas ativada
3. Verifique os logs:
npm run dev
# Observe o console para erros1. Verifique se a chave está correta:
curl http://localhost:5015/keys
# Confirme que a chave existe2. Teste com nova chave:
curl -X POST http://localhost:5015/keys/generate \
-H "Content-Type: application/json" \
-d '{"name": "teste"}'1. Verifique a URL:
# Local
MONGODB_URI=mongodb://localhost:27017/mailsender
# Atlas
MONGODB_URI=mongodb+srv://usuario:senha@cluster.mongodb.net/mailsender2. Teste a conexão:
mongosh "mongodb://localhost:27017/mailsender"1. Verifique as credenciais:
ADMIN_USERNAME=admin
ADMIN_PASSWORD=admin2. Verifique se JWT_SECRET está configurado:
JWT_SECRET=uma-chave-secreta-longa3. Limpe o localStorage do navegador:
- Abra DevTools (F12)
- Vá em Application > Local Storage
- Limpe todos os dados
- Tente fazer login novamente
4. Verifique os logs do servidor:
npm run dev
# Observe erros relacionados a JWT ou admin- O token expira após 8 horas
- Faça login novamente no painel
- O sistema vai gerar um novo token automaticamente
1. Verifique se a chave está ativa:
curl http://localhost:5015/api/keys \
-H "Authorization: Bearer SEU_JWT_TOKEN"2. Verifique o header:
x-api-key: SUA_CHAVE_COMPLETA_AQUI
3. Reative a chave se estiver desativada
- Confirmação de pedido
- Notificação de envio
- Recuperação de carrinho
- Avaliação de produto
- Boas-vindas
- Confirmação de email
- Reset de senha
- Notificações de sistema
- Relatórios periódicos
- Matrícula confirmada
- Lembretes de aula
- Certificados
- Comunicados
- Boletins informativos
- Atualizações de produto
- Convites para eventos
Contribuições são bem-vindas! Para contribuir:
- Fork o projeto
- Crie uma branch para sua feature
git checkout -b feature/MinhaFeature
- Commit suas mudanças
git commit -m 'Adiciona MinhaFeature' - Push para a branch
git push origin feature/MinhaFeature
- Abra um Pull Request
- Use TypeScript
- Siga os padrões de código existentes
- Adicione testes se possível
- Documente mudanças significativas
- Atualize o README se necessário
Este projeto está sob a licença ISC. Veja o arquivo LICENSE para mais detalhes.
Ruan Lopes 💼 📧 |
Se este projeto foi útil para você, considere:
- ⭐ Dar uma estrela no GitHub
- 🐛 Reportar bugs ou sugerir features
- 📢 Compartilhar com outros desenvolvedores
- 💬 Contribuir com código ou documentação
Desenvolvido por Ruan Lopes
⭐ mailsender-ts ⭐