Skip to content

feat: implementando CRUD de Eleições#404

Open
mateusmrosa wants to merge 2 commits intohomolfrom
feat/SA10.TV014-implementar-CRUD-eleicoes
Open

feat: implementando CRUD de Eleições#404
mateusmrosa wants to merge 2 commits intohomolfrom
feat/SA10.TV014-implementar-CRUD-eleicoes

Conversation

@mateusmrosa
Copy link
Contributor

@mateusmrosa mateusmrosa commented Aug 26, 2025

Summary by CodeRabbit

  • New Features

    • Full election management: create, list (with filters), retrieve, update, and delete endpoints.
    • Filtering on listings by type, year, and "current for mandates".
    • Role-based access control for management actions.
    • Soft-delete with safeguards against removing elections that have related records.
  • Documentation

    • Improved API docs for election endpoints, parameters, enums, and examples.

@coderabbitai
Copy link
Contributor

coderabbitai bot commented Aug 26, 2025

Walkthrough

Adds DTOs for creating, filtering, and updating elections; extends the EleicaoController with full CRUD endpoints and query filtering; and refactors EleicaoService to implement create/findAll/findOne/update/remove with transactions, validations, soft delete, and structured logging.

Changes

Cohort / File(s) Summary
DTOs for Eleição
backend/src/eleicao/dto/create-eleicao.dto.ts, backend/src/eleicao/dto/filter-eleicao.dto.ts, backend/src/eleicao/dto/update-eleicao.dto.ts
New CreateEleicaoDto, FilterEleicaoDto, and UpdateEleicaoDto. Include enum/int/bool validations, class-transformer transforms, optional handling for filters, Swagger metadata, and PartialType for updates.
Controller CRUD and filtering
backend/src/eleicao/eleicao.controller.ts
Adds POST /eleicao (create), GET /eleicao (list with FilterEleicaoDto), GET /eleicao/:id, PATCH /eleicao/:id, DELETE /eleicao/:id; applies role guards, returns ids/entities, and accepts query filters.
Service CRUD, filtering, and logging
backend/src/eleicao/eleicao.service.ts
Replaces previous read with create/findAll/findOne/update/remove. Implements filtering, ordering, soft delete, uniqueness checks, relation guards, transaction handling, Prisma P2002 handling → BadRequest, and operation logging. Adjusts findAll return shape to ListEleicaoDto[].

Sequence Diagram(s)

sequenceDiagram
  autonumber
  actor Admin as SMAE.superadmin
  participant Ctrl as EleicaoController
  participant Svc as EleicaoService
  participant DB as Prisma/DB
  participant Log as LoggerWithLog

  rect rgb(240,248,255)
  note over Admin,Ctrl: Create Eleição (POST /eleicao)
  Admin->>Ctrl: CreateEleicaoDto
  Ctrl->>Svc: create(dto, user)
  Svc->>Log: log start create
  Svc->>DB: begin tx -> insert eleicao
  DB-->>Svc: success / P2002
  alt Unique conflict
    Svc-->>Ctrl: throw BadRequestException
  else Success
    Svc->>Log: log success
    Svc-->>Ctrl: created Eleicao (id)
  end
  end

  rect rgb(245,255,240)
  note over Admin,Ctrl: List Eleições (GET /eleicao?filters)
  Admin->>Ctrl: FilterEleicaoDto
  Ctrl->>Svc: findAll(filters)
  Svc->>DB: select where removido_em is null + filters
  DB-->>Svc: rows
  Svc-->>Ctrl: ListEleicaoDto[] (wrapped)
  Ctrl-->>Admin: list response
  end

  rect rgb(255,248,240)
  note over Admin,Ctrl: Update / Delete flows
  Admin->>Ctrl: PATCH/DELETE /eleicao/:id
  Ctrl->>Svc: update(id,dto,user) / remove(id,user)
  Svc->>DB: validate existence, uniqueness checks, relation checks
  alt validation fail
    Svc-->>Ctrl: throw BadRequestException
  else proceed
    Svc->>DB: tx update / soft-delete
    Svc->>Log: log update/remove
    Svc-->>Ctrl: { id } or 204
  end
  Ctrl-->>Admin: response
  end
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~60 minutes

Suggested reviewers

  • robsonsobral

Poem

Thump-thump, I scurry through each line,
New DTO carrots in tidy design.
Controllers sprout CRUD in a row,
Services log where soft-deletes go.
Hooray—elections planted just so! 🥕🐇

Tip

🔌 Remote MCP (Model Context Protocol) integration is now available!

Pro plan users can now connect to remote MCP servers from the Integrations page. Connect with popular remote MCPs such as Notion and Linear to add more context to your reviews and chats.

✨ Finishing Touches
  • 📝 Generate Docstrings
🧪 Generate unit tests
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch feat/SA10.TV014-implementar-CRUD-eleicoes

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share
🪧 Tips

Chat

There are 3 ways to chat with CodeRabbit:

  • Review comments: Directly reply to a review comment made by CodeRabbit. Example:
    • I pushed a fix in commit <commit_id>, please review it.
    • Open a follow-up GitHub issue for this discussion.
  • Files and specific lines of code (under the "Files changed" tab): Tag @coderabbitai in a new review comment at the desired location with your query.
  • PR comments: Tag @coderabbitai in a new PR comment to ask questions about the PR branch. For the best results, please provide a very specific query, as very limited context is provided in this mode. Examples:
    • @coderabbitai gather interesting stats about this repository and render them as a table. Additionally, render a pie chart showing the language distribution in the codebase.
    • @coderabbitai read the files in the src/scheduler package and generate a class diagram using mermaid and a README in the markdown format.

Support

Need help? Create a ticket on our support page for assistance with any issues or questions.

CodeRabbit Commands (Invoked using PR/Issue comments)

Type @coderabbitai help to get the list of available commands.

Other keywords and placeholders

  • Add @coderabbitai ignore anywhere in the PR description to prevent this PR from being reviewed.
  • Add @coderabbitai summary to generate the high-level summary at a specific location in the PR description.
  • Add @coderabbitai anywhere in the PR title to generate the title automatically.

CodeRabbit Configuration File (.coderabbit.yaml)

  • You can programmatically configure CodeRabbit by adding a .coderabbit.yaml file to the root of your repository.
  • Please see the configuration documentation for more information.
  • If your editor has YAML language server enabled, you can add the path at the top of this file to enable auto-completion and validation: # yaml-language-server: $schema=https://coderabbit.ai/integrations/schema.v2.json

Status, Documentation and Community

  • Visit our Status Page to check the current availability of CodeRabbit.
  • Visit our Documentation for detailed information on how to use CodeRabbit.
  • Join our Discord Community to get help, request features, and share feedback.
  • Follow us on X/Twitter for updates and announcements.

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 4

🧹 Nitpick comments (6)
backend/src/eleicao/dto/create-eleicao.dto.ts (1)

19-22: Normalize boolean parsing (case-insensitive) for atual_para_mandatos

Today only the literal string 'true' becomes true; 'TRUE'/'True' are treated as false. Align with FilterEleicaoDto behavior and avoid surprises across endpoints.

-    @Transform(({ value }) => value === 'true' || value === true)
+    @Transform(({ value }) => (typeof value === 'string' ? value.toLowerCase() === 'true' : value === true))
     atual_para_mandatos: boolean;
backend/src/eleicao/dto/filter-eleicao.dto.ts (2)

12-18: Minor: align number coercion message with Create DTO (optional)

Current Transform is fine. If you want fully consistent DX across DTOs, mirror the numeric coercion approach used in CreateEleicaoDto (via @type(() => Number)) and keep the empty-string-to-undefined behavior. Optional.


7-10: Optional: consistent enum error message

Consider adding the same custom IsEnum message used in CreateEleicaoDto so clients get uniform feedback across endpoints.

-    @IsEnum(EleicaoTipo)
+    @IsEnum(EleicaoTipo, { message: '$property| Precisa ser um dos seguintes valores: ' + Object.values(EleicaoTipo).join(', ') })
     tipo?: EleicaoTipo;
backend/src/eleicao/eleicao.controller.ts (1)

41-43: Return type annotation for list endpoint (if you keep a single method)

Ensure the surviving list method explicitly returns Promise<ListEleicaoDto[]> for consistency with service.

backend/src/eleicao/eleicao.service.ts (2)

65-85: Prefer NotFoundException for missing records (optional)

Semantically, an inexistente resource is a 404. If project conventions allow, swap BadRequestException for NotFoundException here.

-import { Injectable, BadRequestException } from '@nestjs/common';
+import { Injectable, BadRequestException, NotFoundException } from '@nestjs/common';
@@
-        if (!eleicao) {
-            throw new BadRequestException('Eleição não encontrada');
-        }
+        if (!eleicao) {
+            throw new NotFoundException('Eleição não encontrada');
+        }

129-156: Race window between relationship checks and soft delete

Between the two count() calls and the update(), related records could be created, allowing a soft delete despite the intent. Consider performing the checks and the update in the same transaction (using the same tx client) to narrow the window, or enforce via FK constraints.

-        const mandatos = await this.prisma.parlamentarMandato.count({
+        const mandatos = await this.prisma.parlamentarMandato.count({
             where: { eleicao_id: id },
         });
@@
-        await this.prisma.$transaction(async (prismaTx: Prisma.TransactionClient) => {
-            logger.log(`Eleição: ${id}`);
-            await prismaTx.eleicao.update({
-                where: { id: id },
-                data: { removido_em: new Date() },
-            });
-            await logger.saveLogs(prismaTx, user.getLogData());
-        });
+        await this.prisma.$transaction(async (tx) => {
+            const [mandatosTx, comparecimentosTx] = await Promise.all([
+                tx.parlamentarMandato.count({ where: { eleicao_id: id } }),
+                tx.eleicaoComparecimento.count({ where: { eleicao_id: id } }),
+            ]);
+            if (mandatosTx > 0 || comparecimentosTx > 0) {
+                throw new BadRequestException(
+                    'Não é possível remover esta eleição pois ela possui mandatos ou comparecimentos associados'
+                );
+            }
+            logger.log(`Eleição: ${id}`);
+            await tx.eleicao.update({
+                where: { id },
+                data: { removido_em: new Date() },
+            });
+            await logger.saveLogs(tx, user.getLogData());
+        });
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

💡 Knowledge Base configuration:

  • MCP integration is disabled by default for public repositories
  • Jira integration is disabled by default for public repositories
  • Linear integration is disabled by default for public repositories

You can enable these sources in your CodeRabbit configuration.

📥 Commits

Reviewing files that changed from the base of the PR and between dc56d7d and bd8fb23.

📒 Files selected for processing (5)
  • backend/src/eleicao/dto/create-eleicao.dto.ts (1 hunks)
  • backend/src/eleicao/dto/filter-eleicao.dto.ts (1 hunks)
  • backend/src/eleicao/dto/update-eleicao.dto.ts (1 hunks)
  • backend/src/eleicao/eleicao.controller.ts (2 hunks)
  • backend/src/eleicao/eleicao.service.ts (1 hunks)
🧰 Additional context used
🧬 Code graph analysis (3)
backend/src/eleicao/dto/update-eleicao.dto.ts (1)
backend/src/eleicao/dto/create-eleicao.dto.ts (1)
  • CreateEleicaoDto (6-23)
backend/src/eleicao/eleicao.controller.ts (6)
backend/src/eleicao/dto/filter-eleicao.dto.ts (1)
  • FilterEleicaoDto (6-33)
backend/src/auth/models/PessoaFromJwt.ts (1)
  • PessoaFromJwt (16-249)
backend/src/eleicao/dto/create-eleicao.dto.ts (1)
  • CreateEleicaoDto (6-23)
backend/src/common/dto/record-with-id.dto.ts (1)
  • RecordWithId (4-9)
backend/src/wiki-link/dto/find-one-params.dto.ts (1)
  • FindOneParams (6-11)
backend/src/eleicao/dto/update-eleicao.dto.ts (1)
  • UpdateEleicaoDto (4-4)
backend/src/eleicao/eleicao.service.ts (4)
backend/src/eleicao/dto/create-eleicao.dto.ts (1)
  • CreateEleicaoDto (6-23)
backend/src/auth/models/PessoaFromJwt.ts (1)
  • PessoaFromJwt (16-249)
backend/src/eleicao/dto/filter-eleicao.dto.ts (1)
  • FilterEleicaoDto (6-33)
backend/src/eleicao/dto/update-eleicao.dto.ts (1)
  • UpdateEleicaoDto (4-4)
🔇 Additional comments (4)
backend/src/eleicao/dto/create-eleicao.dto.ts (1)

7-11: Good: explicit enum validation with helpful message

Clear developer-facing feedback by listing allowed EleicaoTipo values. This will save debugging time.

backend/src/eleicao/dto/update-eleicao.dto.ts (1)

4-4: LGTM: PartialType reuse keeps validation rules DRY

Using PartialType(CreateEleicaoDto) is the right call for patch semantics.

backend/src/eleicao/dto/filter-eleicao.dto.ts (1)

20-32: Thoughtful boolean transform for filters

Nice handling of undefined/empty inputs and case-insensitive string parsing. This will make query-string usage resilient.

backend/src/eleicao/eleicao.controller.ts (1)

11-11: Incorrect import warning can be ignored
The class FindOneParams is indeed defined and exported in backend/src/common/decorators/find-params.ts, so the existing import is valid. There is no common/dto/find-one-params.dto.ts in the repo, and the proposed path would cause a compile error. Please continue using:

import { FindOneParams } from 'src/common/decorators/find-params';

Likely an incorrect or invalid review comment.

@sonarqubecloud
Copy link

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

💡 Knowledge Base configuration:

  • MCP integration is disabled by default for public repositories
  • Jira integration is disabled by default for public repositories
  • Linear integration is disabled by default for public repositories

You can enable these sources in your CodeRabbit configuration.

📥 Commits

Reviewing files that changed from the base of the PR and between bd8fb23 and 18f38b5.

📒 Files selected for processing (4)
  • backend/src/eleicao/dto/create-eleicao.dto.ts (1 hunks)
  • backend/src/eleicao/dto/update-eleicao.dto.ts (1 hunks)
  • backend/src/eleicao/eleicao.controller.ts (1 hunks)
  • backend/src/eleicao/eleicao.service.ts (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • backend/src/eleicao/dto/create-eleicao.dto.ts
🧰 Additional context used
🧬 Code graph analysis (3)
backend/src/eleicao/eleicao.controller.ts (6)
backend/src/eleicao/dto/create-eleicao.dto.ts (1)
  • CreateEleicaoDto (6-24)
backend/src/auth/models/PessoaFromJwt.ts (1)
  • PessoaFromJwt (16-249)
backend/src/common/dto/record-with-id.dto.ts (1)
  • RecordWithId (4-9)
backend/src/eleicao/dto/filter-eleicao.dto.ts (1)
  • FilterEleicaoDto (6-33)
backend/src/wiki-link/dto/find-one-params.dto.ts (1)
  • FindOneParams (6-11)
backend/src/eleicao/dto/update-eleicao.dto.ts (1)
  • UpdateEleicaoDto (6-17)
backend/src/eleicao/dto/update-eleicao.dto.ts (1)
backend/src/eleicao/dto/create-eleicao.dto.ts (1)
  • CreateEleicaoDto (6-24)
backend/src/eleicao/eleicao.service.ts (4)
backend/src/eleicao/dto/create-eleicao.dto.ts (1)
  • CreateEleicaoDto (6-24)
backend/src/auth/models/PessoaFromJwt.ts (1)
  • PessoaFromJwt (16-249)
backend/src/eleicao/dto/filter-eleicao.dto.ts (1)
  • FilterEleicaoDto (6-33)
backend/src/eleicao/dto/update-eleicao.dto.ts (1)
  • UpdateEleicaoDto (6-17)
🔇 Additional comments (9)
backend/src/eleicao/dto/update-eleicao.dto.ts (1)

6-17: LGTM - Proper handling of boolean transformation for PATCH operations.

The override of the atual_para_mandatos field correctly prevents accidental coercion of empty strings to false during update operations, maintaining the intended "no change" semantics for partial updates.

backend/src/eleicao/eleicao.controller.ts (5)

21-30: LGTM - Well-structured create endpoint.

The create endpoint properly implements authentication, authorization, and returns the expected RecordWithId format.


32-37: LGTM - Clean list endpoint implementation.

The findAll endpoint correctly uses filters and returns the appropriate DTO type.


39-44: LGTM - Standard findOne implementation.

The endpoint correctly retrieves a single election by ID with proper authorization.


46-56: LGTM - Complete update endpoint.

The update endpoint properly handles partial updates using the specialized DTO and returns the expected format.


58-64: LGTM - Proper soft delete endpoint.

The delete endpoint correctly implements HTTP 204 status code for successful deletions and uses soft delete semantics.

backend/src/eleicao/eleicao.service.ts (3)

16-43: LGTM - Robust create method with proper error handling.

The create method correctly handles unique constraint violations and implements transaction-based logging.


87-130: Good implementation with proper error handling.

The update method correctly implements pre-validation for uniqueness constraints and handles both validation and transaction-level errors appropriately. The error handling matches the create method's approach.


132-160: LGTM - Comprehensive remove method with relationship validation.

The method properly:

  • Validates existence before removal
  • Checks for dependent relationships (mandatos and comparecimentos)
  • Implements soft delete with transaction-based logging

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant