Loading backend/db.py +49 −32 Original line number Diff line number Diff line import os import pandas as pd import yfinance as yf from sqlalchemy import create_engine, text import psycopg2 from psycopg2.extras import execute_values from dotenv import load_dotenv from sqlalchemy.exc import OperationalError # Load environment variables from .env file load_dotenv() DATABASE_URL = os.getenv("DATABASE_URL", "postgresql://postgres:postgres@localhost:5432/postgres") engine = create_engine(DATABASE_URL) # Read database connection parameters from environment variables DB_HOST = os.getenv("DB_HOST", "db") DB_NAME = os.getenv("DB_NAME", "postgres") DB_USER = os.getenv("DB_USER", "postgres") DB_PASSWORD = os.getenv("POSTGRES_PASSWORD", "postgres") def get_connection(): return psycopg2.connect( host=DB_HOST, database=DB_NAME, user=DB_USER, password=DB_PASSWORD ) def init_db(): retries = 10 for i in range(retries): try: with engine.begin() as conn: # << ensures auto-commit conn.execute(text(""" with get_connection() as conn: with conn.cursor() as cur: cur.execute(""" CREATE TABLE IF NOT EXISTS nvda_stock ( date DATE PRIMARY KEY, open FLOAT, Loading @@ -24,15 +34,8 @@ def init_db(): close FLOAT, volume BIGINT ) """)) print("✅ Table nvda_stock ensured.") break except Exception as e: print(f"❌ Failed to initialize DB (attempt {i+1}/{retries}): {e}") time.sleep(2) else: raise Exception("❌ Could not initialize database after retries.") """) conn.commit() def store_nvda_data(): df = yf.Ticker("NVDA").history(period="5y") Loading @@ -40,11 +43,25 @@ def store_nvda_data(): df.reset_index(inplace=True) df.columns = ["date", "open", "high", "low", "close", "volume"] with engine.begin() as conn: df.to_sql("nvda_stock", con=conn, if_exists="append", index=False, method="multi") records = df.to_records(index=False) values = [tuple(r) for r in records] insert_query = """ INSERT INTO nvda_stock (date, open, high, low, close, volume) VALUES %s ON CONFLICT (date) DO NOTHING """ with get_connection() as conn: with conn.cursor() as cur: execute_values(cur, insert_query, values) conn.commit() def get_nvda_data(): with engine.connect() as conn: result = conn.execute(text("SELECT * FROM nvda_stock ORDER BY date DESC LIMIT 100")) rows = [dict(row) for row in result] return rows with get_connection() as conn: with conn.cursor() as cur: cur.execute("SELECT * FROM nvda_stock ORDER BY date DESC LIMIT 100") rows = cur.fetchall() columns = [desc[0] for desc in cur.description] result = [dict(zip(columns, row)) for row in rows] return result backend/requirements.txt +3 −5 Original line number Diff line number Diff line yfinance pandas SQLAlchemy psycopg2-binary requests tornado psycopg2-binary pandas yfinance python-dotenv docker-compose.yml +10 −4 Original line number Diff line number Diff line Loading @@ -3,8 +3,11 @@ version: "3.8" services: db: image: postgres env_file: - .env environment: DB_HOST: db DB_NAME: postgres DB_USER: postgres POSTGRES_PASSWORD: postgres ports: - "5432:5432" volumes: Loading @@ -14,8 +17,11 @@ services: backend: build: ./backend env_file: - .env environment: DB_HOST: db DB_NAME: postgres DB_USER: postgres POSTGRES_PASSWORD: postgres ports: - "8000:8000" volumes: Loading Loading
backend/db.py +49 −32 Original line number Diff line number Diff line import os import pandas as pd import yfinance as yf from sqlalchemy import create_engine, text import psycopg2 from psycopg2.extras import execute_values from dotenv import load_dotenv from sqlalchemy.exc import OperationalError # Load environment variables from .env file load_dotenv() DATABASE_URL = os.getenv("DATABASE_URL", "postgresql://postgres:postgres@localhost:5432/postgres") engine = create_engine(DATABASE_URL) # Read database connection parameters from environment variables DB_HOST = os.getenv("DB_HOST", "db") DB_NAME = os.getenv("DB_NAME", "postgres") DB_USER = os.getenv("DB_USER", "postgres") DB_PASSWORD = os.getenv("POSTGRES_PASSWORD", "postgres") def get_connection(): return psycopg2.connect( host=DB_HOST, database=DB_NAME, user=DB_USER, password=DB_PASSWORD ) def init_db(): retries = 10 for i in range(retries): try: with engine.begin() as conn: # << ensures auto-commit conn.execute(text(""" with get_connection() as conn: with conn.cursor() as cur: cur.execute(""" CREATE TABLE IF NOT EXISTS nvda_stock ( date DATE PRIMARY KEY, open FLOAT, Loading @@ -24,15 +34,8 @@ def init_db(): close FLOAT, volume BIGINT ) """)) print("✅ Table nvda_stock ensured.") break except Exception as e: print(f"❌ Failed to initialize DB (attempt {i+1}/{retries}): {e}") time.sleep(2) else: raise Exception("❌ Could not initialize database after retries.") """) conn.commit() def store_nvda_data(): df = yf.Ticker("NVDA").history(period="5y") Loading @@ -40,11 +43,25 @@ def store_nvda_data(): df.reset_index(inplace=True) df.columns = ["date", "open", "high", "low", "close", "volume"] with engine.begin() as conn: df.to_sql("nvda_stock", con=conn, if_exists="append", index=False, method="multi") records = df.to_records(index=False) values = [tuple(r) for r in records] insert_query = """ INSERT INTO nvda_stock (date, open, high, low, close, volume) VALUES %s ON CONFLICT (date) DO NOTHING """ with get_connection() as conn: with conn.cursor() as cur: execute_values(cur, insert_query, values) conn.commit() def get_nvda_data(): with engine.connect() as conn: result = conn.execute(text("SELECT * FROM nvda_stock ORDER BY date DESC LIMIT 100")) rows = [dict(row) for row in result] return rows with get_connection() as conn: with conn.cursor() as cur: cur.execute("SELECT * FROM nvda_stock ORDER BY date DESC LIMIT 100") rows = cur.fetchall() columns = [desc[0] for desc in cur.description] result = [dict(zip(columns, row)) for row in rows] return result
backend/requirements.txt +3 −5 Original line number Diff line number Diff line yfinance pandas SQLAlchemy psycopg2-binary requests tornado psycopg2-binary pandas yfinance python-dotenv
docker-compose.yml +10 −4 Original line number Diff line number Diff line Loading @@ -3,8 +3,11 @@ version: "3.8" services: db: image: postgres env_file: - .env environment: DB_HOST: db DB_NAME: postgres DB_USER: postgres POSTGRES_PASSWORD: postgres ports: - "5432:5432" volumes: Loading @@ -14,8 +17,11 @@ services: backend: build: ./backend env_file: - .env environment: DB_HOST: db DB_NAME: postgres DB_USER: postgres POSTGRES_PASSWORD: postgres ports: - "8000:8000" volumes: Loading