From f998c65d2559d630a7c9acb2f999d2ece7699467 Mon Sep 17 00:00:00 2001 From: denis0001-dev Date: Mon, 29 Sep 2025 17:57:20 +0300 Subject: [PATCH] Fix duplicated logging --- backend/alembic/env.py | 1 + backend/app.py | 26 +++++++++++++++++++++++- backend/main.py | 7 +------ backend/migration.py | 45 +++++++++++++++++++++--------------------- 4 files changed, 50 insertions(+), 29 deletions(-) diff --git a/backend/alembic/env.py b/backend/alembic/env.py index dddd356..4779ac1 100644 --- a/backend/alembic/env.py +++ b/backend/alembic/env.py @@ -1,4 +1,5 @@ from logging.config import fileConfig +import logging from sqlalchemy import engine_from_config from sqlalchemy import pool diff --git a/backend/app.py b/backend/app.py index dd2ee15..0570982 100644 --- a/backend/app.py +++ b/backend/app.py @@ -1,10 +1,34 @@ from fastapi import FastAPI from fastapi.middleware.cors import CORSMiddleware +import logging +from contextlib import asynccontextmanager +from migration import run_migrations from routes import account, messaging, profile, push +# Configure logging +logger = logging.getLogger("uvicorn.error") +logger.handlers.clear() + +@asynccontextmanager +async def lifespan(app: FastAPI): + """Handle application lifespan events.""" + # Startup + try: + logger.info("Starting database migration check...") + run_migrations() + logger.info("Database migrations completed successfully.") + except Exception as e: + logger.error(f"Failed to run database migrations: {e}") + raise + + yield + + # Shutdown (if needed in the future) + # logger.info("Application shutdown") + # Инициализация FastAPI -app = FastAPI(title="PixelChat") +app = FastAPI(title="FromChat", lifespan=lifespan) # CORS app.add_middleware( diff --git a/backend/main.py b/backend/main.py index d0714f1..63204f8 100644 --- a/backend/main.py +++ b/backend/main.py @@ -4,9 +4,4 @@ from models import * from validation import * from utils import * from dependencies import * -from migration import run_migrations -from app import * - -# Run database migrations on startup -print("Starting database migration check...") -run_migrations() \ No newline at end of file +from app import * \ No newline at end of file diff --git a/backend/migration.py b/backend/migration.py index 6a16eab..fc016c1 100644 --- a/backend/migration.py +++ b/backend/migration.py @@ -3,13 +3,14 @@ Database migration utility using Alembic. This module handles running database migrations on startup. """ import os -import sys +import logging from alembic import command from alembic.config import Config from alembic.runtime.migration import MigrationContext from sqlalchemy import create_engine from constants import DATABASE_URL +logger = logging.getLogger("uvicorn.error") def run_migrations(): """ @@ -36,7 +37,7 @@ def run_migrations(): migration_files = [f for f in os.listdir(versions_dir) if f.endswith('.py') and not f.startswith('__')] if not migration_files: - print("No migration files found. Creating initial migration...") + logger.info("No migration files found. Creating initial migration...") # Check if database exists and has tables engine = create_engine(DATABASE_URL) with engine.connect() as connection: @@ -45,7 +46,7 @@ def run_migrations(): existing_tables = result.fetchall() if existing_tables: - print("Found existing database with tables. Creating migration to match current schema...") + logger.info("Found existing database with tables. Creating migration to match current schema...") # Create migration with autogenerate to detect differences command.revision(alembic_cfg, autogenerate=True, message="Initial migration from existing database") @@ -60,26 +61,26 @@ def run_migrations(): with open(migration_path, 'r') as f: content = f.read() if 'pass' in content and 'op.create_table' not in content and 'op.add_column' not in content: - print("Generated migration is empty. Creating complete schema migration...") + logger.info("Generated migration is empty. Creating complete schema migration...") # Remove the empty migration os.remove(migration_path) # Create a complete migration _create_complete_migration(alembic_cfg) else: - print("No existing tables found. Creating fresh migration...") + logger.info("No existing tables found. Creating fresh migration...") # Create fresh migration command.revision(alembic_cfg, autogenerate=True, message="Initial migration") - print("Initial migration created successfully.") + logger.info("Initial migration created successfully.") # Run the upgrade command - print("Running database migrations...") + logger.info("Running database migrations...") command.upgrade(alembic_cfg, "head") - print("Database migrations completed successfully.") + logger.info("Database migrations completed successfully.") except Exception as e: - print(f"Error running database migrations: {e}") + logger.error(f"Error running database migrations: {e}") # Fully automated recovery - handle ALL error scenarios - print("Attempting automated recovery...") + logger.info("Attempting automated recovery...") try: # Clear the alembic_version table to reset state engine = create_engine(DATABASE_URL) @@ -95,19 +96,19 @@ def run_migrations(): os.remove(os.path.join(versions_dir, file)) # Create a completely fresh migration with full schema - print("Creating fresh migration with complete schema...") + logger.info("Creating fresh migration with complete schema...") _create_complete_migration(alembic_cfg) # Run the migration command.upgrade(alembic_cfg, "head") - print("Automated recovery completed successfully.") + logger.info("Automated recovery completed successfully.") except Exception as recovery_error: - print(f"Automated recovery failed: {recovery_error}") + logger.error(f"Automated recovery failed: {recovery_error}") # Last resort: create database using SQLAlchemy directly - print("Using fallback: creating database directly...") + logger.info("Using fallback: creating database directly...") _create_database_directly() - print("Database created successfully using fallback method.") + logger.info("Database created successfully using fallback method.") def _create_complete_migration(alembic_cfg): @@ -346,14 +347,14 @@ def _create_database_directly(): alter_sql = f"ALTER TABLE {table_name} ADD COLUMN {column.name} {sql_type} {nullable}" try: connection.execute(text(alter_sql)) - print(f"Added column {column.name} to {table_name}") + logger.info(f"Added column {column.name} to {table_name}") # Update existing rows with current timestamp update_sql = f"UPDATE {table_name} SET {column.name} = CURRENT_TIMESTAMP WHERE {column.name} IS NULL" connection.execute(text(update_sql)) - print(f"Updated {column.name} with current timestamp") + logger.info(f"Updated {column.name} with current timestamp") except Exception as e: - print(f"Could not add column {column.name}: {e}") + logger.error(f"Could not add column {column.name}: {e}") else: # Handle other column types with defaults default_clause = "" @@ -367,12 +368,12 @@ def _create_database_directly(): alter_sql = f"ALTER TABLE {table_name} ADD COLUMN {column.name} {sql_type} {nullable}{default_clause}" try: connection.execute(text(alter_sql)) - print(f"Added column {column.name} to {table_name}") + logger.info(f"Added column {column.name} to {table_name}") except Exception as e: - print(f"Could not add column {column.name}: {e}") + logger.error(f"Could not add column {column.name}: {e}") else: # Table doesn't exist, create it - print(f"Creating table {table_name}") + logger.info(f"Creating table {table_name}") # Create alembic_version table manually connection.execute(text(""" @@ -437,7 +438,7 @@ def check_migration_status(): return current_rev != head_rev except Exception as e: - print(f"Error checking migration status: {e}") + logger.error(f"Error checking migration status: {e}") return True # Assume migrations are needed if we can't check