// src/client/entities/employee.ts
// Employee entity - types and Pinia store for employee management

import { defineStore } from 'pinia';
import { ref, computed } from 'vue';
import {
  employeeRepository,
  type EmployeeResponse,
  type CreateEmployeeRequest,
  type UpdateEmployeeRequest,
  type FireEmployeeRequest,
  type RehireEmployeeRequest,
} from '../shared/api/repositories';
// Re-export shared contracts for convenience
export type {
  Employee as EmployeeContract,
  EmployeeInput,
  EmployeeUpdate,
  RehireEmployeeInput as RehireEmployeeInputContract,
  MaidPeriod,
} from '@shared/contracts/personnel';
export { USER_ROLES } from '@shared/constants/roles';

// Re-export types from EmployeeRepository for convenience
export type CreateEmployeeInput = CreateEmployeeRequest;
export type UpdateEmployeeInput = UpdateEmployeeRequest;
export type FireEmployeeInput = FireEmployeeRequest;
export type RehireEmployeeInput = RehireEmployeeRequest;

// Use Employee from repository as main type
export type Employee = EmployeeResponse;

export const useEmployeeStore = defineStore('employee', () => {
  // State
  const employees = ref<Employee[]>([]);
  const loading = ref(false);
  const error = ref<string | null>(null);
  const activeTab = ref<'active' | 'fired'>('active');

  // Computed
  const activeEmployees = computed(() => {
    if (activeTab.value === 'active') {
      return employees.value.filter(e => !e.isFired);
    } else {
      return employees.value.filter(e => e.isFired);
    }
  });

  const employeesByStatus = computed(() => {
    if (activeTab.value === 'active') {
      return employees.value.filter(e => !e.isFired);
    } else {
      return employees.value.filter(e => e.isFired);
    }
  });

  // Actions
  async function fetchAll() {
    loading.value = true;
    error.value = null;
    try {
      const data = await employeeRepository.getAll();
      employees.value = data;
      return data;
    } catch (err: any) {
      error.value = err.message || 'Не удалось загрузить сотрудников';
      throw err;
    } finally {
      loading.value = false;
    }
  }

  async function fetchByStatus(status: 'active' | 'fired') {
    loading.value = true;
    error.value = null;
    try {
      const data = await employeeRepository.getByStatus(status);
      employees.value = data;
      return data;
    } catch (err: any) {
      error.value = err.message || 'Не удалось загрузить сотрудников';
      throw err;
    } finally {
      loading.value = false;
    }
  }

  async function fetchById(id: string) {
    loading.value = true;
    error.value = null;
    try {
      const data = await employeeRepository.getById(id);
      // Update or add to list
      const index = employees.value.findIndex((e: Employee) => e.id === id);
      if (index >= 0) {
        employees.value[index] = data;
      } else {
        employees.value.push(data);
      }
      return data;
    } catch (err: any) {
      error.value = err.message || 'Не удалось загрузить сотрудника';
      throw err;
    } finally {
      loading.value = false;
    }
  }

  async function create(input: CreateEmployeeInput) {
    loading.value = true;
    error.value = null;
    try {
      const data = await employeeRepository.create(input);
      employees.value.push(data);
      return data;
    } catch (err: any) {
      error.value = err.message || 'Не удалось создать сотрудника';
      throw err;
    } finally {
      loading.value = false;
    }
  }

  async function update(id: string, input: UpdateEmployeeInput) {
    loading.value = true;
    error.value = null;
    try {
      const data = await employeeRepository.update(id, input);
      // Smart merge: update only fields present in input
      const index = employees.value.findIndex((e: Employee) => e.id === id);
      if (index >= 0) {
        employees.value[index] = data;
      }
      return data;
    } catch (err: any) {
      error.value = err.message || 'Не удалось обновить сотрудника';
      throw err;
    } finally {
      loading.value = false;
    }
  }

  async function fire(id: string, input: FireEmployeeInput) {
    loading.value = true;
    error.value = null;
    try {
      const data = await employeeRepository.fire(id, input);
      const index = employees.value.findIndex((e: Employee) => e.id === id);
      if (index >= 0) {
        employees.value[index] = { ...employees.value[index], isFired: true, firedReason: input.firedReason };
      }
      return data;
    } catch (err: any) {
      error.value = err.message || 'Не удалось уволить сотрудника';
      throw err;
    } finally {
      loading.value = false;
    }
  }

  async function rehire(id: string, input: RehireEmployeeInput) {
    loading.value = true;
    error.value = null;
    try {
      const data = await employeeRepository.rehire(id, input);
      const index = employees.value.findIndex((e: Employee) => e.id === id);
      if (index >= 0) {
        employees.value[index] = { ...employees.value[index], isFired: false };
      }
      return data;
    } catch (err: any) {
      error.value = err.message || 'Не удалось восстановить сотрудника';
      throw err;
    } finally {
      loading.value = false;
    }
  }

  function clearError() {
    error.value = null;
  }

  async function switchTab(tab: 'active' | 'fired') {
    activeTab.value = tab;
    return fetchByStatus(tab);
  }

  return {
    // State
    employees,
    loading,
    error,
    activeTab,

    // Computed
    activeEmployees,
    employeesByStatus,

    // Actions
    fetchAll,
    fetchByStatus,
    fetchById,
    create,
    update,
    fire,
    rehire,
    clearError,
    switchTab,
  };
});


// Legacy interfaces for backward compatibility (deprecated - use types from EmployeeRepository)
/** @deprecated Use EmployeeResponse from EmployeeRepository instead */
export interface EmployeeListResponse {
  success: boolean;
  data: Employee[];
}

/** @deprecated Use EmployeeResponse from EmployeeRepository instead */
export interface EmployeeResponseWrapper {
  success: boolean;
  data: Employee;
}
