import type { IDiscoveryCandidate, TEntityPlatform } from '../../core/types.js';

export const tradfriDefaultCoapDtlsPort = 5684;

export type TTradfriResourceType = 'gateway' | 'device' | 'group';
export type TTradfriEventType = 'snapshot_updated' | 'command_mapped' | 'command_failed' | 'state_changed' | 'error' | string;

export interface ITradfriConfig {
  host?: string;
  port?: number;
  gatewayId?: string;
  identity?: string;
  securityCode?: string;
  psk?: string;
  key?: string;
  gateway?: ITradfriGateway;
  devices?: ITradfriDevice[];
  groups?: ITradfriGroup[];
  snapshot?: ITradfriSnapshot;
  discoveryRecords?: ITradfriDiscoveryRecord[];
  manualEntries?: ITradfriManualEntry[];
  commandExecutor?: TTradfriCommandExecutor;
}

export interface IHomeAssistantTradfriConfig extends ITradfriConfig {}

export interface ITradfriGateway {
  id?: string;
  name?: string;
  model?: string;
  firmwareVersion?: string;
  firmware_version?: string;
  homekitId?: string;
  homekit_id?: string;
  currentTime?: string | number;
  current_time?: string | number;
  commissioningMode?: number;
  commissioning_mode?: number;
  raw?: Record<string, unknown>;
  [key: string]: unknown;
}

export interface ITradfriDeviceInfo {
  manufacturer?: string;
  modelNumber?: string;
  model_number?: string;
  serial?: string;
  firmwareVersion?: string;
  firmware_version?: string;
  powerSource?: number;
  power_source?: number;
  batteryLevel?: number;
  battery_level?: number;
  raw?: Record<string, unknown>;
  [key: string]: unknown;
}

export interface ITradfriLight {
  id?: string | number;
  index?: number;
  state?: boolean | number;
  on?: boolean;
  dimmer?: number;
  brightness?: number;
  brightnessPercent?: number;
  brightness_percent?: number;
  colorTemp?: number;
  color_temp?: number;
  colorMireds?: number;
  color_mireds?: number;
  colorHex?: string;
  color_hex?: string;
  hue?: number;
  saturation?: number;
  colorHue?: number;
  color_hue?: number;
  colorSaturation?: number;
  color_saturation?: number;
  xy?: [number, number];
  raw?: Record<string, unknown>;
  [key: string]: unknown;
}

export interface ITradfriSocket {
  id?: string | number;
  index?: number;
  state?: boolean | number;
  on?: boolean;
  raw?: Record<string, unknown>;
  [key: string]: unknown;
}

export interface ITradfriBlind {
  id?: string | number;
  index?: number;
  position?: number;
  positionPercentage?: number;
  position_percentage?: number;
  currentCoverPosition?: number;
  current_cover_position?: number;
  rawPosition?: number;
  raw_position?: number;
  raw?: Record<string, unknown>;
  [key: string]: unknown;
}

export interface ITradfriSensor {
  id?: string | number;
  index?: number;
  name?: string;
  type?: string;
  deviceClass?: string;
  device_class?: string;
  unit?: string;
  unitOfMeasurement?: string;
  unit_of_measurement?: string;
  value?: string | number | boolean | null;
  state?: string | number | boolean | null;
  binary?: boolean;
  raw?: Record<string, unknown>;
  [key: string]: unknown;
}

export interface ITradfriBinarySensor extends ITradfriSensor {
  binary: true;
}

export interface ITradfriAirPurifier {
  id?: string | number;
  index?: number;
  state?: boolean | number;
  mode?: number;
  fanSpeed?: number;
  fan_speed?: number;
  percentage?: number;
  airQuality?: number;
  air_quality?: number;
  filterLifetimeRemaining?: number;
  filter_lifetime_remaining?: number;
  filterLifetimeTotal?: number;
  filter_lifetime_total?: number;
  controlsLocked?: boolean | number;
  controls_locked?: boolean | number;
  ledsOff?: boolean | number;
  leds_off?: boolean | number;
  raw?: Record<string, unknown>;
  [key: string]: unknown;
}

export interface ITradfriDevice {
  id?: string | number;
  name?: string;
  applicationType?: number;
  application_type?: number;
  reachable?: boolean | number;
  lastSeen?: string | number;
  last_seen?: string | number;
  createdAt?: string | number;
  created_at?: string | number;
  deviceInfo?: ITradfriDeviceInfo;
  device_info?: ITradfriDeviceInfo;
  lightControl?: ITradfriLight[];
  light_control?: ITradfriLight[];
  socketControl?: ITradfriSocket[];
  socket_control?: ITradfriSocket[];
  outletControl?: ITradfriSocket[];
  outlet_control?: ITradfriSocket[];
  blindControl?: ITradfriBlind[];
  blind_control?: ITradfriBlind[];
  coverControl?: ITradfriBlind[];
  cover_control?: ITradfriBlind[];
  sensorControl?: ITradfriSensor[];
  sensor_control?: ITradfriSensor[];
  sensors?: ITradfriSensor[];
  binarySensors?: ITradfriBinarySensor[];
  binary_sensors?: ITradfriBinarySensor[];
  airPurifierControl?: ITradfriAirPurifier[];
  air_purifier_control?: ITradfriAirPurifier[];
  signalRepeaterControl?: unknown[];
  signal_repeater_control?: unknown[];
  raw?: Record<string, unknown>;
  [key: string]: unknown;
}

export interface ITradfriGroup {
  id?: string | number;
  name?: string;
  state?: boolean | number;
  dimmer?: number;
  brightness?: number;
  colorHex?: string;
  color_hex?: string;
  memberIds?: Array<string | number>;
  member_ids?: Array<string | number>;
  groupMembers?: Record<string, unknown>;
  group_members?: Record<string, unknown>;
  moodId?: string | number;
  mood_id?: string | number;
  raw?: Record<string, unknown>;
  [key: string]: unknown;
}

export interface ITradfriSnapshot {
  host?: string;
  port?: number;
  connected?: boolean;
  gateway?: ITradfriGateway;
  devices: ITradfriDevice[];
  groups: ITradfriGroup[];
  states?: ITradfriState[];
  events?: ITradfriEvent[];
  updatedAt?: string | number;
  raw?: Record<string, unknown>;
}

export interface ITradfriState {
  resourceType: TTradfriResourceType;
  resourceId: string;
  featureId: string;
  value: unknown;
  updatedAt?: string | number;
}

export interface ITradfriCommand {
  type: string;
  service: string;
  resourceType: Exclude<TTradfriResourceType, 'gateway'>;
  resourceId: string;
  platform?: TEntityPlatform;
  deviceId?: string;
  entityId?: string;
  uniqueId?: string;
  payload: Record<string, unknown>;
  coap: {
    method: 'put' | 'post' | 'get';
    path: string[];
    payload?: Record<string, unknown>;
  };
  target?: {
    entityId?: string;
    deviceId?: string;
  };
}

export interface ITradfriCommandResult {
  success: boolean;
  error?: string;
  data?: unknown;
}

export type TTradfriCommandExecutor = (
  commandArg: ITradfriCommand
) => Promise<ITradfriCommandResult | unknown> | ITradfriCommandResult | unknown;

export interface ITradfriEvent {
  type: TTradfriEventType;
  timestamp?: number;
  deviceId?: string;
  entityId?: string;
  command?: ITradfriCommand;
  data?: unknown;
}

export interface ITradfriMdnsRecord {
  type?: string;
  name?: string;
  host?: string;
  hostname?: string;
  addresses?: string[];
  port?: number;
  txt?: Record<string, string | undefined>;
  properties?: Record<string, string | undefined>;
}

export interface ITradfriManualEntry {
  host?: string;
  port?: number;
  id?: string;
  gatewayId?: string;
  gateway_id?: string;
  name?: string;
  model?: string;
  manufacturer?: string;
  identity?: string;
  securityCode?: string;
  security_code?: string;
  psk?: string;
  key?: string;
  metadata?: Record<string, unknown>;
}

export interface ITradfriDiscoveryRecord extends ITradfriManualEntry {
  source?: IDiscoveryCandidate['source'] | string;
  type?: string;
  txt?: Record<string, string | undefined>;
}
