|
| 1 | +# Aplicação Java de Exemplo |
| 2 | + |
| 3 | +Uma aplicação REST API Spring Boot abrangente para uma plataforma de mídia social com operações CRUD completas para posts, comentários e curtidas. |
| 4 | + |
| 5 | +## Visão Geral do Projeto |
| 6 | + |
| 7 | +Esta é uma aplicação Spring Boot pronta para produção construída com as seguintes especificações: |
| 8 | + |
| 9 | +- **Nome do Pacote**: `com.contoso.socialapp` |
| 10 | +- **ID do Artefato**: `socialapp` |
| 11 | +- **ID do Grupo**: `com.contoso` |
| 12 | +- **Tipo de Pacote**: `jar` |
| 13 | +- **Versão Java**: OpenJDK 21 |
| 14 | +- **Ferramenta de Build**: Gradle |
| 15 | +- **Banco de Dados**: SQLite (embarcado) |
| 16 | +- **Porta**: 8080 |
| 17 | + |
| 18 | +### Dependências do Projeto |
| 19 | + |
| 20 | +- **Spring Boot 3.2.5**: Framework principal |
| 21 | +- **Spring Web**: Endpoints da RESTful API |
| 22 | +- **Spring Data JPA**: Operações de banco de dados |
| 23 | +- **Spring Boot Actuator**: Monitoramento da aplicação |
| 24 | +- **Spring Boot Validation**: Validação de entrada |
| 25 | +- **SQLite**: Banco de dados embarcado |
| 26 | +- **Hibernate Community Dialects**: Suporte ao SQLite |
| 27 | +- **Springdoc OpenAPI**: Documentação da API (Swagger UI) |
| 28 | +- **Lombok**: Redução de código boilerplate |
| 29 | + |
| 30 | +### Estrutura do Projeto |
| 31 | + |
| 32 | +```text |
| 33 | +src/ |
| 34 | +├── main/ |
| 35 | +│ ├── java/ |
| 36 | +│ │ └── com/ |
| 37 | +│ │ └── contoso/ |
| 38 | +│ │ └── socialapp/ |
| 39 | +│ │ ├── SocialAppApplication.java # Classe principal da aplicação |
| 40 | +│ │ ├── config/ |
| 41 | +│ │ │ ├── WebConfig.java # Configuração CORS |
| 42 | +│ │ │ └── OpenApiConfig.java # Configuração Swagger/OpenAPI |
| 43 | +│ │ ├── controller/ |
| 44 | +│ │ │ ├── HealthController.java # Endpoints de saúde |
| 45 | +│ │ │ ├── PostController.java # Gerenciamento de posts |
| 46 | +│ │ │ └── CommentController.java # Gerenciamento de comentários e curtidas |
| 47 | +│ │ ├── model/ |
| 48 | +│ │ │ ├── Post.java # Entidade Post |
| 49 | +│ │ │ ├── Comment.java # Entidade Comment |
| 50 | +│ │ │ ├── Like.java # Entidade Like |
| 51 | +│ │ │ └── dto/ # Objetos de Transferência de Dados |
| 52 | +│ │ ├── repository/ |
| 53 | +│ │ │ ├── PostRepository.java # Acesso a dados de posts |
| 54 | +│ │ │ ├── CommentRepository.java # Acesso a dados de comentários |
| 55 | +│ │ │ └── LikeRepository.java # Acesso a dados de curtidas |
| 56 | +│ │ └── service/ |
| 57 | +│ │ ├── PostService.java # Lógica de negócio de posts |
| 58 | +│ │ └── CommentService.java # Lógica de negócio de comentários |
| 59 | +│ └── resources/ |
| 60 | +│ ├── application.properties # Configuração da aplicação |
| 61 | +│ └── data.sql # Dados de exemplo (opcional) |
| 62 | +└── test/ |
| 63 | + └── java/ |
| 64 | + └── com/ |
| 65 | + └── contoso/ |
| 66 | + └── socialapp/ |
| 67 | + └── SocialAppApplicationTests.java # Testes de integração |
| 68 | +``` |
| 69 | + |
| 70 | +## Funcionalidades |
| 71 | + |
| 72 | +- ✅ API RESTful completa para operações de mídia social |
| 73 | +- ✅ Gerenciamento de posts (Criar, Ler, Atualizar, Excluir) |
| 74 | +- ✅ Sistema de comentários com operações CRUD completas |
| 75 | +- ✅ Funcionalidade de curtir/descurtir |
| 76 | +- ✅ Banco de dados SQLite com JPA/Hibernate |
| 77 | +- ✅ Documentação OpenAPI/Swagger |
| 78 | +- ✅ CORS habilitado para localhost e GitHub Codespaces |
| 79 | +- ✅ Configuração dinâmica de URL do servidor |
| 80 | +- ✅ Endpoints de verificação de saúde |
| 81 | +- ✅ Integração com Spring Boot Actuator |
| 82 | +- ✅ Tratamento abrangente de erros |
| 83 | +- ✅ Validação de entrada com Bean Validation |
| 84 | + |
| 85 | +## Início Rápido |
| 86 | + |
| 87 | +### Pré-requisitos |
| 88 | + |
| 89 | +Consulte a documentação [README](../../README.md) para preparação. |
| 90 | + |
| 91 | +### 1. Configuração do Ambiente |
| 92 | + |
| 93 | +Primeiro, defina a variável de ambiente `$REPOSITORY_ROOT`. |
| 94 | + |
| 95 | +```bash |
| 96 | +# bash/zsh |
| 97 | +REPOSITORY_ROOT=$(git rev-parse --show-toplevel) |
| 98 | +``` |
| 99 | + |
| 100 | +```powershell |
| 101 | +# PowerShell |
| 102 | +$REPOSITORY_ROOT = git rev-parse --show-toplevel |
| 103 | +``` |
| 104 | + |
| 105 | +Em seguida, navegue até o diretório java. |
| 106 | + |
| 107 | +```bash |
| 108 | +cd $REPOSITORY_ROOT/complete/java |
| 109 | +``` |
| 110 | + |
| 111 | +### 2. Construir a Aplicação |
| 112 | + |
| 113 | +```bash |
| 114 | +# Tornar gradlew executável (se necessário) |
| 115 | +chmod +x ./gradlew |
| 116 | + |
| 117 | +# Construir o projeto |
| 118 | +./gradlew build |
| 119 | +``` |
| 120 | + |
| 121 | +### 3. Executar a Aplicação |
| 122 | + |
| 123 | +```bash |
| 124 | +# Iniciar a aplicação usando Gradle |
| 125 | +./gradlew bootRun |
| 126 | + |
| 127 | +# Alternativa: Executar o arquivo JAR diretamente |
| 128 | +# java -jar build/libs/socialapp-0.0.1-SNAPSHOT.jar |
| 129 | +``` |
| 130 | + |
| 131 | +### 4. Verificar se a Aplicação está Executando |
| 132 | + |
| 133 | +```bash |
| 134 | +# Verificar endpoint de saúde |
| 135 | +curl http://localhost:8080/api/health |
| 136 | + |
| 137 | +# Resposta esperada: {"status":"healthy"} |
| 138 | +``` |
| 139 | + |
| 140 | +### 5. Acessar Documentação da API |
| 141 | + |
| 142 | +Abra seu navegador e navegue para: |
| 143 | + |
| 144 | +- **Swagger UI**: [http://localhost:8080/swagger-ui.html](http://localhost:8080/swagger-ui.html) |
| 145 | +- **OpenAPI JSON**: [http://localhost:8080/v3/api-docs](http://localhost:8080/v3/api-docs) |
| 146 | + |
| 147 | +## Endpoints da API |
| 148 | + |
| 149 | +### Saúde e Boas-vindas |
| 150 | + |
| 151 | +- `GET /api/health` - Endpoint personalizado de verificação de saúde |
| 152 | +- `GET /api/welcome` - Endpoint de mensagem de boas-vindas |
| 153 | + |
| 154 | +### Gerenciamento de Posts |
| 155 | + |
| 156 | +- `GET /api/posts` - Obter todos os posts |
| 157 | +- `GET /api/posts/{id}` - Obter post específico por ID |
| 158 | +- `POST /api/posts` - Criar um novo post |
| 159 | +- `PATCH /api/posts/{id}` - Atualizar um post existente |
| 160 | +- `DELETE /api/posts/{id}` - Excluir um post |
| 161 | + |
| 162 | +### Gerenciamento de Comentários |
| 163 | + |
| 164 | +- `GET /api/posts/{postId}/comments` - Obter todos os comentários de um post |
| 165 | +- `GET /api/posts/{postId}/comments/{commentId}` - Obter comentário específico |
| 166 | +- `POST /api/posts/{postId}/comments` - Adicionar um comentário a um post |
| 167 | +- `PATCH /api/posts/{postId}/comments/{commentId}` - Atualizar um comentário |
| 168 | +- `DELETE /api/posts/{postId}/comments/{commentId}` - Excluir um comentário |
| 169 | + |
| 170 | +### Gerenciamento de Curtidas |
| 171 | + |
| 172 | +- `POST /api/posts/{postId}/like` - Curtir um post |
| 173 | +- `DELETE /api/posts/{postId}/like` - Descurtir um post |
| 174 | + |
| 175 | +### Spring Boot Actuator |
| 176 | + |
| 177 | +- `GET /actuator/health` - Indicador de saúde do Spring Boot |
| 178 | +- `GET /actuator/info` - Informações da aplicação |
| 179 | + |
| 180 | +## Testando a API |
| 181 | + |
| 182 | +### Usando Exemplos de cURL |
| 183 | + |
| 184 | +#### Criar um Post |
| 185 | + |
| 186 | +```bash |
| 187 | +curl -X POST http://localhost:8080/api/posts \ |
| 188 | + -H "Content-Type: application/json" \ |
| 189 | + -d '{ |
| 190 | + "title": "Meu Primeiro Post", |
| 191 | + "content": "Este é o conteúdo do meu primeiro post!", |
| 192 | + "authorName": "João Silva" |
| 193 | + }' |
| 194 | +``` |
| 195 | + |
| 196 | +#### Obter Todos os Posts |
| 197 | + |
| 198 | +```bash |
| 199 | +curl http://localhost:8080/api/posts |
| 200 | +``` |
| 201 | + |
| 202 | +#### Adicionar um Comentário |
| 203 | + |
| 204 | +```bash |
| 205 | +curl -X POST http://localhost:8080/api/posts/1/comments \ |
| 206 | + -H "Content-Type: application/json" \ |
| 207 | + -d '{ |
| 208 | + "content": "Ótimo post!", |
| 209 | + "authorName": "Maria Santos" |
| 210 | + }' |
| 211 | +``` |
| 212 | + |
| 213 | +#### Curtir um Post |
| 214 | + |
| 215 | +```bash |
| 216 | +curl -X POST http://localhost:8080/api/posts/1/like \ |
| 217 | + -H "Content-Type: application/json" \ |
| 218 | + -d '{ |
| 219 | + "userName": "joao_silva" |
| 220 | + }' |
| 221 | +``` |
| 222 | + |
| 223 | +### Usando Swagger UI |
| 224 | + |
| 225 | +1. Abra [http://localhost:8080/swagger-ui.html](http://localhost:8080/swagger-ui.html) |
| 226 | +2. Explore os endpoints disponíveis |
| 227 | +3. Clique em "Try it out" em qualquer endpoint |
| 228 | +4. Preencha os parâmetros e clique em "Execute" |
| 229 | + |
| 230 | +## Desenvolvimento |
| 231 | + |
| 232 | +### Executando Testes |
| 233 | + |
| 234 | +```bash |
| 235 | +# Executar todos os testes |
| 236 | +./gradlew test |
| 237 | + |
| 238 | +# Executar com relatório de cobertura |
| 239 | +./gradlew test jacocoTestReport |
| 240 | + |
| 241 | +# Executar classe de teste específica |
| 242 | +./gradlew test --tests "SocialAppApplicationTests" |
| 243 | +``` |
| 244 | + |
| 245 | +### Banco de Dados |
| 246 | + |
| 247 | +A aplicação usa SQLite como banco de dados embarcado: |
| 248 | + |
| 249 | +- **Arquivo do banco de dados**: `sns_api.db` (criado automaticamente) |
| 250 | +- **Localização**: Diretório raiz do projeto |
| 251 | +- **Schema**: Gerado automaticamente pelo Hibernate |
| 252 | +- **Dados de exemplo**: Carregados de `data.sql` (se presente) |
| 253 | + |
| 254 | +Para resetar o banco de dados, simplesmente exclua o arquivo `sns_api.db` e reinicie a aplicação. |
| 255 | + |
| 256 | +## Configuração |
| 257 | + |
| 258 | +### Propriedades da Aplicação |
| 259 | + |
| 260 | +Configurações principais em `application.properties`: |
| 261 | + |
| 262 | +```properties |
| 263 | +# Configurações da Aplicação |
| 264 | +spring.application.name=socialapp |
| 265 | +server.port=8080 |
| 266 | + |
| 267 | +# Configuração do Banco de Dados |
| 268 | +spring.datasource.url=jdbc:sqlite:sns_api.db |
| 269 | +spring.jpa.hibernate.ddl-auto=update |
| 270 | + |
| 271 | +# Configuração OpenAPI/Swagger |
| 272 | +springdoc.swagger-ui.path=/swagger-ui.html |
| 273 | +springdoc.swagger-ui.operationsSorter=method |
| 274 | +``` |
| 275 | + |
| 276 | +### Configuração CORS |
| 277 | + |
| 278 | +A aplicação suporta tanto localhost quanto GitHub Codespaces: |
| 279 | + |
| 280 | +- **Localhost**: `http://localhost:8080` |
| 281 | +- **GitHub Codespaces**: Detectado e configurado automaticamente de forma dinâmica |
| 282 | + |
| 283 | +### Detecção de Ambiente |
| 284 | + |
| 285 | +A aplicação detecta automaticamente o ambiente de execução: |
| 286 | + |
| 287 | +- **Desenvolvimento Local**: Usa `http://localhost:8080` |
| 288 | +- **GitHub Codespaces**: Usa `https://{codespace-name}-8080.{domain}` |
| 289 | + |
| 290 | +## Implantação |
| 291 | + |
| 292 | +### Construindo para Produção |
| 293 | + |
| 294 | +```bash |
| 295 | +# Criar JAR de produção |
| 296 | +./gradlew clean build |
| 297 | + |
| 298 | +# Localização do JAR |
| 299 | +ls -la build/libs/socialapp-0.0.1-SNAPSHOT.jar |
| 300 | +``` |
| 301 | + |
| 302 | +### Executando em Produção |
| 303 | + |
| 304 | +```bash |
| 305 | +# Executar com perfil de produção |
| 306 | +java -jar build/libs/socialapp-0.0.1-SNAPSHOT.jar --spring.profiles.active=prod |
| 307 | + |
| 308 | +# Ou com porta personalizada |
| 309 | +java -jar build/libs/socialapp-0.0.1-SNAPSHOT.jar --server.port=8081 |
| 310 | +``` |
| 311 | + |
| 312 | +## Solução de Problemas |
| 313 | + |
| 314 | +### Problemas Comuns |
| 315 | + |
| 316 | +#### Porta Já em Uso |
| 317 | + |
| 318 | +```bash |
| 319 | +# Encontrar processo usando porta 8080 |
| 320 | +lsof -i :8080 |
| 321 | + |
| 322 | +# Matar o processo (substitua PID) |
| 323 | +kill -9 <PID> |
| 324 | + |
| 325 | +# Ou usar uma porta diferente |
| 326 | +./gradlew bootRun --args='--server.port=8081' |
| 327 | +``` |
| 328 | + |
| 329 | +#### Falhas de Build |
| 330 | + |
| 331 | +```bash |
| 332 | +# Limpar e reconstruir |
| 333 | +./gradlew clean build |
| 334 | + |
| 335 | +# Atualizar wrapper Gradle |
| 336 | +./gradlew wrapper --gradle-version=8.5 |
| 337 | +``` |
| 338 | + |
| 339 | +#### Problemas com Banco de Dados |
| 340 | + |
| 341 | +```bash |
| 342 | +# Resetar banco de dados |
| 343 | +rm sns_api.db |
| 344 | +./gradlew bootRun |
| 345 | +``` |
| 346 | + |
| 347 | +### Logs e Monitoramento |
| 348 | + |
| 349 | +- **Logs da aplicação**: Saída do console ao executar `./gradlew bootRun` |
| 350 | +- **Verificação de saúde**: `GET /actuator/health` |
| 351 | +- **Informações da aplicação**: `GET /actuator/info` |
| 352 | + |
| 353 | +## Considerações de Segurança |
| 354 | + |
| 355 | +⚠️ **Configuração de Desenvolvimento**: A configuração atual é otimizada para desenvolvimento com: |
| 356 | + |
| 357 | +- CORS habilitado para todas as origens |
| 358 | +- Banco de dados SQLite (não adequado para escala de produção) |
| 359 | +- Sem autenticação/autorização |
| 360 | + |
| 361 | +Para implantação em produção, considere: |
| 362 | + |
| 363 | +- Restringir CORS a domínios específicos |
| 364 | +- Usar PostgreSQL/MySQL em vez de SQLite |
| 365 | +- Implementar Spring Security para autenticação |
| 366 | +- Adicionar limitação de taxa e sanitização de entrada |
| 367 | +- Usar criptografia HTTPS/TLS |
0 commit comments