pg driver — there is no ORM.
Entity relationship overview
schema
Users
Theusers table stores all platform accounts. Role and account status are managed here.
| Column | Type | Constraints | Description |
|---|---|---|---|
id_usuario | integer | PK, auto-increment | Unique user identifier |
nombre | varchar(100) | NOT NULL | Display name |
email | varchar(150) | UNIQUE | Login email address |
password | varchar(150) | NOT NULL | Argon2id password hash |
rol | integer | default 1 | Role: 1 Developer, 2 Project Manager, 3 Admin |
activo | boolean | default true | Soft delete flag — false disables login |
created_at | timestamp | default now() | Account creation time |
update_at | timestamp | nullable | Last profile update time |
Users are never hard-deleted. Setting
activo = false disables the account while preserving all associated tasks, comments, and project ownership. Only an Admin can change this flag via PUT /usuario/estado.Projects
Theprojects table represents work containers that group related tasks.
| Column | Type | Constraints | Description |
|---|---|---|---|
id_proyecto | integer | PK, auto-increment | Unique project identifier |
nombre | varchar(100) | NOT NULL | Project name |
descripcion | varchar(100) | NOT NULL | Short description |
estado | varchar(50) | default 'ACTIVO' | Project state: ACTIVO or ARCHIVADO |
owner_id | integer | NOT NULL, FK → users.id_usuario | The PM or Admin who created the project |
created_at | timestamp | default now() | Creation time |
update_at | timestamp | nullable | Last edit time |
owner_id is used for ownership-scoped authorization. A Project Manager can only archive or view their own projects — those where owner_id matches their id_usuario. This check is enforced in the service layer, not just by role.Tasks
Thetasks table is the core entity of the platform. Each task belongs to one project and is assigned to one user.
| Column | Type | Constraints | Description |
|---|---|---|---|
id_tarea | integer | PK, auto-increment | Unique task identifier |
titulo | varchar(50) | NOT NULL | Task title |
descripcion | varchar(150) | NOT NULL | Task description |
estado | varchar(50) | default 'TODO' | Workflow state: TODO, IN_PROGRESS, IN_REVIEW, DONE |
prioridad | varchar(50) | NOT NULL | Priority level (e.g., ALTA, MEDIA, BAJA) |
due_date | date | NOT NULL | Target completion date |
project_id | integer | NOT NULL, FK → projects.id_proyecto, CASCADE DELETE | Owning project |
assigned_to | integer | NOT NULL, FK → users.id_usuario | User responsible for completing the task |
created_by | integer | NOT NULL, FK → users.id_usuario | User who created the task |
created_at | timestamp | default now() | Creation time |
Comments
Thecomments table stores discussion attached to individual tasks.
| Column | Type | Constraints | Description |
|---|---|---|---|
id_comentario | integer | PK, auto-increment | Unique comment identifier |
contenido | varchar(150) | NOT NULL | Comment body text |
task_id | integer | NOT NULL, FK → tasks.id_tarea, CASCADE DELETE | The task this comment belongs to |
user_id | integer | NOT NULL, FK → users.id_usuario | The user who posted the comment |
The comments data model is fully implemented in the database. A frontend UI for comments is planned but not yet available — see Architecture trade-offs.
Cascade delete behavior
Deletion propagates down the ownership chain:cascade chain
owner_id, assigned_to, created_by, user_id) remain intact.