/**
 * API 응답 → 정규화된 상태 변환 함수
 *
 * API 응답 (Nested 구조) → Zustand 스토어 (정규화된 구조)
 */

import type {
  InitResponse,
  ItemPageResponse,
  ItemSectionResponse,
  ItemFieldResponse,
  BomItemResponse,
} from '@/types/item-master-api';

import type {
  PageEntity,
  SectionEntity,
  FieldEntity,
  BOMItemEntity,
  EntitiesState,
  IdsState,
  SectionType,
  FieldType,
  ItemType,
} from './types';

// ===== 타입 변환 헬퍼 =====

/**
 * 섹션 타입 변환: API ('fields' | 'bom') → Store ('BASIC' | 'BOM' | 'CUSTOM')
 */
const normalizeSectionType = (apiType: string): SectionType => {
  switch (apiType) {
    case 'bom':
      return 'BOM';
    case 'fields':
    default:
      return 'BASIC';
  }
};

/**
 * 필드 타입 변환 (API와 동일하므로 그대로 사용)
 */
const normalizeFieldType = (apiType: string): FieldType => {
  return apiType as FieldType;
};

// ===== 개별 엔티티 변환 =====

/**
 * API 페이지 응답 → PageEntity
 */
export const normalizePageResponse = (
  page: ItemPageResponse,
  sectionIds: number[] = []
): PageEntity => ({
  id: page.id,
  tenant_id: page.tenant_id,
  page_name: page.page_name,
  item_type: page.item_type as ItemType,
  description: page.description,
  absolute_path: page.absolute_path || '',
  is_active: page.is_active,
  order_no: page.order_no,
  created_by: page.created_by,
  updated_by: page.updated_by,
  created_at: page.created_at,
  updated_at: page.updated_at,
  sectionIds,
});

/**
 * API 섹션 응답 → SectionEntity
 */
export const normalizeSectionResponse = (
  section: ItemSectionResponse,
  fieldIds: number[] = [],
  bomItemIds: number[] = []
): SectionEntity => ({
  id: section.id,
  tenant_id: section.tenant_id,
  group_id: section.group_id,
  page_id: section.page_id,
  title: section.title,
  section_type: normalizeSectionType(section.type),
  description: section.description,
  order_no: section.order_no,
  is_template: section.is_template,
  is_default: section.is_default,
  is_collapsible: true, // 프론트엔드 기본값
  is_default_open: true, // 프론트엔드 기본값
  created_by: section.created_by,
  updated_by: section.updated_by,
  created_at: section.created_at,
  updated_at: section.updated_at,
  fieldIds,
  bomItemIds,
});

/**
 * API 필드 응답 → FieldEntity
 */
export const normalizeFieldResponse = (field: ItemFieldResponse): FieldEntity => ({
  id: field.id,
  tenant_id: field.tenant_id,
  group_id: field.group_id,
  section_id: field.section_id,
  master_field_id: field.master_field_id,
  field_name: field.field_name,
  field_key: field.field_key,
  field_type: normalizeFieldType(field.field_type),
  order_no: field.order_no,
  is_required: field.is_required,
  placeholder: field.placeholder,
  default_value: field.default_value,
  display_condition: field.display_condition,
  validation_rules: field.validation_rules,
  options: field.options,
  properties: field.properties,
  is_locked: field.is_locked,
  locked_by: field.locked_by,
  locked_at: field.locked_at,
  created_by: field.created_by,
  updated_by: field.updated_by,
  created_at: field.created_at,
  updated_at: field.updated_at,
});

/**
 * API BOM 응답 → BOMItemEntity
 */
export const normalizeBomItemResponse = (bom: BomItemResponse): BOMItemEntity => ({
  id: bom.id,
  tenant_id: bom.tenant_id,
  group_id: bom.group_id,
  section_id: bom.section_id,
  item_code: bom.item_code,
  item_name: bom.item_name,
  quantity: bom.quantity,
  unit: bom.unit,
  unit_price: bom.unit_price,
  total_price: bom.total_price,
  spec: bom.spec,
  note: bom.note,
  created_by: bom.created_by,
  updated_by: bom.updated_by,
  created_at: bom.created_at,
  updated_at: bom.updated_at,
});

// ===== Init 응답 정규화 (전체 데이터) =====

export interface NormalizedInitData {
  entities: EntitiesState;
  ids: IdsState;
}

/**
 * Init API 응답 → 정규화된 상태
 *
 * API 응답의 Nested 구조를 평탄화:
 * pages[].sections[].fields[] → entities.pages, entities.sections, entities.fields
 */
export const normalizeInitResponse = (data: InitResponse): NormalizedInitData => {
  const entities: EntitiesState = {
    pages: {},
    sections: {},
    fields: {},
    bomItems: {},
  };

  const ids: IdsState = {
    pages: [],
    independentSections: [],
    independentFields: [],
    independentBomItems: [],
  };

  // 1. 페이지 정규화 (Nested sections 포함)
  data.pages.forEach((page) => {
    const sectionIds: number[] = [];

    // 페이지에 포함된 섹션 처리
    if (page.sections && page.sections.length > 0) {
      page.sections.forEach((section) => {
        sectionIds.push(section.id);

        const fieldIds: number[] = [];
        const bomItemIds: number[] = [];

        // 섹션에 포함된 필드 처리
        if (section.fields && section.fields.length > 0) {
          section.fields.forEach((field) => {
            fieldIds.push(field.id);
            entities.fields[field.id] = normalizeFieldResponse(field);
          });
        }

        // 섹션에 포함된 BOM 처리 (bom_items 또는 bomItems)
        const bomItems = section.bom_items || section.bomItems || [];
        if (bomItems.length > 0) {
          bomItems.forEach((bom) => {
            bomItemIds.push(bom.id);
            entities.bomItems[bom.id] = normalizeBomItemResponse(bom);
          });
        }

        // 섹션 저장
        entities.sections[section.id] = normalizeSectionResponse(section, fieldIds, bomItemIds);
      });
    }

    // 페이지 저장
    entities.pages[page.id] = normalizePageResponse(page, sectionIds);
    ids.pages.push(page.id);
  });

  // 2. 독립 섹션 정규화 (sections 필드가 있을 경우)
  if (data.sections && data.sections.length > 0) {
    data.sections.forEach((section) => {
      // 이미 페이지에서 처리된 섹션은 스킵
      if (entities.sections[section.id]) return;

      const fieldIds: number[] = [];
      const bomItemIds: number[] = [];

      // 필드 처리
      if (section.fields && section.fields.length > 0) {
        section.fields.forEach((field) => {
          fieldIds.push(field.id);
          if (!entities.fields[field.id]) {
            entities.fields[field.id] = normalizeFieldResponse(field);
          }
        });
      }

      // BOM 처리
      const bomItems = section.bom_items || section.bomItems || [];
      if (bomItems.length > 0) {
        bomItems.forEach((bom) => {
          bomItemIds.push(bom.id);
          if (!entities.bomItems[bom.id]) {
            entities.bomItems[bom.id] = normalizeBomItemResponse(bom);
          }
        });
      }

      // 섹션 저장
      entities.sections[section.id] = normalizeSectionResponse(section, fieldIds, bomItemIds);

      // 독립 섹션인 경우 (page_id === null)
      if (section.page_id === null) {
        ids.independentSections.push(section.id);
      }
    });
  }

  // 3. 독립 필드 정규화 (fields 필드가 있을 경우)
  if (data.fields && data.fields.length > 0) {
    data.fields.forEach((field) => {
      // 이미 섹션에서 처리된 필드는 스킵
      if (entities.fields[field.id]) return;

      entities.fields[field.id] = normalizeFieldResponse(field);

      // 독립 필드인 경우 (section_id === null)
      if (field.section_id === null) {
        ids.independentFields.push(field.id);
      }
    });
  }

  return { entities, ids };
};

// ===== 역변환 (상태 → API 요청) =====

/**
 * PageEntity → API 요청 형식
 */
export const denormalizePageForRequest = (
  page: Partial<PageEntity>
): Record<string, unknown> => ({
  page_name: page.page_name,
  item_type: page.item_type,
  description: page.description,
  absolute_path: page.absolute_path,
  is_active: page.is_active,
  order_no: page.order_no,
});

/**
 * SectionEntity → API 요청 형식
 */
export const denormalizeSectionForRequest = (
  section: Partial<SectionEntity>
): Record<string, unknown> => {
  // section_type → type 변환
  const type = section.section_type === 'BOM' ? 'bom' : 'fields';

  return {
    title: section.title,
    type,
    description: section.description,
    order_no: section.order_no,
    is_template: section.is_template,
    is_default: section.is_default,
  };
};

/**
 * FieldEntity → API 요청 형식
 */
export const denormalizeFieldForRequest = (
  field: Partial<FieldEntity>
): Record<string, unknown> => ({
  field_name: field.field_name,
  field_key: field.field_key,
  field_type: field.field_type,
  order_no: field.order_no,
  is_required: field.is_required,
  placeholder: field.placeholder,
  default_value: field.default_value,
  display_condition: field.display_condition,
  validation_rules: field.validation_rules,
  options: field.options,
  properties: field.properties,
});

/**
 * BOMItemEntity → API 요청 형식
 */
export const denormalizeBomItemForRequest = (
  bom: Partial<BOMItemEntity>
): Record<string, unknown> => ({
  item_code: bom.item_code,
  item_name: bom.item_name,
  quantity: bom.quantity,
  unit: bom.unit,
  unit_price: bom.unit_price,
  spec: bom.spec,
  note: bom.note,
});