export const elgatoDomain = 'elgato';
export const elgatoDisplayName = 'Elgato Light';
export const elgatoManufacturer = 'Elgato';
export const elgatoDefaultPort = 9123;
export const elgatoDefaultTimeoutMs = 8000;
export const elgatoZeroconfType = '_elg._tcp.local.';

export type TElgatoSnapshotSource = 'http' | 'client' | 'manual' | 'snapshot' | 'runtime';
export type TElgatoColorMode = 'color_temp' | 'hs';
export type TElgatoCommandAction = 'refresh' | 'set_light' | 'identify' | 'restart' | 'battery_bypass' | 'energy_saving';

export interface IElgatoWifiInfo {
  frequencyMHz?: number;
  rssi?: number;
  ssid?: string;
}

export interface IElgatoInfo {
  features?: string[];
  firmwareBuildNumber?: number;
  firmwareVersion?: string;
  hardwareBoardType?: number;
  productName?: string;
  serialNumber?: string;
  displayName?: string;
  macAddress?: string;
  'wifi-info'?: IElgatoWifiInfo;
  [key: string]: unknown;
}

export interface IElgatoEnergySavingAdjustBrightnessSettings {
  brightness?: number;
  enable?: number | boolean;
}

export interface IElgatoEnergySavingSettings {
  adjustBrightness?: IElgatoEnergySavingAdjustBrightnessSettings;
  disableWifi?: number | boolean;
  enable?: number | boolean;
  minimumBatteryLevel?: number;
}

export interface IElgatoBatterySettings {
  bypass?: number | boolean;
  energySaving?: IElgatoEnergySavingSettings;
}

export interface IElgatoSettings {
  colorChangeDurationMs?: number;
  powerOnBehavior?: number;
  powerOnBrightness?: number;
  switchOffDurationMs?: number;
  switchOnDurationMs?: number;
  battery?: IElgatoBatterySettings | null;
  powerOnHue?: number;
  powerOnSaturation?: number;
  powerOnTemperature?: number;
  [key: string]: unknown;
}

export interface IElgatoState {
  on?: number | boolean;
  brightness?: number;
  hue?: number | null;
  saturation?: number | null;
  temperature?: number | null;
  [key: string]: unknown;
}

export interface IElgatoBatteryInfo {
  powerSource?: number;
  level?: number;
  status?: number;
  currentBatteryVoltage?: number;
  inputChargeVoltage?: number;
  inputChargeCurrent?: number;
  [key: string]: unknown;
}

export interface IElgatoRawData {
  info?: IElgatoInfo;
  settings?: IElgatoSettings;
  state?: IElgatoState;
  battery?: IElgatoBatteryInfo;
  fetchedAt?: string;
}

export interface IElgatoDeviceSnapshotInfo {
  id: string;
  name: string;
  manufacturer: string;
  model?: string;
  serialNumber?: string;
  firmwareVersion?: string;
  firmwareBuildNumber?: number;
  hardwareBoardType?: number;
  macAddress?: string;
  host?: string;
  port?: number;
  baseUrl?: string;
}

export interface IElgatoLightSnapshot {
  on: boolean;
  brightness?: number;
  brightness255?: number;
  colorMode: TElgatoColorMode;
  supportedColorModes: TElgatoColorMode[];
  colorTemperatureMired?: number;
  colorTemperatureKelvin?: number;
  minColorTemperatureKelvin: number;
  maxColorTemperatureKelvin: number;
  hue?: number;
  saturation?: number;
}

export interface IElgatoBatterySnapshot {
  level?: number;
  status?: number;
  powerSource?: number;
  voltage?: number;
  inputChargeVoltage?: number;
  inputChargeCurrent?: number;
  chargePower?: number;
  bypass?: boolean;
  energySavingEnabled?: boolean;
}

export interface IElgatoCapabilities {
  localControl: boolean;
  colorTemperature: boolean;
  color: boolean;
  identify: boolean;
  restart: boolean;
  battery: boolean;
  batterySettings: boolean;
}

export interface IElgatoSnapshot {
  device: IElgatoDeviceSnapshotInfo;
  light: IElgatoLightSnapshot;
  battery?: IElgatoBatterySnapshot;
  capabilities: IElgatoCapabilities;
  rawData?: IElgatoRawData;
  online: boolean;
  updatedAt: string;
  source: TElgatoSnapshotSource;
  error?: string;
}

export interface IElgatoCommandRequest {
  action: TElgatoCommandAction;
  service?: string;
  target?: {
    entityId?: string;
    deviceId?: string;
  };
  data?: Record<string, unknown>;
  on?: boolean;
  brightness?: number;
  brightness255?: number;
  temperature?: number;
  colorTemperatureKelvin?: number;
  hue?: number;
  saturation?: number;
  enabled?: boolean;
}

export interface IElgatoRefreshResult {
  success: boolean;
  snapshot?: IElgatoSnapshot;
  error?: string;
  data?: Record<string, unknown>;
}

export interface IElgatoClientLike {
  getSnapshot?: () => Promise<IElgatoSnapshot | Partial<IElgatoRawData>>;
  getRawData?: () => Promise<Partial<IElgatoRawData>>;
  info?: () => Promise<IElgatoInfo>;
  settings?: () => Promise<IElgatoSettings>;
  state?: () => Promise<IElgatoState>;
  battery?: () => Promise<IElgatoBatteryInfo>;
  light?: (requestArg: Partial<IElgatoCommandRequest>) => Promise<unknown>;
  identify?: () => Promise<unknown>;
  restart?: () => Promise<unknown>;
  batteryBypass?: (onArg: boolean) => Promise<unknown>;
  energySaving?: (onArg: boolean) => Promise<unknown>;
  execute?: (requestArg: IElgatoCommandRequest) => Promise<unknown>;
  destroy?: () => Promise<void>;
}

export interface IElgatoCommandExecutor {
  execute(requestArg: IElgatoCommandRequest): Promise<unknown>;
}

export interface IElgatoConfig {
  host?: string;
  url?: string;
  port?: number;
  timeoutMs?: number;
  name?: string;
  uniqueId?: string;
  manufacturer?: string;
  model?: string;
  serialNumber?: string;
  macAddress?: string;
  snapshot?: IElgatoSnapshot;
  rawData?: Partial<IElgatoRawData>;
  info?: IElgatoInfo;
  settings?: IElgatoSettings;
  state?: IElgatoState;
  battery?: IElgatoBatteryInfo;
  client?: IElgatoClientLike;
  commandExecutor?: IElgatoCommandExecutor;
  online?: boolean;
}

export interface IHomeAssistantElgatoConfig extends IElgatoConfig {}

export interface IElgatoManualEntry extends IElgatoConfig {
  id?: string;
  metadata?: Record<string, unknown>;
}

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

export interface IElgatoDhcpRecord {
  ip?: string;
  address?: string;
  host?: string;
  hostname?: string;
  hostName?: string;
  macaddress?: string;
  macAddress?: string;
  registeredDevices?: boolean;
  registered_devices?: boolean;
  name?: string;
  manufacturer?: string;
  model?: string;
  metadata?: Record<string, unknown>;
}
