import { getPostgresClient } from './postgres-client.js' /** * CSP 위반을 원본 없이 정규화된 차원별로 집계한다. * @param {Array<{ policyVersion: string, documentPath: string, effectiveDirective: string, blockedOrigin: string, userAgentFamily: string }>} reports - CSP 집계 행 * @returns {Promise} */ export const recordCspReports = async (reports) => { const sql = getPostgresClient() if (!sql || reports.length === 0) { return } await sql.begin(async (transaction) => { for (const report of reports) { await transaction` INSERT INTO csp_violation_aggregates ( policy_version, document_path, effective_directive, blocked_origin, user_agent_family, violation_count, first_seen_at, last_seen_at ) VALUES ( ${report.policyVersion}, ${report.documentPath}, ${report.effectiveDirective}, ${report.blockedOrigin}, ${report.userAgentFamily}, 1, now(), now() ) ON CONFLICT ( policy_version, document_path, effective_directive, blocked_origin, user_agent_family ) DO UPDATE SET violation_count = csp_violation_aggregates.violation_count + 1, last_seen_at = now() ` } }) }