chore: first migration

This commit is contained in:
Gabriel Santana de Menezes 2026-05-10 16:41:41 -04:00
parent 6537e96e46
commit c2a6c52141
8 changed files with 111 additions and 59 deletions

View file

@ -36,11 +36,18 @@ cd backend
./mvnw quarkus:dev ./mvnw quarkus:dev
``` ```
Default database settings already point to the local Docker PostgreSQL instance: Default database settings point to the local Docker PostgreSQL instance, including in the `dev` profile:
- database: `timetrack` - database: `beetask`
- user: `timetrack` - user: `beetask`
- password: `timetrack` - password: `beetask`
- JDBC URL: `jdbc:postgresql://localhost:5432/beetask`
If needed, you can override them with:
- `DB_URL`
- `DB_USER`
- `DB_PASSWORD`
Main API endpoints: Main API endpoints:

View file

@ -51,6 +51,10 @@
<groupId>io.quarkus</groupId> <groupId>io.quarkus</groupId>
<artifactId>quarkus-smallrye-openapi</artifactId> <artifactId>quarkus-smallrye-openapi</artifactId>
</dependency> </dependency>
<dependency>
<groupId>io.quarkus</groupId>
<artifactId>quarkus-smallrye-health</artifactId>
</dependency>
<dependency> <dependency>
<groupId>io.quarkus</groupId> <groupId>io.quarkus</groupId>
<artifactId>quarkus-flyway</artifactId> <artifactId>quarkus-flyway</artifactId>

View file

@ -3,9 +3,9 @@ package net.beetechgroup.beetask.frameworks.persistence.entities;
import java.util.List; import java.util.List;
import jakarta.persistence.CascadeType; import jakarta.persistence.CascadeType;
import jakarta.persistence.CollectionTable;
import jakarta.persistence.ElementCollection;
import jakarta.persistence.Entity; import jakarta.persistence.Entity;
import jakarta.persistence.EnumType;
import jakarta.persistence.Enumerated;
import jakarta.persistence.GeneratedValue; import jakarta.persistence.GeneratedValue;
import jakarta.persistence.GenerationType; import jakarta.persistence.GenerationType;
import jakarta.persistence.Id; import jakarta.persistence.Id;
@ -23,6 +23,7 @@ public class TaskEntity {
private Long id; private Long id;
private String title; private String title;
private String description; private String description;
@Enumerated(EnumType.STRING)
private TaskStatus status; private TaskStatus status;
private java.time.LocalDateTime finishedAt; private java.time.LocalDateTime finishedAt;

View file

@ -3,22 +3,18 @@ quarkus.http.cors=true
quarkus.http.cors.origins=http://localhost:5173 quarkus.http.cors.origins=http://localhost:5173
quarkus.datasource.db-kind=postgresql quarkus.datasource.db-kind=postgresql
quarkus.datasource.username=${DB_USER:timetrack} quarkus.datasource.username=${DB_USER:beetask}
quarkus.datasource.password=${DB_PASSWORD:timetrack} quarkus.datasource.password=${DB_PASSWORD:beetask}
quarkus.datasource.jdbc.url=${DB_URL:jdbc:postgresql://localhost:5432/timetrack} quarkus.datasource.jdbc.url=${DB_URL:jdbc:postgresql://localhost:5432/beetask}
%dev.quarkus.datasource.db-kind=h2 quarkus.flyway.migrate-at-start=true
%dev.quarkus.datasource.jdbc.url=jdbc:h2:file:./data/beetask;DB_CLOSE_DELAY=-1;AUTO_SERVER=TRUE
%dev.quarkus.h2.console=true
%dev.quarkus.hibernate-orm.database.generation=update
quarkus.flyway.migrate-at-start=false
quarkus.hibernate-orm.database.generation=validate quarkus.hibernate-orm.database.generation=validate
# Swagger & OpenAPI # Swagger & OpenAPI
quarkus.smallrye-openapi.path=/openapi quarkus.smallrye-openapi.path=/openapi
quarkus.swagger-ui.path=/swagger quarkus.swagger-ui.path=/swagger
quarkus.swagger-ui.always-include=true quarkus.swagger-ui.always-include=true
quarkus.smallrye-health.root-path=/status
# JWT Security # JWT Security
mp.jwt.verify.issuer=https://beetech.net mp.jwt.verify.issuer=https://beetech.net

View file

@ -1,13 +0,0 @@
CREATE TABLE tasks (
id BIGINT GENERATED BY DEFAULT AS IDENTITY PRIMARY KEY,
title VARCHAR(255) NOT NULL,
description VARCHAR(2000),
status VARCHAR(32) NOT NULL,
project VARCHAR(255)
);
CREATE TABLE task_activities (
task_id BIGINT NOT NULL,
activity VARCHAR(255),
CONSTRAINT fk_task_activities_task FOREIGN KEY (task_id) REFERENCES tasks (id)
);

View file

@ -0,0 +1,82 @@
CREATE TABLE users_entity (
id BIGINT GENERATED BY DEFAULT AS IDENTITY PRIMARY KEY,
name VARCHAR(255) NOT NULL,
email VARCHAR(255) NOT NULL,
password VARCHAR(255) NOT NULL,
photo VARCHAR(1000),
CONSTRAINT uk_users_entity_email UNIQUE (email)
);
CREATE TABLE organizations (
id BIGINT GENERATED BY DEFAULT AS IDENTITY PRIMARY KEY,
name VARCHAR(255) NOT NULL
);
CREATE TABLE projects (
id BIGINT GENERATED BY DEFAULT AS IDENTITY PRIMARY KEY,
name VARCHAR(255) NOT NULL,
organization_id BIGINT,
CONSTRAINT fk_projects_organization
FOREIGN KEY (organization_id) REFERENCES organizations (id)
);
CREATE TABLE user_organizations (
id BIGINT GENERATED BY DEFAULT AS IDENTITY PRIMARY KEY,
user_id BIGINT,
organization_id BIGINT,
role VARCHAR(32),
status VARCHAR(32),
CONSTRAINT fk_user_organizations_user
FOREIGN KEY (user_id) REFERENCES users_entity (id),
CONSTRAINT fk_user_organizations_organization
FOREIGN KEY (organization_id) REFERENCES organizations (id),
CONSTRAINT uk_user_organizations_user_org UNIQUE (user_id, organization_id),
CONSTRAINT chk_user_organizations_role
CHECK (role IN ('OWNER', 'ADMIN', 'MEMBER')),
CONSTRAINT chk_user_organizations_status
CHECK (status IN ('PENDING', 'ACTIVE', 'REJECTED'))
);
CREATE TABLE project_users (
project_id BIGINT NOT NULL,
user_id BIGINT NOT NULL,
CONSTRAINT pk_project_users PRIMARY KEY (project_id, user_id),
CONSTRAINT fk_project_users_project
FOREIGN KEY (project_id) REFERENCES projects (id),
CONSTRAINT fk_project_users_user
FOREIGN KEY (user_id) REFERENCES users_entity (id)
);
CREATE TABLE tasks (
id BIGINT GENERATED BY DEFAULT AS IDENTITY PRIMARY KEY,
title VARCHAR(255),
description VARCHAR(255),
status VARCHAR(32),
finished_at TIMESTAMP(6),
project_id BIGINT,
user_id BIGINT,
CONSTRAINT fk_tasks_project
FOREIGN KEY (project_id) REFERENCES projects (id),
CONSTRAINT fk_tasks_user
FOREIGN KEY (user_id) REFERENCES users_entity (id),
CONSTRAINT chk_tasks_status
CHECK (status IN ('NOT_STARTED', 'IN_PROGRESS', 'COMPLETED', 'CANCELED'))
);
CREATE TABLE task_history (
id BIGINT GENERATED BY DEFAULT AS IDENTITY PRIMARY KEY,
start_at TIMESTAMP(6),
end_at TIMESTAMP(6),
task_id BIGINT,
CONSTRAINT fk_task_history_task
FOREIGN KEY (task_id) REFERENCES tasks (id)
);
CREATE INDEX idx_projects_organization_id ON projects (organization_id);
CREATE INDEX idx_user_organizations_user_id ON user_organizations (user_id);
CREATE INDEX idx_user_organizations_organization_id ON user_organizations (organization_id);
CREATE INDEX idx_project_users_user_id ON project_users (user_id);
CREATE INDEX idx_tasks_project_id ON tasks (project_id);
CREATE INDEX idx_tasks_user_id ON tasks (user_id);
CREATE INDEX idx_tasks_status ON tasks (status);
CREATE INDEX idx_task_history_task_id ON task_history (task_id);

View file

@ -1,6 +0,0 @@
-- This file allow to write SQL commands that will be emitted in test and dev.
-- The commands are commented as their support depends of the database
-- insert into myentity (id, field) values(1, 'field-1');
-- insert into myentity (id, field) values(2, 'field-2');
-- insert into myentity (id, field) values(3, 'field-3');
-- alter sequence myentity_seq restart with 4;

View file

@ -1,40 +1,21 @@
services: services:
postgres: postgres:
image: postgres:18.3 image: postgres:18.3
container_name: timetrack-postgres container_name: bee-task-postgres
environment: environment:
POSTGRES_USER: timetrack POSTGRES_USER: beetask
POSTGRES_PASSWORD: timetrack POSTGRES_PASSWORD: beetask
POSTGRES_DB: timetrack POSTGRES_DB: beetask
ports: ports:
- "5432:5432" - "5432:5432"
volumes: volumes:
- postgres_data:/var/lib/postgresql - postgres_data:/var/lib/postgresql/data
- ./docker/postgres/init:/docker-entrypoint-initdb.d - ./docker/postgres/init:/docker-entrypoint-initdb.d
healthcheck: healthcheck:
test: ["CMD-SHELL", "pg_isready -U timetrack"] test: ["CMD-SHELL", "pg_isready -U beetask"]
interval: 10s interval: 10s
timeout: 5s timeout: 5s
retries: 5 retries: 5
keycloak:
image: quay.io/keycloak/keycloak:26.6.1
container_name: timetrack-keycloak
command: start-dev
environment:
KEYCLOAK_ADMIN: admin
KEYCLOAK_ADMIN_PASSWORD: admin
KC_DB: postgres
KC_DB_URL_HOST: postgres
KC_DB_URL_PORT: 5432
KC_DB_URL_DATABASE: keycloak
KC_DB_USERNAME: timetrack
KC_DB_PASSWORD: timetrack
ports:
- "8081:8080"
depends_on:
postgres:
condition: service_healthy
volumes: volumes:
postgres_data: postgres_data: