/**
 * Risk Assessment Store
 * Zustand store for risk questionnaire and profile management
 */

import { create } from 'zustand';
import { devtools } from 'zustand/middleware';
import {
  getQuestions,
  submitAssessment,
  getCurrentAssessment,
  getProfile,
  checkValidAssessment,
  getAssessmentHistory,
  getRecommendations,
  type RiskQuestion,
  type RiskAssessment,
  type RiskRecommendation,
  type SubmitAssessmentInput,
} from '../services/risk.service';

// ============================================================================
// State Interface
// ============================================================================

interface RiskState {
  // Risk data
  questions: RiskQuestion[];
  currentAssessment: RiskAssessment | null;
  userProfile: RiskAssessment | null;
  recommendations: RiskRecommendation | null;
  assessmentHistory: RiskAssessment[];
  isAssessmentValid: boolean;

  // Questionnaire progress
  currentQuestionIndex: number;
  answers: Record<string, string>;

  // Loading states
  loading: boolean;
  loadingQuestions: boolean;
  loadingProfile: boolean;
  loadingHistory: boolean;
  submitting: boolean;

  // Error state
  error: string | null;

  // Actions
  fetchQuestions: () => Promise<void>;
  submitAssessment: (completionTimeSeconds?: number) => Promise<RiskAssessment>;
  fetchProfile: (userId?: string) => Promise<void>;
  fetchCurrentAssessment: () => Promise<void>;
  fetchAssessmentHistory: () => Promise<void>;
  checkValidity: () => Promise<boolean>;

  // Questionnaire actions
  setAnswer: (questionId: string, answer: string) => void;
  nextQuestion: () => void;
  previousQuestion: () => void;
  goToQuestion: (index: number) => void;
  resetQuestionnaire: () => void;

  // Utility actions
  clearError: () => void;
  reset: () => void;
}

// ============================================================================
// Initial State
// ============================================================================

const initialState = {
  questions: [],
  currentAssessment: null,
  userProfile: null,
  recommendations: null,
  assessmentHistory: [],
  isAssessmentValid: false,
  currentQuestionIndex: 0,
  answers: {},
  loading: false,
  loadingQuestions: false,
  loadingProfile: false,
  loadingHistory: false,
  submitting: false,
  error: null,
};

// ============================================================================
// Store
// ============================================================================

export const useRiskStore = create<RiskState>()(
  devtools(
    (set, get) => ({
      ...initialState,

      // ========================================================================
      // Data Fetching Actions
      // ========================================================================

      fetchQuestions: async () => {
        set({ loadingQuestions: true, error: null });

        try {
          const questions = await getQuestions();
          set({ questions, loadingQuestions: false });
        } catch (error) {
          const message = error instanceof Error ? error.message : 'Error loading questions';
          set({ error: message, loadingQuestions: false });
        }
      },

      submitAssessment: async (completionTimeSeconds?: number) => {
        const { questions, answers } = get();

        // Validate all questions are answered
        const unanswered = questions.filter((q) => !answers[q.id]);
        if (unanswered.length > 0) {
          throw new Error(`Please answer all questions. ${unanswered.length} remaining.`);
        }

        set({ submitting: true, error: null });

        try {
          const input: SubmitAssessmentInput = {
            responses: questions.map((q) => ({
              questionId: q.id,
              answer: answers[q.id],
            })),
            completionTimeSeconds,
          };

          const assessment = await submitAssessment(input);
          const recommendations = getRecommendations(assessment.riskProfile);

          set({
            currentAssessment: assessment,
            userProfile: assessment,
            recommendations,
            isAssessmentValid: true,
            submitting: false,
          });

          return assessment;
        } catch (error) {
          const message = error instanceof Error ? error.message : 'Error submitting assessment';
          set({ error: message, submitting: false });
          throw error;
        }
      },

      fetchProfile: async (userId?: string) => {
        set({ loadingProfile: true, error: null });

        try {
          let profile: RiskAssessment | null;

          if (userId) {
            profile = await getProfile(userId);
          } else {
            profile = await getCurrentAssessment();
          }

          if (profile) {
            const recommendations = getRecommendations(profile.riskProfile);
            set({
              userProfile: profile,
              currentAssessment: profile,
              recommendations,
              isAssessmentValid: !profile.isExpired,
              loadingProfile: false,
            });
          } else {
            set({
              userProfile: null,
              recommendations: null,
              isAssessmentValid: false,
              loadingProfile: false,
            });
          }
        } catch (error) {
          const message = error instanceof Error ? error.message : 'Error loading profile';
          set({ error: message, loadingProfile: false });
        }
      },

      fetchCurrentAssessment: async () => {
        set({ loading: true, error: null });

        try {
          const assessment = await getCurrentAssessment();

          if (assessment) {
            const recommendations = getRecommendations(assessment.riskProfile);
            set({
              currentAssessment: assessment,
              userProfile: assessment,
              recommendations,
              isAssessmentValid: !assessment.isExpired,
              loading: false,
            });
          } else {
            set({
              currentAssessment: null,
              isAssessmentValid: false,
              loading: false,
            });
          }
        } catch (error) {
          const message = error instanceof Error ? error.message : 'Error loading assessment';
          set({ error: message, loading: false });
        }
      },

      fetchAssessmentHistory: async () => {
        set({ loadingHistory: true, error: null });

        try {
          const history = await getAssessmentHistory();
          set({ assessmentHistory: history, loadingHistory: false });
        } catch (error) {
          const message = error instanceof Error ? error.message : 'Error loading history';
          set({ error: message, loadingHistory: false });
        }
      },

      checkValidity: async () => {
        try {
          const isValid = await checkValidAssessment();
          set({ isAssessmentValid: isValid });
          return isValid;
        } catch (error) {
          console.error('Error checking assessment validity:', error);
          return false;
        }
      },

      // ========================================================================
      // Questionnaire Actions
      // ========================================================================

      setAnswer: (questionId: string, answer: string) => {
        set((state) => ({
          answers: {
            ...state.answers,
            [questionId]: answer,
          },
        }));
      },

      nextQuestion: () => {
        const { currentQuestionIndex, questions } = get();
        if (currentQuestionIndex < questions.length - 1) {
          set({ currentQuestionIndex: currentQuestionIndex + 1 });
        }
      },

      previousQuestion: () => {
        const { currentQuestionIndex } = get();
        if (currentQuestionIndex > 0) {
          set({ currentQuestionIndex: currentQuestionIndex - 1 });
        }
      },

      goToQuestion: (index: number) => {
        const { questions } = get();
        if (index >= 0 && index < questions.length) {
          set({ currentQuestionIndex: index });
        }
      },

      resetQuestionnaire: () => {
        set({
          currentQuestionIndex: 0,
          answers: {},
        });
      },

      // ========================================================================
      // Utility Actions
      // ========================================================================

      clearError: () => {
        set({ error: null });
      },

      reset: () => {
        set(initialState);
      },
    }),
    {
      name: 'risk-store',
    }
  )
);

// ============================================================================
// Selectors
// ============================================================================

export const useRiskQuestions = () => useRiskStore((state) => state.questions);
export const useCurrentAssessment = () => useRiskStore((state) => state.currentAssessment);
export const useUserProfile = () => useRiskStore((state) => state.userProfile);
export const useRiskRecommendations = () => useRiskStore((state) => state.recommendations);
export const useAssessmentHistory = () => useRiskStore((state) => state.assessmentHistory);
export const useIsAssessmentValid = () => useRiskStore((state) => state.isAssessmentValid);
export const useCurrentQuestionIndex = () => useRiskStore((state) => state.currentQuestionIndex);
export const useRiskAnswers = () => useRiskStore((state) => state.answers);
export const useRiskLoading = () => useRiskStore((state) => state.loading);
export const useRiskSubmitting = () => useRiskStore((state) => state.submitting);
export const useRiskError = () => useRiskStore((state) => state.error);

// Computed selector for progress
export const useQuestionnaireProgress = () =>
  useRiskStore((state) => {
    const total = state.questions.length;
    const answered = Object.keys(state.answers).length;
    return {
      total,
      answered,
      percentage: total > 0 ? Math.round((answered / total) * 100) : 0,
      isComplete: answered === total && total > 0,
    };
  });

// Computed selector for current question
export const useCurrentQuestion = () =>
  useRiskStore((state) => {
    const { questions, currentQuestionIndex, answers } = state;
    if (questions.length === 0) return null;
    const question = questions[currentQuestionIndex];
    return {
      ...question,
      currentAnswer: answers[question.id] || null,
      isFirst: currentQuestionIndex === 0,
      isLast: currentQuestionIndex === questions.length - 1,
    };
  });

export default useRiskStore;
