From 19056d5e757f27e74c82d8258edced7c6574974d Mon Sep 17 00:00:00 2001 From: Denis Lugowski Date: Sat, 27 Sep 2025 10:00:04 +0200 Subject: [PATCH] feat: Add database restore script --- .gitignore | 3 +- .../config/TestContainersConfig.kt | 1 + .../resources/legalconsenthub-db-backup.sql | 450 ++++++++++++++++++ legalconsenthub/sqlite-backup.db | Bin 0 -> 81920 bytes manage-db.sh | 327 +++++++++++++ 5 files changed, 780 insertions(+), 1 deletion(-) create mode 100644 legalconsenthub-backend/src/main/resources/legalconsenthub-db-backup.sql create mode 100644 legalconsenthub/sqlite-backup.db create mode 100755 manage-db.sh diff --git a/.gitignore b/.gitignore index 55ee0ec..96f7a14 100644 --- a/.gitignore +++ b/.gitignore @@ -58,5 +58,6 @@ bin/ legalconsenthub/.api-client legalconsenthub/.api-client-middleware -### PostgreSQL persistent data ### +### TestContainers persistent data ### legalconsenthub-backend/postgres-data/ + diff --git a/legalconsenthub-backend/src/main/kotlin/com/betriebsratkanzlei/legalconsenthub/config/TestContainersConfig.kt b/legalconsenthub-backend/src/main/kotlin/com/betriebsratkanzlei/legalconsenthub/config/TestContainersConfig.kt index abade63..f0414db 100644 --- a/legalconsenthub-backend/src/main/kotlin/com/betriebsratkanzlei/legalconsenthub/config/TestContainersConfig.kt +++ b/legalconsenthub-backend/src/main/kotlin/com/betriebsratkanzlei/legalconsenthub/config/TestContainersConfig.kt @@ -24,6 +24,7 @@ class TestContainersConfig { .withPassword("legalconsenthub") .withExposedPorts(5432) .withCreateContainerCmdModifier { cmd -> + cmd.withName("legalconsenthub-backend") cmd.withHostConfig( HostConfig().apply { this.withPortBindings( diff --git a/legalconsenthub-backend/src/main/resources/legalconsenthub-db-backup.sql b/legalconsenthub-backend/src/main/resources/legalconsenthub-db-backup.sql new file mode 100644 index 0000000..65a086a --- /dev/null +++ b/legalconsenthub-backend/src/main/resources/legalconsenthub-db-backup.sql @@ -0,0 +1,450 @@ +-- +-- PostgreSQL database dump +-- +-- AG Invitation URL: http://192.168.178.114:3001/accept-invitation/CxVPVaWD0u0hztcwBbV4Pyub0tHIds5o + +-- Dumped from database version 17.5 +-- Dumped by pg_dump version 17.5 + +-- +-- Force drop all tables and constraints to ensure clean restoration +-- + +DROP TABLE IF EXISTS public.user_organization_roles CASCADE; +DROP TABLE IF EXISTS public.notification CASCADE; +DROP TABLE IF EXISTS public.form_element_section CASCADE; +DROP TABLE IF EXISTS public.form_element_options CASCADE; +DROP TABLE IF EXISTS public.form_element CASCADE; +DROP TABLE IF EXISTS public.comment CASCADE; +DROP TABLE IF EXISTS public.application_form CASCADE; +DROP TABLE IF EXISTS public.app_user CASCADE; +DROP TABLE IF EXISTS public.databasechangeloglock CASCADE; +DROP TABLE IF EXISTS public.databasechangelog CASCADE; + +-- Drop any remaining sequences, views, or other objects +DROP SEQUENCE IF EXISTS public.hibernate_sequence CASCADE; + +-- Reset database configuration +SET statement_timeout = 0; +SET lock_timeout = 0; +SET idle_in_transaction_session_timeout = 0; +SET transaction_timeout = 0; +SET client_encoding = 'UTF8'; +SET standard_conforming_strings = on; +SELECT pg_catalog.set_config('search_path', '', false); +SET check_function_bodies = false; +SET xmloption = content; +SET client_min_messages = warning; +SET row_security = off; + +SET default_tablespace = ''; + +SET default_table_access_method = heap; + +-- +-- Name: app_user; Type: TABLE; Schema: public; Owner: legalconsenthub +-- + +CREATE TABLE public.app_user ( + created_at timestamp(6) without time zone NOT NULL, + modified_at timestamp(6) without time zone NOT NULL, + id character varying(255) NOT NULL, + name character varying(255) NOT NULL, + status character varying(255) NOT NULL, + CONSTRAINT app_user_status_check CHECK (((status)::text = ANY ((ARRAY['INVITED'::character varying, 'ACTIVE'::character varying, 'BLOCKED'::character varying, 'SUSPENDED_SUBSCRIPTION'::character varying])::text[]))) +); + + +ALTER TABLE public.app_user OWNER TO legalconsenthub; + +-- +-- Name: application_form; Type: TABLE; Schema: public; Owner: legalconsenthub +-- + +CREATE TABLE public.application_form ( + is_template boolean NOT NULL, + created_at timestamp(6) without time zone NOT NULL, + modified_at timestamp(6) without time zone NOT NULL, + id uuid NOT NULL, + created_by_id character varying(255) NOT NULL, + last_modified_by_id character varying(255) NOT NULL, + name character varying(255) NOT NULL, + organization_id character varying(255), + status character varying(255) NOT NULL, + CONSTRAINT application_form_status_check CHECK (((status)::text = ANY ((ARRAY['DRAFT'::character varying, 'SUBMITTED'::character varying, 'APPROVED'::character varying, 'REJECTED'::character varying, 'SIGNED'::character varying])::text[]))) +); + + +ALTER TABLE public.application_form OWNER TO legalconsenthub; + +-- +-- Name: comment; Type: TABLE; Schema: public; Owner: legalconsenthub +-- + +CREATE TABLE public.comment ( + created_at timestamp(6) without time zone NOT NULL, + modified_at timestamp(6) without time zone NOT NULL, + application_form_id uuid NOT NULL, + form_element_id uuid NOT NULL, + id uuid NOT NULL, + created_by_id character varying(255) NOT NULL, + message character varying(255) NOT NULL +); + + +ALTER TABLE public.comment OWNER TO legalconsenthub; + +-- +-- Name: databasechangelog; Type: TABLE; Schema: public; Owner: legalconsenthub +-- + +CREATE TABLE public.databasechangelog ( + id character varying(255) NOT NULL, + author character varying(255) NOT NULL, + filename character varying(255) NOT NULL, + dateexecuted timestamp without time zone NOT NULL, + orderexecuted integer NOT NULL, + exectype character varying(10) NOT NULL, + md5sum character varying(35), + description character varying(255), + comments character varying(255), + tag character varying(255), + liquibase character varying(20), + contexts character varying(255), + labels character varying(255), + deployment_id character varying(10) +); + + +ALTER TABLE public.databasechangelog OWNER TO legalconsenthub; + +-- +-- Name: databasechangeloglock; Type: TABLE; Schema: public; Owner: legalconsenthub +-- + +CREATE TABLE public.databasechangeloglock ( + id integer NOT NULL, + locked boolean NOT NULL, + lockgranted timestamp without time zone, + lockedby character varying(255) +); + + +ALTER TABLE public.databasechangeloglock OWNER TO legalconsenthub; + +-- +-- Name: form_element; Type: TABLE; Schema: public; Owner: legalconsenthub +-- + +CREATE TABLE public.form_element ( + type smallint NOT NULL, + form_element_section_id uuid NOT NULL, + id uuid NOT NULL, + description character varying(255), + title character varying(255), + CONSTRAINT form_element_type_check CHECK (((type >= 0) AND (type <= 4))) +); + + +ALTER TABLE public.form_element OWNER TO legalconsenthub; + +-- +-- Name: form_element_options; Type: TABLE; Schema: public; Owner: legalconsenthub +-- + +CREATE TABLE public.form_element_options ( + employee_data_category smallint NOT NULL, + processing_purpose smallint NOT NULL, + form_element_id uuid NOT NULL, + label character varying(255) NOT NULL, + option_value character varying(255) NOT NULL, + CONSTRAINT form_element_options_employee_data_category_check CHECK (((employee_data_category >= 0) AND (employee_data_category <= 3))), + CONSTRAINT form_element_options_processing_purpose_check CHECK (((processing_purpose >= 0) AND (processing_purpose <= 3))) +); + + +ALTER TABLE public.form_element_options OWNER TO legalconsenthub; + +-- +-- Name: form_element_section; Type: TABLE; Schema: public; Owner: legalconsenthub +-- + +CREATE TABLE public.form_element_section ( + application_form_id uuid NOT NULL, + id uuid NOT NULL, + description character varying(255), + short_title character varying(255), + title character varying(255) NOT NULL +); + + +ALTER TABLE public.form_element_section OWNER TO legalconsenthub; + +-- +-- Name: notification; Type: TABLE; Schema: public; Owner: legalconsenthub +-- + +CREATE TABLE public.notification ( + is_read boolean NOT NULL, + created_at timestamp(6) without time zone NOT NULL, + id uuid NOT NULL, + click_target character varying(255) NOT NULL, + message text NOT NULL, + organization_id character varying(255) NOT NULL, + recipient_id character varying(255), + role character varying(255) NOT NULL, + title character varying(255) NOT NULL, + type character varying(255) NOT NULL, + CONSTRAINT notification_type_check CHECK (((type)::text = ANY ((ARRAY['INFO'::character varying, 'WARNING'::character varying, 'ERROR'::character varying])::text[]))) +); + + +ALTER TABLE public.notification OWNER TO legalconsenthub; + +-- +-- Name: user_organization_roles; Type: TABLE; Schema: public; Owner: legalconsenthub +-- + +CREATE TABLE public.user_organization_roles ( + organization_id character varying(255) NOT NULL, + role character varying(255) NOT NULL, + user_id character varying(255) NOT NULL +); + + +ALTER TABLE public.user_organization_roles OWNER TO legalconsenthub; + +-- +-- Data for Name: app_user; Type: TABLE DATA; Schema: public; Owner: legalconsenthub +-- + +COPY public.app_user (created_at, modified_at, id, name, status) FROM stdin; +2025-09-27 08:25:18.821058 2025-09-27 08:25:18.845236 umgS7DllaoSY17iNDK2FizXKeGJHQs2g Denis Lugowski ACTIVE +2025-09-27 08:26:08.333312 2025-09-27 08:26:08.335975 wMZ2SEChna9CdzLOhwfZ3Qb5vxh5YUmD BR ACTIVE +2025-09-27 08:27:28.27983 2025-09-27 08:27:28.282089 ZHbzeqHRYWe2USuDQuIHINAL22EjXVyb AG ACTIVE +\. + + +-- +-- Data for Name: application_form; Type: TABLE DATA; Schema: public; Owner: legalconsenthub +-- + +COPY public.application_form (is_template, created_at, modified_at, id, created_by_id, last_modified_by_id, name, organization_id, status) FROM stdin; +\. + + +-- +-- Data for Name: comment; Type: TABLE DATA; Schema: public; Owner: legalconsenthub +-- + +COPY public.comment (created_at, modified_at, application_form_id, form_element_id, id, created_by_id, message) FROM stdin; +\. + + +-- +-- Data for Name: databasechangelog; Type: TABLE DATA; Schema: public; Owner: legalconsenthub +-- + +COPY public.databasechangelog (id, author, filename, dateexecuted, orderexecuted, exectype, md5sum, description, comments, tag, liquibase, contexts, labels, deployment_id) FROM stdin; +raw includeAll db/migrations/001-schema.sql 2025-09-27 08:24:34.933234 1 EXECUTED 9:1ffb09d62ed861ad7fac642fc83efeaf sql \N 4.29.2 \N \N 8954274880 +\. + + +-- +-- Data for Name: databasechangeloglock; Type: TABLE DATA; Schema: public; Owner: legalconsenthub +-- + +COPY public.databasechangeloglock (id, locked, lockgranted, lockedby) FROM stdin; +1 f \N \N +\. + + +-- +-- Data for Name: form_element; Type: TABLE DATA; Schema: public; Owner: legalconsenthub +-- + +COPY public.form_element (type, form_element_section_id, id, description, title) FROM stdin; +\. + + +-- +-- Data for Name: form_element_options; Type: TABLE DATA; Schema: public; Owner: legalconsenthub +-- + +COPY public.form_element_options (employee_data_category, processing_purpose, form_element_id, label, option_value) FROM stdin; +\. + + +-- +-- Data for Name: form_element_section; Type: TABLE DATA; Schema: public; Owner: legalconsenthub +-- + +COPY public.form_element_section (application_form_id, id, description, short_title, title) FROM stdin; +\. + + +-- +-- Data for Name: notification; Type: TABLE DATA; Schema: public; Owner: legalconsenthub +-- + +COPY public.notification (is_read, created_at, id, click_target, message, organization_id, recipient_id, role, title, type) FROM stdin; +\. + + +-- +-- Data for Name: user_organization_roles; Type: TABLE DATA; Schema: public; Owner: legalconsenthub +-- + +COPY public.user_organization_roles (organization_id, role, user_id) FROM stdin; +AHA19yfn1CQW3gzsbtFRIpqKZUQqbh9V works_council_member wMZ2SEChna9CdzLOhwfZ3Qb5vxh5YUmD +\. + + +-- +-- Name: app_user app_user_pkey; Type: CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.app_user + ADD CONSTRAINT app_user_pkey PRIMARY KEY (id); + + +-- +-- Name: application_form application_form_pkey; Type: CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.application_form + ADD CONSTRAINT application_form_pkey PRIMARY KEY (id); + + +-- +-- Name: comment comment_pkey; Type: CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.comment + ADD CONSTRAINT comment_pkey PRIMARY KEY (id); + + +-- +-- Name: databasechangeloglock databasechangeloglock_pkey; Type: CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.databasechangeloglock + ADD CONSTRAINT databasechangeloglock_pkey PRIMARY KEY (id); + + +-- +-- Name: form_element form_element_pkey; Type: CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.form_element + ADD CONSTRAINT form_element_pkey PRIMARY KEY (id); + + +-- +-- Name: form_element_section form_element_section_pkey; Type: CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.form_element_section + ADD CONSTRAINT form_element_section_pkey PRIMARY KEY (id); + + +-- +-- Name: notification notification_pkey; Type: CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.notification + ADD CONSTRAINT notification_pkey PRIMARY KEY (id); + + +-- +-- Name: user_organization_roles user_organization_roles_pkey; Type: CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.user_organization_roles + ADD CONSTRAINT user_organization_roles_pkey PRIMARY KEY (organization_id, role, user_id); + + +-- +-- Name: application_form fk5yewx8bespw0uiivxioeh7q0d; Type: FK CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.application_form + ADD CONSTRAINT fk5yewx8bespw0uiivxioeh7q0d FOREIGN KEY (last_modified_by_id) REFERENCES public.app_user(id); + + +-- +-- Name: comment fkbbjqikfmgeacfsnaasxxqoygh; Type: FK CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.comment + ADD CONSTRAINT fkbbjqikfmgeacfsnaasxxqoygh FOREIGN KEY (created_by_id) REFERENCES public.app_user(id); + + +-- +-- Name: form_element fkdpr6k93m4hqllqjsvoa4or6mp; Type: FK CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.form_element + ADD CONSTRAINT fkdpr6k93m4hqllqjsvoa4or6mp FOREIGN KEY (form_element_section_id) REFERENCES public.form_element_section(id); + + +-- +-- Name: notification fkeg1j4hnp0y4lbm0y35hgr4e8r; Type: FK CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.notification + ADD CONSTRAINT fkeg1j4hnp0y4lbm0y35hgr4e8r FOREIGN KEY (recipient_id) REFERENCES public.app_user(id); + + +-- +-- Name: comment fkfg84w0i76tw9os13950272c6f; Type: FK CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.comment + ADD CONSTRAINT fkfg84w0i76tw9os13950272c6f FOREIGN KEY (form_element_id) REFERENCES public.form_element(id); + + +-- +-- Name: user_organization_roles fkhgmm93qre3up6hy63wcef3yqk; Type: FK CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.user_organization_roles + ADD CONSTRAINT fkhgmm93qre3up6hy63wcef3yqk FOREIGN KEY (user_id) REFERENCES public.app_user(id); + + +-- +-- Name: application_form fkhtad5onoy2jknhtyfmx6cvvey; Type: FK CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.application_form + ADD CONSTRAINT fkhtad5onoy2jknhtyfmx6cvvey FOREIGN KEY (created_by_id) REFERENCES public.app_user(id); + + +-- +-- Name: comment fklavy9axrt26sepreg5lqtuoap; Type: FK CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.comment + ADD CONSTRAINT fklavy9axrt26sepreg5lqtuoap FOREIGN KEY (application_form_id) REFERENCES public.application_form(id); + + +-- +-- Name: form_element_options fknq0lpby5nspv1xi27n9el6us6; Type: FK CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.form_element_options + ADD CONSTRAINT fknq0lpby5nspv1xi27n9el6us6 FOREIGN KEY (form_element_id) REFERENCES public.form_element(id); + + +-- +-- Name: form_element_section fktn0lreovauwf2v29doo70o3qs; Type: FK CONSTRAINT; Schema: public; Owner: legalconsenthub +-- + +ALTER TABLE ONLY public.form_element_section + ADD CONSTRAINT fktn0lreovauwf2v29doo70o3qs FOREIGN KEY (application_form_id) REFERENCES public.application_form(id); + + +-- +-- PostgreSQL database dump complete +-- + diff --git a/legalconsenthub/sqlite-backup.db b/legalconsenthub/sqlite-backup.db new file mode 100644 index 0000000000000000000000000000000000000000..e8c05c401f17f274f0212e938784c818c154b6b7 GIT binary patch literal 81920 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 Jzul#X{{!0O;I{w( literal 0 HcmV?d00001 diff --git a/manage-db.sh b/manage-db.sh new file mode 100755 index 0000000..228c32f --- /dev/null +++ b/manage-db.sh @@ -0,0 +1,327 @@ +#!/bin/bash + +# Database Management Script +# Handles backup and restore operations for both SQLite (frontend) and PostgreSQL (backend) + +set -e # Exit on any error + +# Configuration +SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" +BACKEND_DIR="$SCRIPT_DIR/legalconsenthub-backend" +FRONTEND_DIR="$SCRIPT_DIR/legalconsenthub" + +# Database files +SQLITE_DB="$FRONTEND_DIR/sqlite.db" +SQLITE_BACKUP="$FRONTEND_DIR/sqlite-backup.db" +POSTGRES_BACKUP="$BACKEND_DIR/src/main/resources/legalconsenthub-db-backup.sql" + +# PostgreSQL connection details +POSTGRES_HOST="localhost" +POSTGRES_PORT="5432" +POSTGRES_DB="legalconsenthub" +POSTGRES_USER="legalconsenthub" +POSTGRES_PASSWORD="legalconsenthub" + +# Colors for output +RED='\033[0;31m' +GREEN='\033[0;32m' +YELLOW='\033[1;33m' +BLUE='\033[0;34m' +NC='\033[0m' # No Color + +# Helper functions +log_info() { + echo -e "${BLUE}[INFO]${NC} $1" +} + +log_success() { + echo -e "${GREEN}[SUCCESS]${NC} $1" +} + +log_warning() { + echo -e "${YELLOW}[WARNING]${NC} $1" +} + +log_error() { + echo -e "${RED}[ERROR]${NC} $1" +} + +# Check if PostgreSQL container is running +check_postgres() { + # Check if the legalconsenthub-backend container is running + if docker ps --format "table {{.Names}}\t{{.Status}}" | grep -q "legalconsenthub-backend.*Up"; then + # Additional check to see if the database is ready + if docker exec legalconsenthub-backend pg_isready -U "$POSTGRES_USER" -d "$POSTGRES_DB" &>/dev/null; then + return 0 + fi + fi + return 1 +} + +# Check if PostgreSQL container exists and is running +ensure_postgres_running() { + if ! check_postgres; then + log_error "PostgreSQL container 'legalconsenthub-backend' is not running." + log_error "Please start the container before running backup/restore operations." + exit 1 + fi +} + +# Create backup of current SQLite database +backup_sqlite() { + log_info "Creating SQLite backup..." + if [ -f "$SQLITE_DB" ]; then + cp "$SQLITE_DB" "$SQLITE_BACKUP" + log_success "SQLite backup created: $SQLITE_BACKUP" + else + log_warning "SQLite database not found: $SQLITE_DB" + fi +} + +# Create backup of current PostgreSQL database +backup_postgres() { + log_info "Creating PostgreSQL backup..." + ensure_postgres_running + + # Create temporary backup file + local temp_backup="${POSTGRES_BACKUP}.tmp" + + # Generate backup with pg_dump + docker exec legalconsenthub-backend pg_dump \ + -U "$POSTGRES_USER" \ + -d "$POSTGRES_DB" \ + --no-owner \ + --no-privileges \ + --clean \ + --if-exists \ + > "$temp_backup" + + # Add force DROP statements at the beginning + { + echo "--" + echo "-- PostgreSQL database dump" + echo "--" + echo "" + echo "--" + echo "-- Force drop all tables and constraints to ensure clean restoration" + echo "--" + echo "" + echo "DROP TABLE IF EXISTS public.user_organization_roles CASCADE;" + echo "DROP TABLE IF EXISTS public.notification CASCADE;" + echo "DROP TABLE IF EXISTS public.form_element_section CASCADE;" + echo "DROP TABLE IF EXISTS public.form_element_options CASCADE;" + echo "DROP TABLE IF EXISTS public.form_element CASCADE;" + echo "DROP TABLE IF EXISTS public.comment CASCADE;" + echo "DROP TABLE IF EXISTS public.application_form CASCADE;" + echo "DROP TABLE IF EXISTS public.app_user CASCADE;" + echo "DROP TABLE IF EXISTS public.databasechangeloglock CASCADE;" + echo "DROP TABLE IF EXISTS public.databasechangelog CASCADE;" + echo "" + echo "-- Drop any remaining sequences, views, or other objects" + echo "DROP SEQUENCE IF EXISTS public.hibernate_sequence CASCADE;" + echo "" + echo "-- Reset database configuration" + + # Skip the first few lines of the original dump (headers) and append the rest + tail -n +4 "$temp_backup" + } > "$POSTGRES_BACKUP" + + # Remove temporary file + rm "$temp_backup" + + log_success "PostgreSQL backup created with force DROP statements: $POSTGRES_BACKUP" +} + +# Restore SQLite database from backup +restore_sqlite() { + log_info "Restoring SQLite database from backup..." + if [ -f "$SQLITE_BACKUP" ]; then + # Remove current database if it exists + if [ -f "$SQLITE_DB" ]; then + rm "$SQLITE_DB" + log_info "Removed current SQLite database" + fi + + # Copy backup to current database + cp "$SQLITE_BACKUP" "$SQLITE_DB" + log_success "SQLite database restored from: $SQLITE_BACKUP" + else + log_error "SQLite backup not found: $SQLITE_BACKUP" + exit 1 + fi +} + +# Restore PostgreSQL database from backup +restore_postgres() { + log_info "Restoring PostgreSQL database from backup..." + + if [ ! -f "$POSTGRES_BACKUP" ]; then + log_error "PostgreSQL backup not found: $POSTGRES_BACKUP" + exit 1 + fi + + ensure_postgres_running + + # Terminate all connections and drop/recreate database + log_info "Terminating all connections to PostgreSQL database..." + docker exec legalconsenthub-backend psql \ + -U "$POSTGRES_USER" \ + -d "postgres" \ + -c "SELECT pg_terminate_backend(pid) FROM pg_stat_activity WHERE datname = '$POSTGRES_DB' AND pid <> pg_backend_pid();" + + log_info "Dropping and recreating PostgreSQL database..." + docker exec legalconsenthub-backend psql \ + -U "$POSTGRES_USER" \ + -d "postgres" \ + -c "DROP DATABASE IF EXISTS $POSTGRES_DB;" + + docker exec legalconsenthub-backend psql \ + -U "$POSTGRES_USER" \ + -d "postgres" \ + -c "CREATE DATABASE $POSTGRES_DB OWNER $POSTGRES_USER;" + + # Restore from backup + log_info "Restoring database from backup file..." + docker exec -i legalconsenthub-backend psql \ + -U "$POSTGRES_USER" \ + -d "$POSTGRES_DB" \ + < "$POSTGRES_BACKUP" + + log_success "PostgreSQL database restored from: $POSTGRES_BACKUP" +} + +# Show usage information +show_usage() { + echo "Database Management Script" + echo "" + echo "Usage: $0 [COMMAND]" + echo "" + echo "Commands:" + echo " backup Create backups of current databases" + echo " restore Restore databases from backups" + echo " backup-sqlite Create backup of SQLite database only" + echo " backup-postgres Create backup of PostgreSQL database only" + echo " restore-sqlite Restore SQLite database from backup only" + echo " restore-postgres Restore PostgreSQL database from backup only" + echo " status Show current status" + echo " help Show this help message" + echo "" + echo "Note: PostgreSQL operations require the 'legalconsenthub-backend' container to be running." + echo "" + echo "Examples:" + echo " $0 backup # Create backups of both databases" + echo " $0 restore # Restore both databases from backups" + echo " $0 backup-sqlite # Backup only SQLite database" + echo " $0 status # Check database status" +} + +# Show current status +show_status() { + log_info "Database Status:" + echo "" + + # SQLite status + echo "SQLite Database:" + if [ -f "$SQLITE_DB" ]; then + local size=$(du -h "$SQLITE_DB" | cut -f1) + local modified=$(stat -c "%y" "$SQLITE_DB" 2>/dev/null || stat -f "%Sm" "$SQLITE_DB" 2>/dev/null || echo "Unknown") + echo " Current DB: ✅ $SQLITE_DB ($size, modified: $modified)" + else + echo " Current DB: ❌ Not found" + fi + + if [ -f "$SQLITE_BACKUP" ]; then + local backup_size=$(du -h "$SQLITE_BACKUP" | cut -f1) + local backup_modified=$(stat -c "%y" "$SQLITE_BACKUP" 2>/dev/null || stat -f "%Sm" "$SQLITE_BACKUP" 2>/dev/null || echo "Unknown") + echo " Backup: ✅ $SQLITE_BACKUP ($backup_size, modified: $backup_modified)" + else + echo " Backup: ❌ Not found" + fi + + echo "" + + # PostgreSQL status + echo "PostgreSQL Database:" + if check_postgres; then + echo " Container: ✅ legalconsenthub-backend (Running)" + local db_size=$(docker exec legalconsenthub-backend psql -U "$POSTGRES_USER" -d "$POSTGRES_DB" -t -c "SELECT pg_size_pretty(pg_database_size('$POSTGRES_DB'));" 2>/dev/null | xargs || echo "Unknown") + echo " Database: ✅ $POSTGRES_DB ($db_size)" + else + echo " Container: ❌ legalconsenthub-backend (Not running or not found)" + echo " Database: ❓ Cannot check (container not available)" + fi + + if [ -f "$POSTGRES_BACKUP" ]; then + local backup_size=$(du -h "$POSTGRES_BACKUP" | cut -f1) + local backup_modified=$(stat -c "%y" "$POSTGRES_BACKUP" 2>/dev/null || stat -f "%Sm" "$POSTGRES_BACKUP" 2>/dev/null || echo "Unknown") + echo " Backup: ✅ $POSTGRES_BACKUP ($backup_size, modified: $backup_modified)" + else + echo " Backup: ❌ Not found" + fi +} + +# Main script logic +main() { + case "${1:-help}" in + "backup") + log_info "Creating backups of both databases..." + backup_sqlite + backup_postgres + log_success "All backups completed successfully!" + ;; + "restore") + log_info "Restoring both databases from backups..." + restore_sqlite + restore_postgres + log_success "All databases restored successfully!" + ;; + "backup-sqlite") + backup_sqlite + ;; + "backup-postgres") + backup_postgres + ;; + "restore-sqlite") + restore_sqlite + ;; + "restore-postgres") + restore_postgres + ;; + "status") + show_status + ;; + "help"|"-h"|"--help") + show_usage + ;; + *) + log_error "Unknown command: $1" + echo "" + show_usage + exit 1 + ;; + esac +} + +# Check for required tools +check_dependencies() { + local missing_tools=() + + # Check for Docker + if ! command -v docker &> /dev/null; then + missing_tools+=("docker") + fi + + if [ ${#missing_tools[@]} -gt 0 ]; then + log_error "Missing required tools:" + for tool in "${missing_tools[@]}"; do + echo " - $tool" + done + echo "" + echo "Please install the missing tools and try again." + exit 1 + fi +} + +# Run dependency check and main function +check_dependencies +main "$@"