docs(jwt): Fix endpoints table and add missing logout route#16
Conversation
…ensitivity to prevent double account with e.g (Testes.admin && testes.admin)
There was a problem hiding this comment.
Pull request overview
Adds JWT-based authentication to the HomeMatch Django/DRF API (SimpleJWT), including registration/login/logout endpoints and supporting documentation/diagrams.
Changes:
- Configure SimpleJWT (incl. refresh rotation + blacklist) and enable the blacklist app in Django settings.
- Add public registration endpoint plus JWT login/refresh/logout routes; rename the authenticated “profile” action to
/me. - Add documentation for authentication/security plus database diagrams (mermaid + PNG).
Reviewed changes
Copilot reviewed 8 out of 9 changed files in this pull request and generated 11 comments.
Show a summary per file
| File | Description |
|---|---|
| docs/jwt.md | New JWT/auth documentation and example requests. |
| docs/diagrama_database.mermaid | Adds a mermaid ER diagram for the project schema. |
| docs/diagram.png | Adds an image version of the database diagram. |
| config/settings.py | Enables SimpleJWT + blacklist app and sets JWT lifetimes/rotation behavior. |
| apps/users/views.py | Adds RegisterUserView and renames profile action to me; keeps favorites endpoint. |
| apps/users/urls.py | Adds /register, /login, /token/refresh, /logout routes alongside router endpoints. |
| apps/users/serializers.py | Adds RegisterSerializer for user creation. |
| apps/users/models.py | Introduces a custom UserManager for email-based auth. |
| apps/users/migrations/0003_alter_user_managers.py | Adds a migration altering model managers. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
config/settings.py
Outdated
| AUTH_PASSWORD_VALIDATORS = [ | ||
| { | ||
| "NAME": "django.contrib.auth.password_validation.UserAttributeSimilarityValidator" | ||
| "NAME": "django.contrib.auth.password_validation.UserAttributeSimilarityValidator" |
There was a problem hiding this comment.
The AUTH_PASSWORD_VALIDATORS entry has inconsistent indentation for the dict key, which makes the settings file harder to read and deviates from the surrounding style. Align the "NAME" line indentation with the other dict entries.
| "NAME": "django.contrib.auth.password_validation.UserAttributeSimilarityValidator" | |
| "NAME": "django.contrib.auth.password_validation.UserAttributeSimilarityValidator" |
|
|
||
| class RegisterUserView(generics.CreateAPIView): | ||
| queryset = User.objects.all() | ||
| permission_classes = [AllowAny] |
There was a problem hiding this comment.
permission_classes = [AllowAny] has trailing whitespace. Please remove it to satisfy linters/formatters and keep diffs clean.
| permission_classes = [AllowAny] | |
| permission_classes = [AllowAny] |
| raise ValueError("Superuser need is_staff=True.") | ||
| if extra_fields.get("is_superuser") is not True: | ||
| raise ValueError("Superuser need is_superuser=True.") |
There was a problem hiding this comment.
The error messages in these ValueErrors have grammatical issues ("Superuser need ..."). Adjust wording to be clear and correct (e.g., "Superuser needs is_staff=True.") so these messages are useful when surfaced in CLI/admin flows.
| raise ValueError("Superuser need is_staff=True.") | |
| if extra_fields.get("is_superuser") is not True: | |
| raise ValueError("Superuser need is_superuser=True.") | |
| raise ValueError("Superuser needs is_staff=True.") | |
| if extra_fields.get("is_superuser") is not True: | |
| raise ValueError("Superuser needs is_superuser=True.") |
| @action(detail=False, methods=['get', 'post', 'delete'], url_path='favorites') | ||
| def favorites(self, request): | ||
| from apps.properties.serializers import PropertiesSerializer # Sei que soa estranho, mas esse import tem que tá aqui praa poder não ter import repetido | ||
| from apps.properties.models import Properties | ||
| from apps.properties.models import Properties |
There was a problem hiding this comment.
This endpoint relies on user.favorites (used later in the method), but the User model in this PR does not define a favorites relation (the ManyToMany field is commented out and there is no alternative relation in apps/properties). This will raise an AttributeError at runtime. Either add/restore the favorites ManyToMany (with a migration) or update the endpoint to use the actual persisted favorites model/table.
| | Método | Endpoint | Acesso | Descrição | | ||
| | :--- | :--- | :--- | :--- | | ||
| | `POST` | `/api/users/register/` | Público | Registra um novo usuário na plataforma. | | ||
| | `POST` | `/api/users/login/` | Público | Recebe as credenciais e retorna os tokens `access` e `refresh`. | | ||
| | `POST` | `/api/users/token/refresh/` | Público | Gera um novo `access` token utilizando um `refresh` válido. | |
There was a problem hiding this comment.
The markdown table for the JWT endpoints is malformed (rows start with ||), which prevents proper rendering in standard Markdown parsers. Use single | separators and a single header separator row.
There was a problem hiding this comment.
Fixed in dc2c90a. The table now uses proper single | separators and I also added the missing POST /api/users/logout/ row, which was already defined in the URL conf but omitted from the docs.
| "password": "sua senha cadastrada" | ||
| }' | ||
| ``` | ||
| * Só ai, você testa com seu token. |
There was a problem hiding this comment.
This sentence has a spelling/grammar issue ("Só ai"). Please correct to "Só aí" for proper Portuguese.
| * Só ai, você testa com seu token. | |
| * Só aí, você testa com seu token. |
config/settings.py
Outdated
| from datetime import timedelta | ||
| SIMPLE_JWT = { |
There was a problem hiding this comment.
Keep imports grouped at the top of the module. timedelta is imported mid-file, which makes settings harder to scan and can conflict with linting rules.
config/settings.py
Outdated
| 'ACCESS_TOKEN_LIFETIME': timedelta(minutes=60), | ||
| 'REFRESH_TOKEN_LIFETIME': timedelta(days=1), | ||
| 'ROTATE_REFRESH_TOKENS': True, | ||
| 'BLACKLIST_AFTER_ROTATION': True, |
There was a problem hiding this comment.
Quote style is inconsistent: this settings file largely uses double quotes, but SIMPLE_JWT uses single quotes for keys. Standardize the quoting style to match the rest of the file to keep formatting consistent.
| 'ACCESS_TOKEN_LIFETIME': timedelta(minutes=60), | |
| 'REFRESH_TOKEN_LIFETIME': timedelta(days=1), | |
| 'ROTATE_REFRESH_TOKENS': True, | |
| 'BLACKLIST_AFTER_ROTATION': True, | |
| "ACCESS_TOKEN_LIFETIME": timedelta(minutes=60), | |
| "REFRESH_TOKEN_LIFETIME": timedelta(days=1), | |
| "ROTATE_REFRESH_TOKENS": True, | |
| "BLACKLIST_AFTER_ROTATION": True, |
| user_type=validated_data['user_type'], | ||
| password=validated_data['password'] | ||
| ) | ||
| return user |
There was a problem hiding this comment.
Add a blank line between create and validate_email. Having def validate_email immediately after return user violates PEP 8 and makes the serializer harder to read.
| return user | |
| return user |
| operations = [ | ||
| migrations.AlterModelManagers( | ||
| name='user', | ||
| managers=[ | ||
| ], | ||
| ), | ||
| ] |
There was a problem hiding this comment.
This migration alters model managers but provides an empty managers=[], which is unusual and can create confusing migration state (and it doesn't affect the DB schema). Consider removing it, or include the intended manager so the migration accurately represents the model state.
| operations = [ | |
| migrations.AlterModelManagers( | |
| name='user', | |
| managers=[ | |
| ], | |
| ), | |
| ] | |
| operations = [] |
Agent-Logs-Url: https://github.com/DevlTz/HomeMatch/sessions/ffd2d2d2-2749-48f3-a23a-f55c32465b7f Co-authored-by: DevlTz <110422010+DevlTz@users.noreply.github.com>
The JWT endpoints table in
docs/jwt.mdwas malformed and missing thelogoutendpoint despite it being wired up in the URL conf viaTokenBlacklistView.Changes
docs/jwt.md: Corrected markdown table formatting (single|separators, single header separator row); added missingPOST /api/users/logout/row documenting the blacklist-based logout endpoint.POST/api/users/logout/refreshtoken (blacklist), encerrando a sessão.