import { sendNotifications } from './notification-service.js'; import type { AppConfigSnapshot } from './app-config-service.js'; import { getPlanItemById } from './plan-service.js'; function buildPlanNotificationTargetUrl(planId: number, workId: string | null | undefined) { const targetUrl = new URL('https://sm-home.cloud/'); targetUrl.searchParams.set('topMenu', 'plans'); targetUrl.searchParams.set('planId', String(planId)); if (workId?.trim()) { targetUrl.searchParams.set('workId', workId.trim()); } return targetUrl.toString(); } export function shouldNotifyPlanEventType( automation: AppConfigSnapshot['automation'] | undefined, eventType: string, ) { if (eventType === 'work-started') { return automation?.notifyOnAutomationStart ?? true; } if (eventType === 'work-progress') { return automation?.notifyOnAutomationProgress ?? true; } if ( eventType === 'work-completed' || eventType === 'work-noop-complete' || eventType === 'development-completed' || eventType === 'plan-completed' ) { return automation?.notifyOnAutomationCompletion ?? true; } if (eventType === 'release-merged') { return automation?.notifyOnAutomationRelease ?? true; } if (eventType === 'main-merged') { return automation?.notifyOnAutomationMain ?? true; } if ( eventType === 'branch-failed' || eventType === 'work-failed' || eventType === 'release-failed' || eventType === 'main-failed' ) { return automation?.notifyOnAutomationFailure ?? true; } if (eventType === 'plan-restarted') { return automation?.notifyOnAutomationRestart ?? true; } if (eventType === 'issue-resolved') { return automation?.notifyOnAutomationIssueResolved ?? true; } return true; } export async function shouldSendPlanNotification(eventType: string) { void eventType; return true; } export function buildPlanNotificationData(planId: number, workId: string | null | undefined, eventType: string) { return { category: 'automation', planId: String(planId), workId: String(workId ?? ''), eventType, notificationScope: 'automation', targetUrl: buildPlanNotificationTargetUrl(planId, workId), notificationKey: `plan:${planId}`, }; } export async function notifyPlanEvent( planId: number, title: string, body: string, eventType: string, ) { if (!(await shouldSendPlanNotification(eventType))) { return { ok: true, skipped: true, reason: '앱 설정에서 이 알림 항목이 꺼져 있습니다.', }; } const item = await getPlanItemById(planId); if (!item) { return { ok: false, skipped: true, reason: '작업 항목을 찾을 수 없습니다.', }; } return sendNotifications({ title, body, threadId: `plan-${planId}`, data: buildPlanNotificationData(planId, String(item.workId), eventType), }, { disableWebPush: Boolean(item.suppressWebPush), }); }