Include full contents of all nested repositories
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
272
letsbe-hub/prisma/migrations/20260106134433_init/migration.sql
Normal file
272
letsbe-hub/prisma/migrations/20260106134433_init/migration.sql
Normal file
@@ -0,0 +1,272 @@
|
||||
-- CreateEnum
|
||||
CREATE TYPE "UserStatus" AS ENUM ('PENDING_VERIFICATION', 'ACTIVE', 'SUSPENDED');
|
||||
|
||||
-- CreateEnum
|
||||
CREATE TYPE "StaffRole" AS ENUM ('ADMIN', 'SUPPORT');
|
||||
|
||||
-- CreateEnum
|
||||
CREATE TYPE "SubscriptionPlan" AS ENUM ('TRIAL', 'STARTER', 'PRO', 'ENTERPRISE');
|
||||
|
||||
-- CreateEnum
|
||||
CREATE TYPE "SubscriptionTier" AS ENUM ('HUB_DASHBOARD', 'ADVANCED');
|
||||
|
||||
-- CreateEnum
|
||||
CREATE TYPE "SubscriptionStatus" AS ENUM ('TRIAL', 'ACTIVE', 'CANCELED', 'PAST_DUE');
|
||||
|
||||
-- CreateEnum
|
||||
CREATE TYPE "OrderStatus" AS ENUM ('PAYMENT_CONFIRMED', 'AWAITING_SERVER', 'SERVER_READY', 'DNS_PENDING', 'DNS_READY', 'PROVISIONING', 'FULFILLED', 'EMAIL_CONFIGURED', 'FAILED');
|
||||
|
||||
-- CreateEnum
|
||||
CREATE TYPE "JobStatus" AS ENUM ('PENDING', 'CLAIMED', 'RUNNING', 'COMPLETED', 'FAILED', 'DEAD');
|
||||
|
||||
-- CreateEnum
|
||||
CREATE TYPE "LogLevel" AS ENUM ('DEBUG', 'INFO', 'WARN', 'ERROR');
|
||||
|
||||
-- CreateEnum
|
||||
CREATE TYPE "ServerConnectionStatus" AS ENUM ('PENDING', 'REGISTERED', 'ONLINE', 'OFFLINE');
|
||||
|
||||
-- CreateEnum
|
||||
CREATE TYPE "CommandStatus" AS ENUM ('PENDING', 'SENT', 'EXECUTING', 'COMPLETED', 'FAILED');
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "users" (
|
||||
"id" TEXT NOT NULL,
|
||||
"email" TEXT NOT NULL,
|
||||
"password_hash" TEXT NOT NULL,
|
||||
"name" TEXT,
|
||||
"company" TEXT,
|
||||
"status" "UserStatus" NOT NULL DEFAULT 'PENDING_VERIFICATION',
|
||||
"email_verified" TIMESTAMP(3),
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
"updated_at" TIMESTAMP(3) NOT NULL,
|
||||
|
||||
CONSTRAINT "users_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "staff" (
|
||||
"id" TEXT NOT NULL,
|
||||
"email" TEXT NOT NULL,
|
||||
"password_hash" TEXT NOT NULL,
|
||||
"name" TEXT NOT NULL,
|
||||
"role" "StaffRole" NOT NULL DEFAULT 'SUPPORT',
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
"updated_at" TIMESTAMP(3) NOT NULL,
|
||||
|
||||
CONSTRAINT "staff_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "subscriptions" (
|
||||
"id" TEXT NOT NULL,
|
||||
"user_id" TEXT NOT NULL,
|
||||
"plan" "SubscriptionPlan" NOT NULL DEFAULT 'TRIAL',
|
||||
"tier" "SubscriptionTier" NOT NULL DEFAULT 'HUB_DASHBOARD',
|
||||
"token_limit" INTEGER NOT NULL DEFAULT 10000,
|
||||
"tokens_used" INTEGER NOT NULL DEFAULT 0,
|
||||
"trial_ends_at" TIMESTAMP(3),
|
||||
"stripe_customer_id" TEXT,
|
||||
"stripe_subscription_id" TEXT,
|
||||
"status" "SubscriptionStatus" NOT NULL DEFAULT 'TRIAL',
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
"updated_at" TIMESTAMP(3) NOT NULL,
|
||||
|
||||
CONSTRAINT "subscriptions_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "orders" (
|
||||
"id" TEXT NOT NULL,
|
||||
"user_id" TEXT NOT NULL,
|
||||
"status" "OrderStatus" NOT NULL DEFAULT 'PAYMENT_CONFIRMED',
|
||||
"tier" "SubscriptionTier" NOT NULL,
|
||||
"domain" TEXT NOT NULL,
|
||||
"tools" TEXT[],
|
||||
"config_json" JSONB NOT NULL,
|
||||
"server_ip" TEXT,
|
||||
"server_password_encrypted" TEXT,
|
||||
"ssh_port" INTEGER NOT NULL DEFAULT 22,
|
||||
"portainer_url" TEXT,
|
||||
"dashboard_url" TEXT,
|
||||
"failure_reason" TEXT,
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
"updated_at" TIMESTAMP(3) NOT NULL,
|
||||
"server_ready_at" TIMESTAMP(3),
|
||||
"provisioning_started_at" TIMESTAMP(3),
|
||||
"completed_at" TIMESTAMP(3),
|
||||
|
||||
CONSTRAINT "orders_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "provisioning_logs" (
|
||||
"id" TEXT NOT NULL,
|
||||
"order_id" TEXT NOT NULL,
|
||||
"level" "LogLevel" NOT NULL DEFAULT 'INFO',
|
||||
"message" TEXT NOT NULL,
|
||||
"step" TEXT,
|
||||
"timestamp" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
|
||||
CONSTRAINT "provisioning_logs_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "provisioning_jobs" (
|
||||
"id" TEXT NOT NULL,
|
||||
"order_id" TEXT NOT NULL,
|
||||
"job_type" TEXT NOT NULL,
|
||||
"status" "JobStatus" NOT NULL DEFAULT 'PENDING',
|
||||
"priority" INTEGER NOT NULL DEFAULT 0,
|
||||
"claimed_at" TIMESTAMP(3),
|
||||
"claimed_by" TEXT,
|
||||
"container_name" TEXT,
|
||||
"attempt" INTEGER NOT NULL DEFAULT 1,
|
||||
"max_attempts" INTEGER NOT NULL DEFAULT 3,
|
||||
"next_retry_at" TIMESTAMP(3),
|
||||
"config_snapshot" JSONB NOT NULL,
|
||||
"runner_token_hash" TEXT,
|
||||
"result" JSONB,
|
||||
"error" TEXT,
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
"updated_at" TIMESTAMP(3) NOT NULL,
|
||||
"completed_at" TIMESTAMP(3),
|
||||
|
||||
CONSTRAINT "provisioning_jobs_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "job_logs" (
|
||||
"id" TEXT NOT NULL,
|
||||
"job_id" TEXT NOT NULL,
|
||||
"level" "LogLevel" NOT NULL DEFAULT 'INFO',
|
||||
"message" TEXT NOT NULL,
|
||||
"step" TEXT,
|
||||
"progress" INTEGER,
|
||||
"timestamp" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
|
||||
CONSTRAINT "job_logs_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "token_usage" (
|
||||
"id" TEXT NOT NULL,
|
||||
"user_id" TEXT NOT NULL,
|
||||
"instance_id" TEXT,
|
||||
"operation" TEXT NOT NULL,
|
||||
"tokens_input" INTEGER NOT NULL,
|
||||
"tokens_output" INTEGER NOT NULL,
|
||||
"model" TEXT NOT NULL,
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
|
||||
CONSTRAINT "token_usage_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "runner_tokens" (
|
||||
"id" TEXT NOT NULL,
|
||||
"token_hash" TEXT NOT NULL,
|
||||
"name" TEXT NOT NULL,
|
||||
"is_active" BOOLEAN NOT NULL DEFAULT true,
|
||||
"last_used" TIMESTAMP(3),
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
|
||||
CONSTRAINT "runner_tokens_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "server_connections" (
|
||||
"id" TEXT NOT NULL,
|
||||
"order_id" TEXT NOT NULL,
|
||||
"registration_token" TEXT NOT NULL,
|
||||
"hub_api_key" TEXT,
|
||||
"orchestrator_url" TEXT,
|
||||
"agent_version" TEXT,
|
||||
"status" "ServerConnectionStatus" NOT NULL DEFAULT 'PENDING',
|
||||
"registered_at" TIMESTAMP(3),
|
||||
"last_heartbeat" TIMESTAMP(3),
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
"updated_at" TIMESTAMP(3) NOT NULL,
|
||||
|
||||
CONSTRAINT "server_connections_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "remote_commands" (
|
||||
"id" TEXT NOT NULL,
|
||||
"server_connection_id" TEXT NOT NULL,
|
||||
"type" TEXT NOT NULL,
|
||||
"payload" JSONB NOT NULL,
|
||||
"status" "CommandStatus" NOT NULL DEFAULT 'PENDING',
|
||||
"result" JSONB,
|
||||
"error_message" TEXT,
|
||||
"queued_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
"sent_at" TIMESTAMP(3),
|
||||
"executed_at" TIMESTAMP(3),
|
||||
"completed_at" TIMESTAMP(3),
|
||||
"initiated_by" TEXT,
|
||||
|
||||
CONSTRAINT "remote_commands_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "users_email_key" ON "users"("email");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "staff_email_key" ON "staff"("email");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "provisioning_logs_order_id_timestamp_idx" ON "provisioning_logs"("order_id", "timestamp");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "provisioning_jobs_status_priority_created_at_idx" ON "provisioning_jobs"("status", "priority", "created_at");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "provisioning_jobs_order_id_idx" ON "provisioning_jobs"("order_id");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "job_logs_job_id_timestamp_idx" ON "job_logs"("job_id", "timestamp");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "token_usage_user_id_created_at_idx" ON "token_usage"("user_id", "created_at");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "runner_tokens_token_hash_key" ON "runner_tokens"("token_hash");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "server_connections_order_id_key" ON "server_connections"("order_id");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "server_connections_registration_token_key" ON "server_connections"("registration_token");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "server_connections_hub_api_key_key" ON "server_connections"("hub_api_key");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "remote_commands_server_connection_id_status_idx" ON "remote_commands"("server_connection_id", "status");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "remote_commands_status_queued_at_idx" ON "remote_commands"("status", "queued_at");
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "subscriptions" ADD CONSTRAINT "subscriptions_user_id_fkey" FOREIGN KEY ("user_id") REFERENCES "users"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "orders" ADD CONSTRAINT "orders_user_id_fkey" FOREIGN KEY ("user_id") REFERENCES "users"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "provisioning_logs" ADD CONSTRAINT "provisioning_logs_order_id_fkey" FOREIGN KEY ("order_id") REFERENCES "orders"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "provisioning_jobs" ADD CONSTRAINT "provisioning_jobs_order_id_fkey" FOREIGN KEY ("order_id") REFERENCES "orders"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "job_logs" ADD CONSTRAINT "job_logs_job_id_fkey" FOREIGN KEY ("job_id") REFERENCES "provisioning_jobs"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "token_usage" ADD CONSTRAINT "token_usage_user_id_fkey" FOREIGN KEY ("user_id") REFERENCES "users"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "server_connections" ADD CONSTRAINT "server_connections_order_id_fkey" FOREIGN KEY ("order_id") REFERENCES "orders"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "remote_commands" ADD CONSTRAINT "remote_commands_server_connection_id_fkey" FOREIGN KEY ("server_connection_id") REFERENCES "server_connections"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
@@ -0,0 +1,20 @@
|
||||
-- AlterTable
|
||||
ALTER TABLE "orders" ADD COLUMN "company_name" TEXT,
|
||||
ADD COLUMN "customer" TEXT,
|
||||
ADD COLUMN "license_key" TEXT;
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "system_settings" (
|
||||
"id" TEXT NOT NULL,
|
||||
"key" TEXT NOT NULL,
|
||||
"value" TEXT NOT NULL,
|
||||
"encrypted" BOOLEAN NOT NULL DEFAULT false,
|
||||
"category" TEXT NOT NULL DEFAULT 'general',
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
"updated_at" TIMESTAMP(3) NOT NULL,
|
||||
|
||||
CONSTRAINT "system_settings_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "system_settings_key_key" ON "system_settings"("key");
|
||||
@@ -0,0 +1,57 @@
|
||||
-- CreateEnum
|
||||
CREATE TYPE "AutomationMode" AS ENUM ('AUTO', 'MANUAL', 'PAUSED');
|
||||
|
||||
-- CreateEnum
|
||||
CREATE TYPE "DnsRecordStatus" AS ENUM ('PENDING', 'VERIFIED', 'MISMATCH', 'NOT_FOUND', 'ERROR', 'SKIPPED');
|
||||
|
||||
-- AlterTable
|
||||
ALTER TABLE "orders" ADD COLUMN "automationMode" "AutomationMode" NOT NULL DEFAULT 'MANUAL',
|
||||
ADD COLUMN "automation_paused_at" TIMESTAMP(3),
|
||||
ADD COLUMN "automation_paused_reason" TEXT,
|
||||
ADD COLUMN "dns_verified_at" TIMESTAMP(3),
|
||||
ADD COLUMN "netcup_server_id" TEXT,
|
||||
ADD COLUMN "source" TEXT;
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "dns_verifications" (
|
||||
"id" TEXT NOT NULL,
|
||||
"order_id" TEXT NOT NULL,
|
||||
"wildcard_passed" BOOLEAN NOT NULL DEFAULT false,
|
||||
"manual_override" BOOLEAN NOT NULL DEFAULT false,
|
||||
"all_passed" BOOLEAN NOT NULL DEFAULT false,
|
||||
"total_subdomains" INTEGER NOT NULL DEFAULT 0,
|
||||
"passed_count" INTEGER NOT NULL DEFAULT 0,
|
||||
"last_checked_at" TIMESTAMP(3),
|
||||
"verified_at" TIMESTAMP(3),
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
"updated_at" TIMESTAMP(3) NOT NULL,
|
||||
|
||||
CONSTRAINT "dns_verifications_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "dns_records" (
|
||||
"id" TEXT NOT NULL,
|
||||
"dns_verification_id" TEXT NOT NULL,
|
||||
"subdomain" TEXT NOT NULL,
|
||||
"full_domain" TEXT NOT NULL,
|
||||
"expected_ip" TEXT NOT NULL,
|
||||
"resolved_ip" TEXT,
|
||||
"status" "DnsRecordStatus" NOT NULL DEFAULT 'PENDING',
|
||||
"error_message" TEXT,
|
||||
"checked_at" TIMESTAMP(3),
|
||||
|
||||
CONSTRAINT "dns_records_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "dns_verifications_order_id_key" ON "dns_verifications"("order_id");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "dns_records_dns_verification_id_idx" ON "dns_records"("dns_verification_id");
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "dns_verifications" ADD CONSTRAINT "dns_verifications_order_id_fkey" FOREIGN KEY ("order_id") REFERENCES "orders"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "dns_records" ADD CONSTRAINT "dns_records_dns_verification_id_fkey" FOREIGN KEY ("dns_verification_id") REFERENCES "dns_verifications"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
@@ -0,0 +1,4 @@
|
||||
-- AlterTable
|
||||
ALTER TABLE "orders" ADD COLUMN "credentials_synced_at" TIMESTAMP(3),
|
||||
ADD COLUMN "portainer_password_enc" TEXT,
|
||||
ADD COLUMN "portainer_username" TEXT;
|
||||
@@ -0,0 +1,143 @@
|
||||
-- CreateEnum
|
||||
CREATE TYPE "ErrorSeverity" AS ENUM ('INFO', 'WARNING', 'ERROR', 'CRITICAL');
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "enterprise_clients" (
|
||||
"id" TEXT NOT NULL,
|
||||
"name" TEXT NOT NULL,
|
||||
"company_name" TEXT,
|
||||
"contact_email" TEXT NOT NULL,
|
||||
"contact_phone" TEXT,
|
||||
"notes" TEXT,
|
||||
"is_active" BOOLEAN NOT NULL DEFAULT true,
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
"updated_at" TIMESTAMP(3) NOT NULL,
|
||||
|
||||
CONSTRAINT "enterprise_clients_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "enterprise_servers" (
|
||||
"id" TEXT NOT NULL,
|
||||
"client_id" TEXT NOT NULL,
|
||||
"netcup_server_id" TEXT NOT NULL,
|
||||
"nickname" TEXT,
|
||||
"purpose" TEXT,
|
||||
"is_active" BOOLEAN NOT NULL DEFAULT true,
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
"updated_at" TIMESTAMP(3) NOT NULL,
|
||||
"portainer_url" TEXT,
|
||||
"portainer_username" TEXT,
|
||||
"portainer_password_enc" TEXT,
|
||||
|
||||
CONSTRAINT "enterprise_servers_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "server_stats_snapshots" (
|
||||
"id" TEXT NOT NULL,
|
||||
"server_id" TEXT NOT NULL,
|
||||
"client_id" TEXT NOT NULL,
|
||||
"timestamp" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
"cpu_percent" DOUBLE PRECISION,
|
||||
"memory_used_mb" DOUBLE PRECISION,
|
||||
"memory_total_mb" DOUBLE PRECISION,
|
||||
"disk_read_mbps" DOUBLE PRECISION,
|
||||
"disk_write_mbps" DOUBLE PRECISION,
|
||||
"network_in_mbps" DOUBLE PRECISION,
|
||||
"network_out_mbps" DOUBLE PRECISION,
|
||||
"containers_running" INTEGER,
|
||||
"containers_stopped" INTEGER,
|
||||
|
||||
CONSTRAINT "server_stats_snapshots_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "error_detection_rules" (
|
||||
"id" TEXT NOT NULL,
|
||||
"client_id" TEXT NOT NULL,
|
||||
"name" TEXT NOT NULL,
|
||||
"pattern" TEXT NOT NULL,
|
||||
"severity" "ErrorSeverity" NOT NULL DEFAULT 'WARNING',
|
||||
"is_active" BOOLEAN NOT NULL DEFAULT true,
|
||||
"description" TEXT,
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
"updated_at" TIMESTAMP(3) NOT NULL,
|
||||
|
||||
CONSTRAINT "error_detection_rules_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "detected_errors" (
|
||||
"id" TEXT NOT NULL,
|
||||
"server_id" TEXT NOT NULL,
|
||||
"rule_id" TEXT NOT NULL,
|
||||
"container_id" TEXT,
|
||||
"container_name" TEXT,
|
||||
"log_line" TEXT NOT NULL,
|
||||
"context" TEXT,
|
||||
"timestamp" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
"acknowledged_at" TIMESTAMP(3),
|
||||
"acknowledged_by" TEXT,
|
||||
|
||||
CONSTRAINT "detected_errors_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "security_verification_codes" (
|
||||
"id" TEXT NOT NULL,
|
||||
"client_id" TEXT NOT NULL,
|
||||
"code" TEXT NOT NULL,
|
||||
"action" TEXT NOT NULL,
|
||||
"target_server_id" TEXT NOT NULL,
|
||||
"expires_at" TIMESTAMP(3) NOT NULL,
|
||||
"used_at" TIMESTAMP(3),
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
|
||||
CONSTRAINT "security_verification_codes_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "enterprise_servers_client_id_idx" ON "enterprise_servers"("client_id");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "enterprise_servers_client_id_netcup_server_id_key" ON "enterprise_servers"("client_id", "netcup_server_id");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "server_stats_snapshots_server_id_timestamp_idx" ON "server_stats_snapshots"("server_id", "timestamp");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "server_stats_snapshots_client_id_timestamp_idx" ON "server_stats_snapshots"("client_id", "timestamp");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "error_detection_rules_client_id_idx" ON "error_detection_rules"("client_id");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "detected_errors_server_id_timestamp_idx" ON "detected_errors"("server_id", "timestamp");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "detected_errors_rule_id_timestamp_idx" ON "detected_errors"("rule_id", "timestamp");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "security_verification_codes_client_id_code_idx" ON "security_verification_codes"("client_id", "code");
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "enterprise_servers" ADD CONSTRAINT "enterprise_servers_client_id_fkey" FOREIGN KEY ("client_id") REFERENCES "enterprise_clients"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "server_stats_snapshots" ADD CONSTRAINT "server_stats_snapshots_server_id_fkey" FOREIGN KEY ("server_id") REFERENCES "enterprise_servers"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "server_stats_snapshots" ADD CONSTRAINT "server_stats_snapshots_client_id_fkey" FOREIGN KEY ("client_id") REFERENCES "enterprise_clients"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "error_detection_rules" ADD CONSTRAINT "error_detection_rules_client_id_fkey" FOREIGN KEY ("client_id") REFERENCES "enterprise_clients"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "detected_errors" ADD CONSTRAINT "detected_errors_server_id_fkey" FOREIGN KEY ("server_id") REFERENCES "enterprise_servers"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "detected_errors" ADD CONSTRAINT "detected_errors_rule_id_fkey" FOREIGN KEY ("rule_id") REFERENCES "error_detection_rules"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "security_verification_codes" ADD CONSTRAINT "security_verification_codes_client_id_fkey" FOREIGN KEY ("client_id") REFERENCES "enterprise_clients"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
@@ -0,0 +1,84 @@
|
||||
-- CreateEnum
|
||||
CREATE TYPE "ContainerEventType" AS ENUM ('CRASH', 'OOM_KILLED', 'RESTART', 'STOPPED');
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "log_scan_positions" (
|
||||
"id" TEXT NOT NULL,
|
||||
"server_id" TEXT NOT NULL,
|
||||
"container_id" TEXT NOT NULL,
|
||||
"last_line_count" INTEGER NOT NULL DEFAULT 0,
|
||||
"last_log_hash" TEXT,
|
||||
"last_scanned_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
|
||||
CONSTRAINT "log_scan_positions_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "container_state_snapshots" (
|
||||
"id" TEXT NOT NULL,
|
||||
"server_id" TEXT NOT NULL,
|
||||
"container_id" TEXT NOT NULL,
|
||||
"container_name" TEXT NOT NULL,
|
||||
"state" TEXT NOT NULL,
|
||||
"exit_code" INTEGER,
|
||||
"captured_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
|
||||
CONSTRAINT "container_state_snapshots_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "container_events" (
|
||||
"id" TEXT NOT NULL,
|
||||
"server_id" TEXT NOT NULL,
|
||||
"container_id" TEXT NOT NULL,
|
||||
"container_name" TEXT NOT NULL,
|
||||
"event_type" "ContainerEventType" NOT NULL,
|
||||
"exit_code" INTEGER,
|
||||
"details" TEXT,
|
||||
"acknowledged_at" TIMESTAMP(3),
|
||||
"acknowledged_by" TEXT,
|
||||
"timestamp" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
|
||||
CONSTRAINT "container_events_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "notification_settings" (
|
||||
"id" TEXT NOT NULL,
|
||||
"client_id" TEXT NOT NULL,
|
||||
"enabled" BOOLEAN NOT NULL DEFAULT false,
|
||||
"critical_errors_only" BOOLEAN NOT NULL DEFAULT true,
|
||||
"container_crashes" BOOLEAN NOT NULL DEFAULT true,
|
||||
"recipients" TEXT[] DEFAULT ARRAY[]::TEXT[],
|
||||
"cooldown_minutes" INTEGER NOT NULL DEFAULT 30,
|
||||
"last_notified_at" TIMESTAMP(3),
|
||||
|
||||
CONSTRAINT "notification_settings_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "log_scan_positions_server_id_container_id_key" ON "log_scan_positions"("server_id", "container_id");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "container_state_snapshots_server_id_container_id_captured_a_idx" ON "container_state_snapshots"("server_id", "container_id", "captured_at");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "container_events_server_id_timestamp_idx" ON "container_events"("server_id", "timestamp");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "container_events_event_type_acknowledged_at_idx" ON "container_events"("event_type", "acknowledged_at");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "notification_settings_client_id_key" ON "notification_settings"("client_id");
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "log_scan_positions" ADD CONSTRAINT "log_scan_positions_server_id_fkey" FOREIGN KEY ("server_id") REFERENCES "enterprise_servers"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "container_state_snapshots" ADD CONSTRAINT "container_state_snapshots_server_id_fkey" FOREIGN KEY ("server_id") REFERENCES "enterprise_servers"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "container_events" ADD CONSTRAINT "container_events_server_id_fkey" FOREIGN KEY ("server_id") REFERENCES "enterprise_servers"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "notification_settings" ADD CONSTRAINT "notification_settings_client_id_fkey" FOREIGN KEY ("client_id") REFERENCES "enterprise_clients"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
@@ -0,0 +1,46 @@
|
||||
-- CreateEnum
|
||||
CREATE TYPE "StaffStatus" AS ENUM ('ACTIVE', 'SUSPENDED');
|
||||
|
||||
-- AlterEnum
|
||||
-- This migration adds more than one value to an enum.
|
||||
-- With PostgreSQL versions 11 and earlier, this is not possible
|
||||
-- in a single migration. This can be worked around by creating
|
||||
-- multiple migrations, each migration adding only one value to
|
||||
-- the enum.
|
||||
|
||||
|
||||
ALTER TYPE "StaffRole" ADD VALUE 'OWNER';
|
||||
ALTER TYPE "StaffRole" ADD VALUE 'MANAGER';
|
||||
|
||||
-- AlterTable
|
||||
ALTER TABLE "staff" ADD COLUMN "backup_codes_enc" TEXT,
|
||||
ADD COLUMN "invited_by" TEXT,
|
||||
ADD COLUMN "status" "StaffStatus" NOT NULL DEFAULT 'ACTIVE',
|
||||
ADD COLUMN "two_factor_enabled" BOOLEAN NOT NULL DEFAULT false,
|
||||
ADD COLUMN "two_factor_secret_enc" TEXT,
|
||||
ADD COLUMN "two_factor_verified_at" TIMESTAMP(3);
|
||||
|
||||
-- AlterTable
|
||||
ALTER TABLE "users" ADD COLUMN "backup_codes_enc" TEXT,
|
||||
ADD COLUMN "two_factor_enabled" BOOLEAN NOT NULL DEFAULT false,
|
||||
ADD COLUMN "two_factor_secret_enc" TEXT,
|
||||
ADD COLUMN "two_factor_verified_at" TIMESTAMP(3);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "staff_invitations" (
|
||||
"id" TEXT NOT NULL,
|
||||
"email" TEXT NOT NULL,
|
||||
"role" "StaffRole" NOT NULL DEFAULT 'SUPPORT',
|
||||
"token" TEXT NOT NULL,
|
||||
"expires_at" TIMESTAMP(3) NOT NULL,
|
||||
"invited_by" TEXT NOT NULL,
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
|
||||
CONSTRAINT "staff_invitations_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "staff_invitations_email_key" ON "staff_invitations"("email");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "staff_invitations_token_key" ON "staff_invitations"("token");
|
||||
@@ -0,0 +1,11 @@
|
||||
-- CreateTable
|
||||
CREATE TABLE "notification_cooldowns" (
|
||||
"id" TEXT NOT NULL,
|
||||
"type" TEXT NOT NULL,
|
||||
"last_sent_at" TIMESTAMP(3) NOT NULL,
|
||||
|
||||
CONSTRAINT "notification_cooldowns_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "notification_cooldowns_type_key" ON "notification_cooldowns"("type");
|
||||
@@ -0,0 +1,2 @@
|
||||
-- AlterTable
|
||||
ALTER TABLE "staff" ADD COLUMN "profile_photo_key" TEXT;
|
||||
@@ -0,0 +1,34 @@
|
||||
-- AlterTable: Add brute-force attempt tracking to security verification codes
|
||||
ALTER TABLE "security_verification_codes" ADD COLUMN "attempts" INTEGER NOT NULL DEFAULT 0;
|
||||
|
||||
-- AlterTable: Add hash-based API key lookup to server connections
|
||||
ALTER TABLE "server_connections" ADD COLUMN "hub_api_key_hash" TEXT;
|
||||
|
||||
-- CreateTable: DB-backed 2FA sessions (replacing in-memory Map)
|
||||
CREATE TABLE "pending_2fa_sessions" (
|
||||
"id" TEXT NOT NULL,
|
||||
"token" TEXT NOT NULL,
|
||||
"user_id" TEXT NOT NULL,
|
||||
"user_type" TEXT NOT NULL,
|
||||
"email" TEXT NOT NULL,
|
||||
"name" TEXT,
|
||||
"role" TEXT,
|
||||
"company" TEXT,
|
||||
"subscription" JSONB,
|
||||
"expires_at" TIMESTAMP(3) NOT NULL,
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
|
||||
CONSTRAINT "pending_2fa_sessions_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "pending_2fa_sessions_token_key" ON "pending_2fa_sessions"("token");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "pending_2fa_sessions_token_idx" ON "pending_2fa_sessions"("token");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE INDEX "pending_2fa_sessions_expires_at_idx" ON "pending_2fa_sessions"("expires_at");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "server_connections_hub_api_key_hash_key" ON "server_connections"("hub_api_key_hash");
|
||||
3
letsbe-hub/prisma/migrations/migration_lock.toml
Normal file
3
letsbe-hub/prisma/migrations/migration_lock.toml
Normal file
@@ -0,0 +1,3 @@
|
||||
# Please do not edit this file manually
|
||||
# It should be added in your version-control system (e.g., Git)
|
||||
provider = "postgresql"
|
||||
Reference in New Issue
Block a user