// src/main/ipc/config-handlers.ts import { ipcMain, BrowserWindow } from 'electron' import { IPC_CHANNELS } from '@d3ro/core/ipc-channels' import { ipcSuccess, ipcError, ErrorCode } from '@d3ro/core/errors' import { configGet, configSet, configGetAll, configReset } from '../services/ConfigService' import { getAutoLaunchService } from '../services/AutoLaunchService' import { reapplyThemeToAllPopups } from '../windows/WindowManager' /** 설정 변경 시 모든 렌더러에 broadcast */ function broadcastConfigChanged(key: string, value: unknown, previousValue?: unknown): void { for (const win of BrowserWindow.getAllWindows()) { win.webContents.send(IPC_CHANNELS.CONFIG.CHANGED, { key, value, previousValue }) } } import type { ConfigGetParams, ConfigSetParams, ConfigResetParams, SetThemeParams, SetLanguageParams, SetAutoLaunchParams, SetCloseToTrayParams, AppConfig } from '@d3ro/core/types' export function registerConfigHandlers(): void { ipcMain.handle(IPC_CHANNELS.CONFIG.GET, async (_event, params: ConfigGetParams) => { try { return ipcSuccess(configGet(params.key)) } catch (error) { const message = error instanceof Error ? error.message : String(error) return ipcError(ErrorCode.ConfigReadFailed, `Failed to read config key ${params.key}: ${message}`) } }) ipcMain.handle(IPC_CHANNELS.CONFIG.SET, async (_event, params: ConfigSetParams) => { try { const prev = configGet(params.key) configSet(params.key, params.value as AppConfig[typeof params.key]) broadcastConfigChanged(params.key, params.value, prev) return ipcSuccess(undefined) } catch (error) { const message = error instanceof Error ? error.message : String(error) return ipcError(ErrorCode.ConfigWriteFailed, `Failed to write config key ${params.key}: ${message}`) } }) ipcMain.handle(IPC_CHANNELS.CONFIG.GET_ALL, async () => { return ipcSuccess(configGetAll()) }) ipcMain.handle(IPC_CHANNELS.CONFIG.RESET, async (_event, params: ConfigResetParams) => { try { configReset(params.key) return ipcSuccess(undefined) } catch (error) { const message = error instanceof Error ? error.message : String(error) return ipcError(ErrorCode.ConfigResetFailed, `Failed to reset config: ${message}`) } }) ipcMain.handle(IPC_CHANNELS.CONFIG.GET_THEME, async () => { return ipcSuccess(configGet('theme')) }) ipcMain.handle(IPC_CHANNELS.CONFIG.SET_THEME, async (_event, params: SetThemeParams) => { const prev = configGet('theme') configSet('theme', params.theme) broadcastConfigChanged('theme', params.theme, prev) reapplyThemeToAllPopups() return ipcSuccess(undefined) }) ipcMain.handle(IPC_CHANNELS.CONFIG.GET_LANGUAGE, async () => { return ipcSuccess(configGet('language')) }) ipcMain.handle(IPC_CHANNELS.CONFIG.SET_LANGUAGE, async (_event, params: SetLanguageParams) => { configSet('language', params.language) return ipcSuccess(undefined) }) ipcMain.handle(IPC_CHANNELS.CONFIG.GET_AUTO_LAUNCH, async () => { return ipcSuccess(configGet('autoLaunch')) }) ipcMain.handle(IPC_CHANNELS.CONFIG.SET_AUTO_LAUNCH, async (_event, params: SetAutoLaunchParams) => { getAutoLaunchService().setEnabled(params.enabled) return ipcSuccess(undefined) }) ipcMain.handle(IPC_CHANNELS.CONFIG.GET_CLOSE_TO_TRAY, async () => { return ipcSuccess(configGet('closeToTray')) }) ipcMain.handle(IPC_CHANNELS.CONFIG.SET_CLOSE_TO_TRAY, async (_event, params: SetCloseToTrayParams) => { configSet('closeToTray', params.enabled) return ipcSuccess(undefined) }) }