-- =====================================================
-- PORTFOLIO SCHEMA - PORTFOLIO GOALS TABLE
-- =====================================================
-- Description: User financial goals and progress tracking
-- Schema: portfolio
-- Author: Database Agent
-- Date: 2026-01-25
-- =====================================================

CREATE TABLE portfolio.portfolio_goals (
  id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
  user_id UUID NOT NULL REFERENCES auth.users(id) ON DELETE CASCADE,
  portfolio_id UUID REFERENCES portfolio.portfolios(id) ON DELETE SET NULL,
  name VARCHAR(100) NOT NULL,
  description TEXT,

  -- Goal targets
  target_amount DECIMAL(20, 2) NOT NULL,
  current_amount DECIMAL(20, 2) NOT NULL DEFAULT 0,
  target_date DATE NOT NULL,
  monthly_contribution DECIMAL(20, 2) NOT NULL DEFAULT 0,

  -- Progress tracking
  progress DECIMAL(5, 2) NOT NULL DEFAULT 0,
  projected_completion_date DATE,
  months_remaining INTEGER,
  required_monthly_contribution DECIMAL(20, 2),

  -- Status
  status portfolio.goal_status NOT NULL DEFAULT 'active',
  completed_at TIMESTAMPTZ,

  -- Metadata
  created_at TIMESTAMPTZ NOT NULL DEFAULT NOW(),
  updated_at TIMESTAMPTZ NOT NULL DEFAULT NOW(),

  -- Constraints
  CONSTRAINT chk_target_amount_positive CHECK (target_amount > 0),
  CONSTRAINT chk_current_amount_positive CHECK (current_amount >= 0),
  CONSTRAINT chk_progress_range CHECK (progress >= 0 AND progress <= 100),
  CONSTRAINT chk_monthly_contribution_positive CHECK (monthly_contribution >= 0)
);

-- Indexes
CREATE INDEX idx_portfolio_goals_user_id ON portfolio.portfolio_goals(user_id);
CREATE INDEX idx_portfolio_goals_portfolio_id ON portfolio.portfolio_goals(portfolio_id);
CREATE INDEX idx_portfolio_goals_status ON portfolio.portfolio_goals(status);
CREATE INDEX idx_portfolio_goals_target_date ON portfolio.portfolio_goals(target_date);

-- Comments
COMMENT ON TABLE portfolio.portfolio_goals IS 'User financial goals with progress tracking';
COMMENT ON COLUMN portfolio.portfolio_goals.target_amount IS 'Target amount to save/invest in USD';
COMMENT ON COLUMN portfolio.portfolio_goals.current_amount IS 'Current progress toward the goal';
COMMENT ON COLUMN portfolio.portfolio_goals.progress IS 'Percentage progress (0-100)';
COMMENT ON COLUMN portfolio.portfolio_goals.projected_completion_date IS 'Estimated date of goal completion based on contributions';
COMMENT ON COLUMN portfolio.portfolio_goals.required_monthly_contribution IS 'Monthly contribution needed to meet target on time';

-- Trigger for updated_at
CREATE TRIGGER trg_portfolio_goals_updated_at
  BEFORE UPDATE ON portfolio.portfolio_goals
  FOR EACH ROW
  EXECUTE FUNCTION portfolio.update_portfolio_updated_at();

-- Function to update goal progress
CREATE OR REPLACE FUNCTION portfolio.update_goal_progress()
RETURNS TRIGGER AS $$
BEGIN
  -- Calculate progress percentage
  IF NEW.target_amount > 0 THEN
    NEW.progress := LEAST(100, (NEW.current_amount / NEW.target_amount) * 100);
  END IF;

  -- Calculate months remaining
  NEW.months_remaining := GREATEST(0,
    EXTRACT(YEAR FROM AGE(NEW.target_date, CURRENT_DATE)) * 12 +
    EXTRACT(MONTH FROM AGE(NEW.target_date, CURRENT_DATE))
  )::INTEGER;

  -- Calculate required monthly contribution
  IF NEW.months_remaining > 0 THEN
    NEW.required_monthly_contribution := GREATEST(0,
      (NEW.target_amount - NEW.current_amount) / NEW.months_remaining
    );
  ELSE
    NEW.required_monthly_contribution := NEW.target_amount - NEW.current_amount;
  END IF;

  -- Calculate projected completion date based on current contributions
  IF NEW.monthly_contribution > 0 AND NEW.current_amount < NEW.target_amount THEN
    NEW.projected_completion_date := CURRENT_DATE +
      (CEIL((NEW.target_amount - NEW.current_amount) / NEW.monthly_contribution) * INTERVAL '1 month')::INTERVAL;
  END IF;

  -- Auto-complete if goal reached
  IF NEW.current_amount >= NEW.target_amount AND NEW.status = 'active' THEN
    NEW.status := 'completed';
    NEW.completed_at := NOW();
    NEW.progress := 100;
  END IF;

  RETURN NEW;
END;
$$ LANGUAGE plpgsql;

CREATE TRIGGER trg_portfolio_goals_progress
  BEFORE INSERT OR UPDATE ON portfolio.portfolio_goals
  FOR EACH ROW
  EXECUTE FUNCTION portfolio.update_goal_progress();
