@composy/log-viewer-core 0.0.1 → 0.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +52 -0
- package/README.md +175 -37
- package/dist/index.js +614 -299
- package/dist/index.js.map +1 -1
- package/dist/index.min.js +548 -1
- package/dist/index.min.js.map +1 -0
- package/es/.dts-output-manifest.json +1 -0
- package/es/.dts.tsbuildinfo +1 -0
- package/es/core/EventEmitter.d.ts +0 -1
- package/es/core/EventEmitter.js +13 -9
- package/es/core/EventEmitter.js.map +1 -1
- package/es/core/LogViewer.d.ts +14 -11
- package/es/core/LogViewer.js +243 -64
- package/es/core/LogViewer.js.map +1 -1
- package/es/filters/FilterEngine.d.ts +0 -1
- package/es/filters/FilterEngine.js +31 -26
- package/es/filters/FilterEngine.js.map +1 -1
- package/es/index.d.ts +7 -7
- package/es/index.js +3 -3
- package/es/index.js.map +1 -1
- package/es/renderers/DiffRenderer.d.ts +0 -1
- package/es/renderers/DiffRenderer.js +13 -3
- package/es/renderers/DiffRenderer.js.map +1 -1
- package/es/renderers/TimelineRenderer.d.ts +7 -3
- package/es/renderers/TimelineRenderer.js +56 -22
- package/es/renderers/TimelineRenderer.js.map +1 -1
- package/es/styles/index.d.ts +1 -5
- package/es/styles/index.js +167 -131
- package/es/styles/index.js.map +1 -1
- package/es/types/index.d.ts +4 -1
- package/es/types/index.js +1 -1
- package/es/types/index.js.map +1 -1
- package/es/utils/index.d.ts +1 -2
- package/es/utils/index.js +54 -6
- package/es/utils/index.js.map +1 -1
- package/esm/core/EventEmitter.js +13 -9
- package/esm/core/EventEmitter.js.map +1 -1
- package/esm/core/LogViewer.js +243 -64
- package/esm/core/LogViewer.js.map +1 -1
- package/esm/filters/FilterEngine.js +31 -26
- package/esm/filters/FilterEngine.js.map +1 -1
- package/esm/index.js +2 -2
- package/esm/index.js.map +1 -1
- package/esm/renderers/DiffRenderer.js +13 -3
- package/esm/renderers/DiffRenderer.js.map +1 -1
- package/esm/renderers/TimelineRenderer.js +56 -22
- package/esm/renderers/TimelineRenderer.js.map +1 -1
- package/esm/styles/index.js +167 -131
- package/esm/styles/index.js.map +1 -1
- package/esm/types/index.js +1 -1
- package/esm/types/index.js.map +1 -1
- package/esm/utils/index.js +54 -6
- package/esm/utils/index.js.map +1 -1
- package/lib/core/EventEmitter.cjs +13 -9
- package/lib/core/EventEmitter.cjs.map +1 -1
- package/{esm/core/EventEmitter.d.ts → lib/core/EventEmitter.d.cts} +0 -1
- package/lib/core/LogViewer.cjs +247 -68
- package/lib/core/LogViewer.cjs.map +1 -1
- package/{esm/core/LogViewer.d.ts → lib/core/LogViewer.d.cts} +14 -11
- package/lib/filters/FilterEngine.cjs +31 -26
- package/lib/filters/FilterEngine.cjs.map +1 -1
- package/lib/filters/{FilterEngine.d.ts → FilterEngine.d.cts} +0 -1
- package/lib/index.cjs +3 -3
- package/lib/index.cjs.map +1 -1
- package/{esm/index.d.ts → lib/index.d.cts} +7 -7
- package/lib/renderers/DiffRenderer.cjs +13 -3
- package/lib/renderers/DiffRenderer.cjs.map +1 -1
- package/lib/renderers/{DiffRenderer.d.ts → DiffRenderer.d.cts} +0 -1
- package/lib/renderers/TimelineRenderer.cjs +55 -21
- package/lib/renderers/TimelineRenderer.cjs.map +1 -1
- package/lib/renderers/{TimelineRenderer.d.ts → TimelineRenderer.d.cts} +7 -3
- package/lib/styles/index.cjs +167 -131
- package/lib/styles/index.cjs.map +1 -1
- package/{esm/styles/index.d.ts → lib/styles/index.d.cts} +1 -5
- package/lib/types/index.cjs +1 -1
- package/lib/types/index.cjs.map +1 -1
- package/{esm/types/index.d.ts → lib/types/index.d.cts} +4 -1
- package/lib/utils/index.cjs +54 -6
- package/lib/utils/index.cjs.map +1 -1
- package/{esm/utils/index.d.ts → lib/utils/index.d.cts} +1 -2
- package/package.json +15 -9
- package/es/core/EventEmitter.d.ts.map +0 -1
- package/es/core/LogViewer.d.ts.map +0 -1
- package/es/filters/FilterEngine.d.ts.map +0 -1
- package/es/index.d.ts.map +0 -1
- package/es/renderers/DiffRenderer.d.ts.map +0 -1
- package/es/renderers/TimelineRenderer.d.ts.map +0 -1
- package/es/styles/index.d.ts.map +0 -1
- package/es/types/index.d.ts.map +0 -1
- package/es/utils/index.d.ts.map +0 -1
- package/esm/core/EventEmitter.d.ts.map +0 -1
- package/esm/core/LogViewer.d.ts.map +0 -1
- package/esm/filters/FilterEngine.d.ts +0 -26
- package/esm/filters/FilterEngine.d.ts.map +0 -1
- package/esm/index.d.ts.map +0 -1
- package/esm/renderers/DiffRenderer.d.ts +0 -18
- package/esm/renderers/DiffRenderer.d.ts.map +0 -1
- package/esm/renderers/TimelineRenderer.d.ts +0 -22
- package/esm/renderers/TimelineRenderer.d.ts.map +0 -1
- package/esm/styles/index.d.ts.map +0 -1
- package/esm/types/index.d.ts.map +0 -1
- package/esm/utils/index.d.ts.map +0 -1
- package/lib/core/EventEmitter.d.ts +0 -11
- package/lib/core/LogViewer.d.ts +0 -46
- package/lib/index.d.ts +0 -26
- package/lib/styles/index.d.ts +0 -9
- package/lib/types/index.d.ts +0 -113
- package/lib/utils/index.d.ts +0 -18
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.min.js","names":["result"],"sources":["../src/types/index.ts","../src/core/EventEmitter.ts","../src/filters/FilterEngine.ts","../src/utils/index.ts","../src/renderers/DiffRenderer.ts","../src/renderers/TimelineRenderer.ts","../src/styles/index.ts","../src/core/LogViewer.ts","../src/index.ts"],"sourcesContent":["/**\r\n * @composy/log-viewer-core 类型定义\r\n */\r\n\r\n/** 操作类型 */\r\nexport type ActionType =\r\n | 'create'\r\n | 'update'\r\n | 'delete'\r\n | 'query'\r\n | 'login'\r\n | 'logout'\r\n | 'export'\r\n | 'import'\r\n | 'approve'\r\n | 'reject'\r\n | 'other'\r\n\r\n/** 主题模式 */\r\nexport type ThemeMode = 'light' | 'dark'\r\n\r\n/** 异常标记类型 */\r\nexport type AnomalyType = 'off-hours' | 'sensitive' | 'high-frequency' | 'none'\r\n\r\n/** 字段变更条目 */\r\nexport interface DiffEntry {\r\n field: string\r\n label?: string\r\n oldValue: unknown\r\n newValue: unknown\r\n}\r\n\r\n/** 日志条目 */\r\nexport interface LogEntry {\r\n id: string\r\n timestamp: string | number | Date\r\n user: string\r\n userId?: string\r\n action: ActionType\r\n module: string\r\n detail?: string\r\n ip?: string\r\n changes?: DiffEntry[]\r\n metadata?: Record<string, unknown>\r\n anomaly?: AnomalyType\r\n}\r\n\r\n/** 筛选配置 */\r\nexport interface FilterConfig {\r\n user?: string\r\n action?: ActionType | ActionType[]\r\n module?: string\r\n ip?: string\r\n timeRange?: [Date | string | number, Date | string | number]\r\n keyword?: string\r\n}\r\n\r\n/** 分页配置 */\r\nexport interface PaginationConfig {\r\n page: number\r\n pageSize: number\r\n total?: number\r\n}\r\n\r\n/** LogViewer 配置 */\r\nexport interface LogViewerConfig {\n container: string | HTMLElement\n data?: LogEntry[]\n dataSource?: string | (() => Promise<LogEntry[]>)\n columns?: string[]\r\n filter?: FilterConfig\r\n pagination?: Partial<PaginationConfig>\r\n theme?: ThemeMode\r\n locale?: 'zh-CN' | 'en-US'\r\n showFilter?: boolean\r\n showDiff?: boolean\r\n showAnomalyBadge?: boolean\r\n pageSize?: number\r\n onEntryClick?: (entry: LogEntry) => void\n onFilterChange?: (filter: FilterConfig) => void\n onThemeChange?: (theme: ThemeMode) => void\n onError?: (error: unknown) => void\n}\n\r\n/** LogViewer 实例接口 */\r\nexport interface LogViewerInstance {\r\n /** 获取当前数据 */\r\n getData(): LogEntry[]\r\n /** 设置数据 */\r\n setData(entries: LogEntry[]): void\r\n /** 追加数据 */\r\n appendData(entries: LogEntry[]): void\r\n /** 获取当前筛选条件 */\r\n getFilter(): FilterConfig\r\n /** 设置筛选条件 */\r\n setFilter(filter: FilterConfig): void\r\n /** 重置筛选 */\r\n resetFilter(): void\r\n /** 获取当前主题 */\r\n getTheme(): ThemeMode\r\n /** 设置主题 */\r\n setTheme(theme: ThemeMode): void\r\n /** 展开指定条目详情 */\r\n expandEntry(id: string): void\r\n /** 折叠指定条目详情 */\r\n collapseEntry(id: string): void\r\n /** 折叠所有详情 */\r\n collapseAll(): void\r\n /** 跳转分页 */\r\n goToPage(page: number): void\r\n /** 获取分页信息 */\r\n getPagination(): PaginationConfig\r\n /** 注册事件监听 */\r\n on(event: string, callback: (...args: unknown[]) => void): () => void\r\n /** 刷新渲染 */\n refresh(): void\n /** 从 dataSource 加载数据 */\n loadData(): Promise<void>\n /** 销毁实例 */\n destroy(): void\n}\n\r\n/** 事件映射 */\r\nexport interface LogViewerEvents {\r\n 'filter:change': (filter: FilterConfig) => void\r\n 'entry:click': (entry: LogEntry) => void\r\n 'entry:expand': (entry: LogEntry) => void\r\n 'entry:collapse': (entry: LogEntry) => void\r\n 'theme:change': (theme: ThemeMode) => void\r\n 'page:change': (page: number) => void\n 'data:change': (entries: LogEntry[]) => void\n error: (error: unknown) => void\n}\n\r\n/** 操作类型标签映射 */\r\nexport const ACTION_LABELS: Record<ActionType, string> = {\r\n create: '新增',\r\n update: '修改',\r\n delete: '删除',\r\n query: '查询',\r\n login: '登录',\r\n logout: '登出',\r\n export: '导出',\r\n import: '导入',\r\n approve: '审批',\r\n reject: '驳回',\r\n other: '其他',\r\n}\r\n\r\n/** 操作类型颜色映射 */\r\nexport const ACTION_COLORS: Record<ActionType, string> = {\r\n create: '#52c41a',\r\n update: '#1890ff',\r\n delete: '#ff4d4f',\r\n query: '#8c8c8c',\r\n login: '#722ed1',\r\n logout: '#eb2f96',\r\n export: '#fa8c16',\r\n import: '#13c2c2',\r\n approve: '#52c41a',\r\n reject: '#ff4d4f',\r\n other: '#d9d9d9',\r\n}\r\n","/**\r\n * 简单的事件发射器\r\n */\r\nexport class EventEmitter {\r\n private listeners = new Map<string, Set<(...args: unknown[]) => void>>()\r\n\r\n on(event: string, callback: (...args: unknown[]) => void): () => void {\r\n if (!event || typeof callback !== 'function') {\r\n return () => undefined\r\n }\r\n if (!this.listeners.has(event)) {\r\n this.listeners.set(event, new Set())\r\n }\r\n const listeners = this.listeners.get(event)!\r\n listeners.add(callback)\r\n return () => this.off(event, callback)\r\n }\r\n\r\n off(event: string, callback: (...args: unknown[]) => void): void {\r\n const listeners = this.listeners.get(event)\r\n if (!listeners) return\r\n listeners.delete(callback)\r\n if (listeners.size === 0) this.listeners.delete(event)\r\n }\r\n\r\n emit(event: string, ...args: unknown[]): void {\r\n const listeners = this.listeners.get(event)\r\n if (!listeners) return\r\n\r\n // Snapshot the set so listeners can unsubscribe or subscribe while the\r\n // current event is being delivered without changing this dispatch cycle.\r\n for (const cb of [...listeners]) {\r\n try {\r\n cb(...args)\r\n } catch (e) {\r\n console.error(`[LogViewer] Event handler error (${event}):`, e)\r\n }\r\n }\r\n }\r\n\r\n removeAllListeners(event?: string): void {\r\n if (event) {\r\n this.listeners.delete(event)\r\n } else {\r\n this.listeners.clear()\r\n }\r\n }\r\n}\r\n","/**\r\n * 筛选引擎 - 支持按操作人/操作类型/时间范围/模块/IP/关键词筛选\r\n */\r\n\r\nimport type { LogEntry, FilterConfig } from '../types'\r\n\r\n/**\r\n * FilterEngine - Filter Engine class\r\n */\r\nexport class FilterEngine {\r\n /**\r\n * 对日志条目进行多维筛选\r\n */\r\n filter(entries: LogEntry[], config: FilterConfig): LogEntry[] {\r\n let result = Array.isArray(entries) ? entries.slice() : []\r\n const normalizedConfig = config || {}\r\n\r\n // 按操作人筛选\r\n if (normalizedConfig.user?.trim()) {\r\n const keyword = normalizedConfig.user.trim().toLowerCase()\r\n result = result.filter(\r\n e =>\r\n e.user?.toLowerCase().includes(keyword) ||\r\n e.userId?.toLowerCase().includes(keyword)\r\n )\r\n }\r\n\r\n // 按操作类型筛选\r\n if (normalizedConfig.action) {\r\n const actions = Array.isArray(normalizedConfig.action)\r\n ? normalizedConfig.action\r\n : [normalizedConfig.action]\r\n if (actions.length > 0)\r\n result = result.filter(e => actions.includes(e.action))\r\n }\r\n\r\n // 按模块筛选\r\n if (normalizedConfig.module?.trim()) {\r\n const mod = normalizedConfig.module.trim().toLowerCase()\r\n result = result.filter(e => e.module?.toLowerCase().includes(mod))\r\n }\r\n\r\n // 按 IP 筛选\r\n if (normalizedConfig.ip?.trim()) {\r\n const ip = normalizedConfig.ip.trim().toLowerCase()\r\n result = result.filter(e => e.ip?.toLowerCase().includes(ip))\r\n }\r\n\r\n // 按时间范围筛选\r\n if (normalizedConfig.timeRange) {\r\n const [start, end] = normalizedConfig.timeRange\r\n const startTime = new Date(start).getTime()\r\n const endTime = new Date(end).getTime()\r\n if (Number.isFinite(startTime) && Number.isFinite(endTime)) {\r\n const lower = Math.min(startTime, endTime)\r\n const upper = Math.max(startTime, endTime)\r\n result = result.filter(e => {\r\n const t = new Date(e.timestamp).getTime()\r\n return Number.isFinite(t) && t >= lower && t <= upper\r\n })\r\n }\r\n }\r\n\r\n // 按关键词全文搜索\r\n if (normalizedConfig.keyword?.trim()) {\r\n const kw = normalizedConfig.keyword.trim().toLowerCase()\r\n result = result.filter(e => {\r\n const texts = [\r\n e.user || '',\r\n e.action,\r\n e.module || '',\r\n e.detail || '',\r\n e.ip || '',\r\n e.id,\r\n ]\r\n return texts.some(t => t.toLowerCase().includes(kw))\r\n })\r\n }\r\n\r\n return result\r\n }\r\n\r\n /**\r\n * 获取所有唯一操作人\r\n */\r\n getUniqueUsers(entries: LogEntry[]): string[] {\r\n return [...new Set(entries.map(e => e.user).filter(Boolean))].sort()\r\n }\r\n\r\n /**\r\n * 获取所有唯一模块\r\n */\r\n getUniqueModules(entries: LogEntry[]): string[] {\r\n return [...new Set(entries.map(e => e.module).filter(Boolean))].sort()\r\n }\r\n\r\n /**\r\n * 获取所有唯一操作类型\r\n */\r\n getUniqueActions(entries: LogEntry[]): string[] {\r\n return [...new Set(entries.map(e => e.action))].sort()\r\n }\r\n}\r\n","/**\r\n * 工具函数\r\n */\r\n\r\nlet _uid = 0\r\n\r\n/** 生成唯一 ID */\r\nexport function uid(prefix = 'lv'): string {\r\n const random =\r\n typeof crypto !== 'undefined' && typeof crypto.randomUUID === 'function'\r\n ? crypto.randomUUID().slice(0, 8)\r\n : Math.random().toString(36).slice(2, 8)\r\n return `${prefix}-${++_uid}-${random}`\r\n}\r\n\r\n/** 格式化日期 */\r\nexport function formatDate(\r\n value: string | number | Date,\r\n fmt = 'YYYY-MM-DD HH:mm:ss'\r\n): string {\r\n const d = value instanceof Date ? value : new Date(value)\r\n if (Number.isNaN(d.getTime())) return String(value)\r\n\r\n const pad = (n: number) => String(n).padStart(2, '0')\r\n const year = String(d.getFullYear())\r\n const month = pad(d.getMonth() + 1)\r\n const day = pad(d.getDate())\r\n const hours = pad(d.getHours())\r\n const minutes = pad(d.getMinutes())\r\n const seconds = pad(d.getSeconds())\r\n\r\n return fmt\r\n .replace('YYYY', year)\r\n .replace('MM', month)\r\n .replace('DD', day)\r\n .replace('HH', hours)\r\n .replace('mm', minutes)\r\n .replace('ss', seconds)\r\n}\r\n\r\n/** 格式化相对时间 */\r\nexport function formatRelativeTime(value: string | number | Date): string {\r\n const d = value instanceof Date ? value : new Date(value)\r\n const now = Date.now()\r\n const diff = now - d.getTime()\r\n\r\n if (!Number.isFinite(diff) || diff < 0) return formatDate(d)\r\n if (diff < 60_000) return '刚刚'\r\n if (diff < 3_600_000) return `${Math.floor(diff / 60_000)} 分钟前`\r\n if (diff < 86_400_000) return `${Math.floor(diff / 3_600_000)} 小时前`\r\n if (diff < 604_800_000) return `${Math.floor(diff / 86_400_000)} 天前`\r\n return formatDate(d)\r\n}\r\n\r\n/** HTML 转义 */\r\nexport function escapeHtml(str: string): string {\r\n const map: Record<string, string> = {\r\n '&': '&',\r\n '<': '<',\r\n '>': '>',\r\n '\"': '"',\r\n \"'\": ''',\r\n }\r\n return str.replace(/[&<>\"']/g, c => map[c] || c)\r\n}\r\n\r\n/** 防抖 */\r\nexport function debounce<T extends (...args: unknown[]) => void>(\r\n fn: T,\r\n delay: number\r\n): T {\r\n let timer: ReturnType<typeof setTimeout> | null = null\r\n const wait = Number.isFinite(delay) && delay > 0 ? delay : 0\r\n return ((...args: unknown[]) => {\r\n if (timer) clearTimeout(timer)\r\n timer = setTimeout(() => {\r\n timer = null\r\n fn(...args)\r\n }, wait)\r\n }) as unknown as T\r\n}\r\n\r\n/** 深拷贝值,同时保留 Date、Map、Set 和循环引用。 */\r\nexport function deepClone<T>(obj: T): T {\r\n if (obj === null || typeof obj !== 'object') return obj\r\n\r\n if (typeof structuredClone === 'function') {\r\n try {\r\n return structuredClone(obj)\r\n } catch {\r\n // structuredClone rejects functions and a few host objects; use the\r\n // compatibility clone below so configuration callbacks stay intact.\r\n }\r\n }\r\n\r\n const seen = new WeakMap<object, unknown>()\r\n\r\n const clone = (value: unknown): unknown => {\r\n if (value === null || typeof value !== 'object') return value\r\n if (seen.has(value)) return seen.get(value)\r\n\r\n if (value instanceof Date) return new Date(value.getTime())\r\n if (value instanceof RegExp) return new RegExp(value.source, value.flags)\r\n\r\n if (value instanceof Map) {\r\n const result = new Map<unknown, unknown>()\r\n seen.set(value, result)\r\n value.forEach((mapValue, key) => result.set(clone(key), clone(mapValue)))\r\n return result\r\n }\r\n\r\n if (value instanceof Set) {\r\n const result = new Set<unknown>()\r\n seen.set(value, result)\r\n value.forEach(setValue => result.add(clone(setValue)))\r\n return result\r\n }\r\n\r\n if (Array.isArray(value)) {\r\n const result: unknown[] = []\r\n seen.set(value, result)\r\n value.forEach(item => result.push(clone(item)))\r\n return result\r\n }\r\n\r\n const result = Object.create(Object.getPrototypeOf(value)) as Record<\r\n string,\r\n unknown\r\n >\r\n seen.set(value, result)\r\n for (const key of Reflect.ownKeys(value)) {\r\n const descriptor = Object.getOwnPropertyDescriptor(value, key)\r\n if (!descriptor || !('value' in descriptor)) continue\r\n Object.defineProperty(result, key, {\r\n ...descriptor,\r\n value: clone(descriptor.value),\r\n })\r\n }\r\n return result\r\n }\r\n\r\n try {\r\n return clone(obj) as T\r\n } catch {\r\n return obj\r\n }\r\n}\r\n\r\n/** 将值格式化为可展示的字符串 */\r\nexport function formatValue(val: unknown): string {\r\n if (val === null || val === undefined) return '-'\r\n if (typeof val === 'object') {\r\n try {\r\n return JSON.stringify(\r\n val,\r\n (_key, value) => {\r\n if (typeof value === 'bigint') return `${value}n`\r\n return value\r\n },\r\n 2\r\n )\r\n } catch {\r\n return String(val)\r\n }\r\n }\r\n return String(val)\r\n}\r\n","/**\r\n * 变更对比渲染器 - 渲染字段变更前后的 Diff 表格\r\n */\r\n\r\nimport type { DiffEntry, LogEntry } from '../types'\r\nimport { formatValue } from '../utils'\r\n\r\n/**\r\n * DiffRenderer - Diff Renderer class\r\n */\r\nexport class DiffRenderer {\r\n /**\r\n * 渲染详情面板(包含 diff 表格和 metadata)\r\n */\r\n renderDetail(entry: LogEntry): HTMLElement {\r\n const container = document.createElement('div')\r\n container.className = 'lv-detail'\r\n\r\n if (entry.changes && entry.changes.length > 0) {\r\n container.appendChild(this.renderDiffTable(entry.changes))\r\n }\r\n\r\n if (entry.metadata && Object.keys(entry.metadata).length > 0) {\r\n const meta = document.createElement('div')\r\n meta.className = 'lv-metadata'\r\n meta.textContent = formatValue(entry.metadata)\r\n container.appendChild(meta)\r\n }\r\n\r\n return container\r\n }\r\n\r\n /**\r\n * 渲染 Diff 表格\r\n */\r\n renderDiffTable(changes: DiffEntry[]): HTMLElement {\r\n const table = document.createElement('table')\r\n table.className = 'lv-diff-table'\r\n\r\n // Header\r\n const thead = document.createElement('thead')\r\n const headerRow = document.createElement('tr')\r\n for (const label of ['字段', '变更前', '变更后']) {\r\n const th = document.createElement('th')\r\n th.textContent = label\r\n headerRow.appendChild(th)\r\n }\r\n thead.appendChild(headerRow)\r\n table.appendChild(thead)\r\n\r\n // Body\r\n const tbody = document.createElement('tbody')\r\n for (const change of changes) {\r\n const tr = document.createElement('tr')\r\n\r\n const tdField = document.createElement('td')\r\n tdField.textContent = change.label || change.field\r\n tr.appendChild(tdField)\r\n\r\n const tdOld = document.createElement('td')\r\n tdOld.className = 'lv-diff-old'\r\n tdOld.textContent = formatValue(change.oldValue)\r\n tr.appendChild(tdOld)\r\n\r\n const tdNew = document.createElement('td')\r\n tdNew.className = 'lv-diff-new'\r\n tdNew.textContent = formatValue(change.newValue)\r\n tr.appendChild(tdNew)\r\n\r\n tbody.appendChild(tr)\r\n }\r\n table.appendChild(tbody)\r\n\r\n return table\r\n }\r\n}\r\n","/**\r\n * 时间线渲染器 - 将日志条目渲染为时间线 DOM\r\n */\r\n\r\nimport type { LogEntry, AnomalyType } from '../types'\r\nimport { ACTION_LABELS } from '../types'\r\nimport { formatDate } from '../utils'\r\n\r\nexport interface TimelineRendererOptions {\r\n showDiff?: boolean\r\n showAnomalyBadge?: boolean\r\n locale?: 'zh-CN' | 'en-US'\r\n}\r\n\r\nconst ANOMALY_LABELS: Record<AnomalyType, string> = {\r\n 'off-hours': '非工作时间',\r\n sensitive: '敏感操作',\r\n 'high-frequency': '高频操作',\r\n none: '',\r\n}\r\n\r\nconst ANOMALY_LABELS_EN: Record<AnomalyType, string> = {\r\n 'off-hours': 'Off hours',\r\n sensitive: 'Sensitive',\r\n 'high-frequency': 'High frequency',\r\n none: '',\r\n}\r\n\r\nconst ACTION_LABELS_EN: Record<string, string> = {\r\n create: 'Create',\r\n update: 'Update',\r\n delete: 'Delete',\r\n query: 'Query',\r\n login: 'Login',\r\n logout: 'Logout',\r\n export: 'Export',\r\n import: 'Import',\r\n approve: 'Approve',\r\n reject: 'Reject',\r\n other: 'Other',\r\n}\r\n\r\n/**\r\n * TimelineRenderer - Timeline Renderer class\r\n */\r\nexport class TimelineRenderer {\r\n /**\r\n * 渲染时间线\r\n */\r\n render(\r\n entries: LogEntry[],\r\n expandedIds: Set<string>,\r\n options: TimelineRendererOptions = {}\r\n ): HTMLElement {\r\n const container = document.createElement('div')\r\n container.className = 'lv-timeline'\r\n\r\n if (entries.length === 0) {\r\n const emptyIcon = document.createElement('div')\r\n emptyIcon.className = 'lv-empty-icon'\r\n emptyIcon.textContent = '--'\r\n const emptyText = document.createElement('div')\r\n emptyText.textContent =\r\n options.locale === 'en-US' ? 'No log entries' : '暂无日志记录'\r\n container.append(emptyIcon, emptyText)\r\n container.className = ''\r\n return container\r\n }\r\n\r\n for (const entry of entries) {\r\n container.appendChild(\r\n this.renderItem(entry, expandedIds.has(entry.id), options)\r\n )\r\n }\r\n\r\n return container\r\n }\r\n\r\n /**\r\n * 渲染单条时间线条目\r\n */\r\n renderItem(\r\n entry: LogEntry,\r\n expanded: boolean,\r\n options: TimelineRendererOptions = {}\r\n ): HTMLElement {\r\n const item = document.createElement('div')\r\n item.className = 'lv-timeline-item'\r\n item.setAttribute('data-id', entry.id)\r\n\r\n const isAnomaly =\r\n options.showAnomalyBadge !== false &&\r\n entry.anomaly &&\r\n entry.anomaly !== 'none'\r\n\r\n // Dot\r\n const dot = document.createElement('div')\r\n dot.className = `lv-timeline-dot${isAnomaly ? ' lv-timeline-dot--anomaly' : ''}`\r\n item.appendChild(dot)\r\n\r\n // Card\r\n const card = document.createElement('div')\r\n card.className = `lv-timeline-card${isAnomaly ? ' lv-timeline-card--anomaly' : ''}`\r\n\r\n // Header\r\n const header = document.createElement('div')\r\n header.className = 'lv-timeline-header'\r\n\r\n const time = document.createElement('span')\r\n time.className = 'lv-timeline-time'\r\n time.textContent = formatDate(entry.timestamp)\r\n header.appendChild(time)\r\n\r\n const user = document.createElement('span')\r\n user.className = 'lv-timeline-user'\r\n user.textContent = entry.user\r\n header.appendChild(user)\r\n\r\n const actionTag = document.createElement('span')\r\n const actionKey = Object.keys(ACTION_LABELS).includes(entry.action)\r\n ? entry.action\r\n : 'other'\r\n actionTag.className = `lv-action-tag lv-action-tag--${actionKey}`\r\n actionTag.textContent =\r\n (options.locale === 'en-US'\r\n ? ACTION_LABELS_EN[entry.action]\r\n : ACTION_LABELS[entry.action]) || entry.action\r\n header.appendChild(actionTag)\r\n\r\n const moduleBadge = document.createElement('span')\r\n moduleBadge.className = 'lv-timeline-module'\r\n moduleBadge.textContent = entry.module\r\n header.appendChild(moduleBadge)\r\n\r\n if (entry.ip) {\r\n const ip = document.createElement('span')\r\n ip.className = 'lv-timeline-ip'\r\n ip.textContent = entry.ip\r\n header.appendChild(ip)\r\n }\r\n\r\n if (options.showAnomalyBadge !== false && isAnomaly) {\r\n const badge = document.createElement('span')\r\n badge.className = 'lv-anomaly-badge'\r\n badge.textContent =\r\n (options.locale === 'en-US'\r\n ? ANOMALY_LABELS_EN[entry.anomaly!]\r\n : ANOMALY_LABELS)[entry.anomaly!] || entry.anomaly\r\n header.appendChild(badge)\r\n }\r\n\r\n card.appendChild(header)\r\n\r\n // Detail text\r\n if (entry.detail) {\r\n const detail = document.createElement('div')\r\n detail.className = 'lv-timeline-detail'\r\n detail.textContent = entry.detail\r\n card.appendChild(detail)\r\n }\r\n\r\n // Expand hint\r\n if (\r\n options.showDiff !== false &&\r\n entry.changes &&\r\n entry.changes.length > 0\r\n ) {\r\n const hint = document.createElement('button')\r\n hint.type = 'button'\r\n hint.className = 'lv-timeline-expand-hint'\r\n hint.setAttribute('aria-expanded', String(expanded))\r\n hint.textContent = expanded\r\n ? '[ 收起变更详情 ]'\r\n : `[ 查看变更详情 (${entry.changes.length} 个字段) ]`\r\n card.appendChild(hint)\r\n }\r\n\r\n item.appendChild(card)\r\n\r\n return item\r\n }\r\n\r\n /**\r\n * 渲染分页\r\n */\r\n renderPagination(page: number, pageSize: number, total: number): HTMLElement {\r\n const container = document.createElement('div')\r\n container.className = 'lv-pagination'\r\n\r\n const safePageSize =\r\n Number.isFinite(pageSize) && pageSize > 0 ? Math.floor(pageSize) : 1\r\n const safeTotal =\r\n Number.isFinite(total) && total > 0 ? Math.floor(total) : 0\r\n const safePage = Number.isFinite(page) && page > 0 ? Math.floor(page) : 1\r\n const totalPages = Math.ceil(safeTotal / safePageSize)\r\n if (totalPages <= 1) return container\r\n\r\n // Prev\r\n const prev = document.createElement('button')\r\n prev.type = 'button'\r\n prev.className = 'lv-pagination-btn'\r\n prev.textContent = '<'\r\n prev.disabled = safePage <= 1\r\n prev.setAttribute('aria-label', 'Previous page')\r\n prev.setAttribute('data-page', String(safePage - 1))\r\n container.appendChild(prev)\r\n\r\n // Page buttons\r\n const maxVisible = 7\r\n let startPage = Math.max(1, safePage - Math.floor(maxVisible / 2))\r\n const endPage = Math.min(totalPages, startPage + maxVisible - 1)\r\n if (endPage - startPage < maxVisible - 1) {\r\n startPage = Math.max(1, endPage - maxVisible + 1)\r\n }\r\n\r\n for (let i = startPage; i <= endPage; i++) {\r\n const btn = document.createElement('button')\r\n btn.type = 'button'\r\n btn.className = `lv-pagination-btn${i === safePage ? ' lv-pagination-btn--active' : ''}`\r\n btn.textContent = String(i)\r\n btn.setAttribute('data-page', String(i))\r\n if (i === safePage) btn.setAttribute('aria-current', 'page')\r\n container.appendChild(btn)\r\n }\r\n\r\n // Next\r\n const next = document.createElement('button')\r\n next.type = 'button'\r\n next.className = 'lv-pagination-btn'\r\n next.textContent = '>'\r\n next.disabled = safePage >= totalPages\r\n next.setAttribute('aria-label', 'Next page')\r\n next.setAttribute('data-page', String(safePage + 1))\r\n container.appendChild(next)\r\n\r\n // Info\r\n const info = document.createElement('span')\r\n info.className = 'lv-pagination-info'\r\n info.textContent = `共 ${safeTotal} 条`\r\n container.appendChild(info)\r\n\r\n return container\r\n }\r\n}\r\n","/**\r\n * 样式注入 - 通过 CSS 变量支持亮色/暗色主题\r\n */\r\n\r\nconst STYLE_ID = 'ldesign-log-viewer-styles'\r\n\r\n/** injectStyles - inject Styles function. */\r\nexport function injectStyles(): void {\r\n if (typeof document === 'undefined') return\r\n if (document.getElementById(STYLE_ID)) return\r\n\r\n const style = document.createElement('style')\r\n style.id = STYLE_ID\r\n style.textContent = CSS_TEXT\r\n document.head.appendChild(style)\r\n}\r\n\r\nconst CSS_TEXT = /* css */ `\r\n/* ===== CSS Variables ===== */\r\n.lv-root {\r\n --lv-bg: var(--ld-white);\r\n --lv-bg-secondary: var(--ld-bg-surface-soft);\r\n --lv-bg-hover: var(--ld-primary-50);\r\n --lv-border: var(--ld-border);\r\n --lv-text: var(--ld-text-primary);\r\n --lv-text-secondary: var(--ld-text-secondary);\r\n --lv-text-muted: var(--ld-text-muted);\r\n --lv-primary: var(--ld-primary-500);\r\n --lv-primary-light: var(--ld-primary-50);\r\n --lv-shadow: color-mix(in srgb, var(--ld-text-primary) 4%, transparent);\r\n --lv-timeline-line: var(--ld-border);\r\n --lv-timeline-dot: var(--ld-primary-500);\r\n --lv-diff-add-bg: var(--ld-success-50);\r\n --lv-diff-add-text: var(--ld-success-700);\r\n --lv-diff-del-bg: var(--ld-danger-50);\r\n --lv-diff-del-text: var(--ld-danger-700);\r\n --lv-anomaly-bg: var(--ld-warning-50);\r\n --lv-anomaly-border: var(--ld-warning-300);\r\n --lv-radius: var(--ld-radius-md);\r\n --lv-font: -apple-system, BlinkMacSystemFont, 'Segoe UI', 'PingFang SC', 'Hiragino Sans GB', 'Microsoft YaHei', sans-serif;\r\n --lv-font-mono: 'Fira Code', 'SF Mono', Consolas, monospace;\r\n}\r\n\r\n.lv-root[data-theme=\"dark\"] {\r\n --lv-bg: var(--ld-bg-surface);\r\n --lv-bg-secondary: var(--ld-bg-surface-soft);\r\n --lv-bg-hover: var(--ld-primary-50);\r\n --lv-border: var(--ld-border-strong);\r\n --lv-text: var(--ld-text-primary);\r\n --lv-text-secondary: var(--ld-text-secondary);\r\n --lv-text-muted: var(--ld-text-muted);\r\n --lv-primary: var(--ld-primary-400);\r\n --lv-primary-light: var(--ld-primary-50);\r\n --lv-shadow: color-mix(in srgb, var(--ld-text-primary) 20%, transparent);\r\n --lv-timeline-line: var(--ld-border-strong);\r\n --lv-timeline-dot: var(--ld-primary-400);\r\n --lv-diff-add-bg: var(--ld-success-50);\r\n --lv-diff-add-text: var(--ld-success-700);\r\n --lv-diff-del-bg: var(--ld-danger-50);\r\n --lv-diff-del-text: var(--ld-danger-700);\r\n --lv-anomaly-bg: var(--ld-warning-50);\r\n --lv-anomaly-border: var(--ld-warning-700);\r\n}\r\n\r\n/* ===== Root ===== */\r\n.lv-root {\r\n font-family: var(--lv-font);\r\n font-size: var(--ld-px-14);\r\n color: var(--lv-text);\r\n background: var(--lv-bg);\r\n line-height: 1.6;\r\n}\r\n\r\n/* ===== Filter Bar ===== */\r\n.lv-filter {\r\n display: flex;\r\n flex-wrap: wrap;\r\n gap: var(--ld-px-10);\r\n padding: var(--ld-px-16);\r\n background: var(--lv-bg);\r\n border: var(--ld-px-1) solid var(--lv-border);\r\n border-radius: var(--lv-radius);\r\n margin-bottom: var(--ld-px-16);\r\n align-items: center;\r\n}\r\n\r\n.lv-filter-item {\r\n display: flex;\r\n align-items: center;\r\n gap: var(--ld-px-6);\r\n font-size: var(--ld-px-13);\r\n}\r\n\r\n.lv-filter-label {\r\n color: var(--lv-text-secondary);\r\n font-size: var(--ld-px-12);\r\n white-space: nowrap;\r\n}\r\n\r\n.lv-filter-input {\r\n padding: var(--ld-px-5) var(--ld-px-10);\r\n border: var(--ld-px-1) solid var(--lv-border);\r\n border-radius: var(--ld-px-6);\r\n font-size: var(--ld-px-13);\r\n background: var(--lv-bg);\r\n color: var(--lv-text);\r\n outline: none;\r\n transition: border-color 0.2s;\r\n min-width: var(--ld-px-120);\r\n}\r\n\r\n.lv-filter-input:focus {\r\n border-color: var(--lv-primary);\r\n}\r\n\r\n.lv-filter-select {\r\n padding: var(--ld-px-5) var(--ld-px-10);\r\n border: var(--ld-px-1) solid var(--lv-border);\r\n border-radius: var(--ld-px-6);\r\n font-size: var(--ld-px-13);\r\n background: var(--lv-bg);\r\n color: var(--lv-text);\r\n outline: none;\r\n cursor: pointer;\r\n}\r\n\r\n.lv-filter-btn {\r\n display: inline-flex;\r\n align-items: center;\r\n gap: var(--ld-px-4);\r\n padding: var(--ld-px-5) var(--ld-px-14);\r\n font-size: var(--ld-px-13);\r\n border: var(--ld-px-1) solid var(--lv-border);\r\n border-radius: var(--ld-px-6);\r\n background: var(--lv-bg);\r\n color: var(--lv-text);\r\n cursor: pointer;\r\n transition: all 0.15s;\r\n}\r\n\r\n.lv-filter-btn:hover {\r\n border-color: var(--lv-primary);\r\n color: var(--lv-primary);\r\n}\r\n\r\n.lv-filter-btn--primary {\r\n background: var(--lv-primary);\r\n border-color: var(--lv-primary);\r\n color: var(--ld-white);\r\n}\r\n\r\n.lv-filter-btn--primary:hover {\r\n opacity: 0.85;\r\n}\r\n\r\n/* ===== Timeline ===== */\r\n.lv-timeline {\r\n position: relative;\r\n padding-left: var(--ld-px-28);\r\n}\r\n\r\n.lv-timeline::before {\r\n content: '';\r\n position: absolute;\r\n left: var(--ld-px-9);\r\n top: 0;\r\n bottom: 0;\r\n width: var(--ld-px-2);\r\n background: var(--lv-timeline-line);\r\n}\r\n\r\n.lv-timeline-item {\r\n position: relative;\r\n padding: 0 0 var(--ld-px-20) 0;\r\n}\r\n\r\n.lv-timeline-dot {\r\n position: absolute;\r\n left: calc(-1 * var(--ld-px-25));\r\n top: var(--ld-px-6);\r\n width: var(--ld-px-12);\r\n height: var(--ld-px-12);\r\n border-radius: 50%;\r\n background: var(--lv-bg);\r\n border: var(--ld-px-2) solid var(--lv-timeline-dot);\r\n z-index: 1;\r\n}\r\n\r\n.lv-timeline-dot--anomaly {\r\n border-color: var(--ld-danger-500);\r\n background: var(--ld-danger-50);\r\n}\r\n\r\n.lv-timeline-card {\r\n background: var(--lv-bg);\r\n border: var(--ld-px-1) solid var(--lv-border);\r\n border-radius: var(--lv-radius);\r\n padding: var(--ld-px-14) var(--ld-px-18);\r\n cursor: pointer;\r\n transition: all 0.2s;\r\n box-shadow: 0 var(--ld-px-1) var(--ld-px-3) var(--lv-shadow);\r\n}\r\n\r\n.lv-timeline-card:hover {\r\n border-color: var(--lv-primary);\r\n box-shadow: 0 var(--ld-px-2) var(--ld-px-8) var(--lv-shadow);\r\n}\r\n\r\n.lv-timeline-card--anomaly {\r\n border-left: var(--ld-px-3) solid var(--lv-anomaly-border);\r\n background: var(--lv-anomaly-bg);\r\n}\r\n\r\n.lv-timeline-header {\r\n display: flex;\r\n align-items: center;\r\n gap: var(--ld-px-10);\r\n flex-wrap: wrap;\r\n margin-bottom: var(--ld-px-4);\r\n}\r\n\r\n.lv-timeline-time {\r\n font-size: var(--ld-px-12);\r\n color: var(--lv-text-muted);\r\n font-family: var(--lv-font-mono);\r\n}\r\n\r\n.lv-timeline-user {\r\n font-weight: 600;\r\n font-size: var(--ld-px-14);\r\n}\r\n\r\n.lv-action-tag {\r\n display: inline-block;\r\n padding: var(--ld-px-1) var(--ld-px-8);\r\n font-size: var(--ld-px-12);\r\n border-radius: var(--ld-px-4);\r\n font-weight: 500;\r\n color: var(--ld-white);\r\n}\r\n\r\n.lv-action-tag--create,\r\n.lv-action-tag--approve {\r\n background: var(--ld-success-500);\r\n}\r\n\r\n.lv-action-tag--update,\r\n.lv-action-tag--login {\r\n background: var(--ld-primary-500);\r\n}\r\n\r\n.lv-action-tag--delete,\r\n.lv-action-tag--reject {\r\n background: var(--ld-danger-500);\r\n}\r\n\r\n.lv-action-tag--query,\r\n.lv-action-tag--other {\r\n background: var(--ld-text-secondary);\r\n}\r\n\r\n.lv-action-tag--logout {\r\n background: var(--ld-primary-700);\r\n}\r\n\r\n.lv-action-tag--export {\r\n background: var(--ld-warning-500);\r\n}\r\n\r\n.lv-action-tag--import {\r\n background: var(--ld-success-500);\r\n}\r\n\r\n.lv-timeline-module {\r\n font-size: var(--ld-px-12);\r\n color: var(--lv-text-secondary);\r\n background: var(--lv-bg-secondary);\r\n padding: var(--ld-px-1) var(--ld-px-8);\r\n border-radius: var(--ld-px-4);\r\n}\r\n\r\n.lv-timeline-ip {\r\n font-size: var(--ld-px-12);\r\n color: var(--lv-text-muted);\r\n font-family: var(--lv-font-mono);\r\n}\r\n\r\n.lv-anomaly-badge {\r\n font-size: var(--ld-px-11);\r\n padding: var(--ld-px-1) var(--ld-px-6);\r\n border-radius: var(--ld-px-3);\r\n background: var(--ld-warning-50);\r\n color: var(--ld-warning-700);\r\n border: var(--ld-px-1) solid var(--ld-warning-300);\r\n}\r\n\r\n.lv-timeline-detail {\r\n font-size: var(--ld-px-13);\r\n color: var(--lv-text-secondary);\r\n margin-top: var(--ld-px-6);\r\n}\r\n\r\n.lv-timeline-expand-hint {\r\n border: 0;\r\n padding: 0;\r\n background: transparent;\r\n font: inherit;\r\n font-size: var(--ld-px-12);\r\n color: var(--lv-primary);\r\n margin-top: var(--ld-px-6);\r\n cursor: pointer;\r\n}\r\n\r\n/* ===== Detail Panel ===== */\r\n.lv-detail {\r\n margin-top: var(--ld-px-12);\r\n padding-top: var(--ld-px-12);\r\n border-top: var(--ld-px-1) dashed var(--lv-border);\r\n animation: lv-slide-down 0.2s ease;\r\n}\r\n\r\n@keyframes lv-slide-down {\r\n from { opacity: 0; transform: translateY(calc(-1 * var(--ld-px-8))); }\r\n to { opacity: 1; transform: translateY(0); }\r\n}\r\n\r\n/* ===== Diff Table ===== */\r\n.lv-diff-table {\r\n width: 100%;\r\n border-collapse: collapse;\r\n font-size: var(--ld-px-13);\r\n border: var(--ld-px-1) solid var(--lv-border);\r\n border-radius: var(--ld-px-6);\r\n overflow: hidden;\r\n}\r\n\r\n.lv-diff-table th {\r\n background: var(--lv-bg-secondary);\r\n padding: var(--ld-px-8) var(--ld-px-12);\r\n text-align: left;\r\n font-weight: 600;\r\n font-size: var(--ld-px-12);\r\n color: var(--lv-text-secondary);\r\n border-bottom: var(--ld-px-1) solid var(--lv-border);\r\n}\r\n\r\n.lv-diff-table td {\r\n padding: var(--ld-px-8) var(--ld-px-12);\r\n border-bottom: var(--ld-px-1) solid var(--lv-border);\r\n vertical-align: top;\r\n}\r\n\r\n.lv-diff-table tr:last-child td {\r\n border-bottom: none;\r\n}\r\n\r\n.lv-diff-old {\r\n background: var(--lv-diff-del-bg);\r\n color: var(--lv-diff-del-text);\r\n text-decoration: line-through;\r\n font-family: var(--lv-font-mono);\r\n font-size: var(--ld-px-12);\r\n}\r\n\r\n.lv-diff-new {\r\n background: var(--lv-diff-add-bg);\r\n color: var(--lv-diff-add-text);\r\n font-family: var(--lv-font-mono);\r\n font-size: var(--ld-px-12);\r\n}\r\n\r\n/* ===== Metadata ===== */\r\n.lv-metadata {\r\n margin-top: var(--ld-px-10);\r\n background: var(--lv-bg-secondary);\r\n border-radius: var(--ld-px-6);\r\n padding: var(--ld-px-10) var(--ld-px-14);\r\n font-size: var(--ld-px-12);\r\n font-family: var(--lv-font-mono);\r\n white-space: pre-wrap;\r\n word-break: break-all;\r\n color: var(--lv-text-secondary);\r\n}\r\n\r\n/* ===== Pagination ===== */\r\n.lv-pagination {\r\n display: flex;\r\n align-items: center;\r\n justify-content: center;\r\n gap: var(--ld-px-6);\r\n padding: var(--ld-px-16) 0;\r\n}\r\n\r\n.lv-pagination-btn {\r\n display: inline-flex;\r\n align-items: center;\r\n justify-content: center;\r\n width: var(--ld-px-32);\r\n height: var(--ld-px-32);\r\n border: var(--ld-px-1) solid var(--lv-border);\r\n border-radius: var(--ld-px-6);\r\n background: var(--lv-bg);\r\n color: var(--lv-text);\r\n font-size: var(--ld-px-13);\r\n cursor: pointer;\r\n transition: all 0.15s;\r\n}\r\n\r\n.lv-pagination-btn:hover {\r\n border-color: var(--lv-primary);\r\n color: var(--lv-primary);\r\n}\r\n\r\n.lv-pagination-btn--active {\r\n background: var(--lv-primary);\r\n border-color: var(--lv-primary);\r\n color: var(--ld-white);\r\n}\r\n\r\n.lv-pagination-btn:disabled {\r\n opacity: 0.4;\r\n cursor: not-allowed;\r\n}\r\n\r\n.lv-pagination-info {\r\n font-size: var(--ld-px-13);\r\n color: var(--lv-text-secondary);\r\n margin: 0 var(--ld-px-8);\r\n}\r\n\r\n/* ===== Empty state ===== */\r\n.lv-empty {\r\n text-align: center;\r\n padding: var(--ld-px-48) var(--ld-px-16);\r\n color: var(--lv-text-muted);\r\n font-size: var(--ld-px-14);\r\n}\r\n\r\n.lv-empty-icon {\r\n font-size: var(--ld-px-48);\r\n margin-bottom: var(--ld-px-12);\r\n opacity: 0.3;\r\n}\r\n`\r\n","/**\n * LogViewer 核心引擎\n */\n\nimport type {\n ActionType,\n FilterConfig,\n LogEntry,\n LogViewerConfig,\n LogViewerInstance,\n PaginationConfig,\n ThemeMode,\n} from '../types'\nimport { ACTION_LABELS } from '../types'\nimport { EventEmitter } from './EventEmitter'\nimport { FilterEngine } from '../filters/FilterEngine'\nimport { DiffRenderer } from '../renderers/DiffRenderer'\nimport { TimelineRenderer } from '../renderers/TimelineRenderer'\nimport { injectStyles } from '../styles'\nimport { deepClone } from '../utils'\n\nconst DEFAULT_PAGE_SIZE = 20\nconst MAX_PAGE_SIZE = 1000\n\nfunction normalizePageSize(\n value: unknown,\n fallback = DEFAULT_PAGE_SIZE\n): number {\n const pageSize = Number(value)\n if (!Number.isFinite(pageSize) || pageSize <= 0) return fallback\n return Math.min(MAX_PAGE_SIZE, Math.max(1, Math.floor(pageSize)))\n}\n\nfunction normalizePage(value: unknown): number {\n const page = Number(value)\n if (!Number.isFinite(page) || page < 1) return 1\n return Math.floor(page)\n}\n\nfunction cloneEntries(entries: readonly LogEntry[] | undefined): LogEntry[] {\n if (entries === undefined) return []\n if (!Array.isArray(entries))\n throw new TypeError('[LogViewer] data must be an array')\n\n return entries.map((entry, index) => {\n if (!entry || typeof entry !== 'object') {\n throw new TypeError(`[LogViewer] data[${index}] must be an object`)\n }\n\n const cloned = deepClone(entry)\n const id = String(cloned.id ?? '').trim()\n if (!id)\n throw new TypeError(\n `[LogViewer] data[${index}].id must be a non-empty string`\n )\n\n return {\n ...cloned,\n id,\n user: String(cloned.user ?? ''),\n module: String(cloned.module ?? ''),\n changes: Array.isArray(cloned.changes) ? cloned.changes : undefined,\n }\n })\n}\n\nfunction isActionType(value: string): value is ActionType {\n return Object.keys(ACTION_LABELS).includes(value)\n}\n\nfunction sourceEntries(payload: unknown): LogEntry[] {\n if (Array.isArray(payload)) return payload as LogEntry[]\n if (!payload || typeof payload !== 'object') {\n throw new TypeError('[LogViewer] dataSource response must be an array')\n }\n\n const record = payload as Record<string, unknown>\n for (const key of ['data', 'logs', 'items', 'entries']) {\n if (Array.isArray(record[key])) return record[key] as LogEntry[]\n }\n throw new TypeError('[LogViewer] dataSource response must contain an array')\n}\n\n/** LogViewer - framework-neutral audit log viewer. */\nexport class LogViewer implements LogViewerInstance {\n private readonly root: HTMLElement\n private readonly emitter = new EventEmitter()\n private readonly filterEngine = new FilterEngine()\n private readonly timelineRenderer = new TimelineRenderer()\n private readonly diffRenderer = new DiffRenderer()\n private readonly config: LogViewerConfig\n\n private data: LogEntry[] = []\n private filteredData: LogEntry[] = []\n private filter: FilterConfig = {}\n private pagination: PaginationConfig = {\n page: 1,\n pageSize: DEFAULT_PAGE_SIZE,\n }\n private theme: ThemeMode = 'light'\n private expandedIds = new Set<string>()\n private filterEl: HTMLElement | null = null\n private timelineEl: HTMLElement | null = null\n private paginationEl: HTMLElement | null = null\n private destroyed = false\n private requestId = 0\n private abortController: AbortController | null = null\n\n constructor(config: LogViewerConfig) {\n if (typeof document === 'undefined') {\n throw new Error('[LogViewer] A browser document is required')\n }\n\n const container =\n typeof config.container === 'string'\n ? document.querySelector<HTMLElement>(config.container)\n : config.container\n if (!container)\n throw new Error(\n `[LogViewer] Container not found: ${String(config.container)}`\n )\n\n this.config = { ...config }\n this.theme = config.theme === 'dark' ? 'dark' : 'light'\n this.pagination = {\n page: normalizePage(config.pagination?.page),\n pageSize: normalizePageSize(\n config.pageSize ?? config.pagination?.pageSize\n ),\n }\n this.filter = deepClone(config.filter || {})\n this.data = cloneEntries(config.data)\n\n injectStyles()\n this.root = document.createElement('div')\n this.root.className = 'lv-root'\n this.root.setAttribute('data-theme', this.theme)\n container.appendChild(this.root)\n\n this.bindEvents()\n this.applyFilterAndRender()\n\n if (config.dataSource) {\n void this.loadData().catch(() => undefined)\n }\n }\n\n getData(): LogEntry[] {\n return deepClone(this.data)\n }\n\n setData(entries: LogEntry[]): void {\n if (this.destroyed) return\n this.data = cloneEntries(entries)\n this.pagination.page = 1\n this.expandedIds.clear()\n this.applyFilterAndRender()\n this.emitter.emit('data:change', this.getData())\n }\n\n appendData(entries: LogEntry[]): void {\n if (this.destroyed) return\n this.data.push(...cloneEntries(entries))\n this.applyFilterAndRender()\n this.emitter.emit('data:change', this.getData())\n }\n\n getFilter(): FilterConfig {\n return deepClone(this.filter)\n }\n\n setFilter(filter: FilterConfig): void {\n if (this.destroyed) return\n this.filter = deepClone(filter || {})\n this.pagination.page = 1\n this.applyFilterAndRender()\n const current = this.getFilter()\n this.emitter.emit('filter:change', current)\n this.config.onFilterChange?.(current)\n }\n\n resetFilter(): void {\n if (this.destroyed) return\n this.setFilter({})\n }\n\n getTheme(): ThemeMode {\n return this.theme\n }\n\n setTheme(theme: ThemeMode): void {\n if (this.destroyed) return\n if (theme !== 'light' && theme !== 'dark') {\n throw new TypeError('[LogViewer] theme must be light or dark')\n }\n if (this.theme === theme) return\n this.theme = theme\n this.root.setAttribute('data-theme', theme)\n this.emitter.emit('theme:change', theme)\n this.config.onThemeChange?.(theme)\n }\n\n expandEntry(id: string): void {\n if (this.destroyed || this.expandedIds.has(id)) return\n this.expandedIds.add(id)\n const entry = this.data.find(item => item.id === id)\n if (entry) this.emitter.emit('entry:expand', deepClone(entry))\n this.renderTimeline()\n }\n\n collapseEntry(id: string): void {\n if (this.destroyed || !this.expandedIds.has(id)) return\n this.expandedIds.delete(id)\n const entry = this.data.find(item => item.id === id)\n if (entry) this.emitter.emit('entry:collapse', deepClone(entry))\n this.renderTimeline()\n }\n\n collapseAll(): void {\n if (this.destroyed || this.expandedIds.size === 0) return\n this.expandedIds.clear()\n this.renderTimeline()\n }\n\n goToPage(page: number): void {\n if (this.destroyed) return\n const totalPages = Math.max(\n 1,\n Math.ceil(this.filteredData.length / this.pagination.pageSize)\n )\n const nextPage = Math.min(totalPages, Math.max(1, normalizePage(page)))\n if (nextPage === this.pagination.page) return\n this.pagination.page = nextPage\n this.emitter.emit('page:change', nextPage)\n this.renderTimeline()\n }\n\n getPagination(): PaginationConfig {\n return {\n ...this.pagination,\n total: this.filteredData.length,\n }\n }\n\n on(event: string, callback: (...args: unknown[]) => void): () => void {\n return this.emitter.on(event, callback)\n }\n\n refresh(): void {\n if (!this.destroyed) this.applyFilterAndRender()\n }\n\n async loadData(): Promise<void> {\n if (this.destroyed || !this.config.dataSource) return\n\n const currentRequest = ++this.requestId\n this.abortController?.abort()\n this.abortController =\n typeof AbortController !== 'undefined' ? new AbortController() : null\n\n try {\n let payload: unknown\n if (typeof this.config.dataSource === 'function') {\n payload = await this.config.dataSource()\n } else {\n if (typeof fetch !== 'function')\n throw new Error('[LogViewer] fetch is unavailable')\n const response = await fetch(this.config.dataSource, {\n signal: this.abortController?.signal,\n })\n if (!response.ok) {\n throw new Error(\n `[LogViewer] dataSource request failed: ${response.status}`\n )\n }\n payload = await response.json()\n }\n\n if (this.destroyed || currentRequest !== this.requestId) return\n this.setData(sourceEntries(payload))\n } catch (error) {\n if (\n this.destroyed ||\n (typeof DOMException !== 'undefined' &&\n error instanceof DOMException &&\n error.name === 'AbortError')\n ) {\n return\n }\n this.config.onError?.(error)\n this.emitter.emit('error', error)\n throw error\n }\n }\n\n destroy(): void {\n if (this.destroyed) return\n this.destroyed = true\n this.requestId++\n this.abortController?.abort()\n this.abortController = null\n this.emitter.removeAllListeners()\n this.expandedIds.clear()\n this.root.replaceChildren()\n this.root.remove()\n }\n\n private applyFilterAndRender(): void {\n this.filteredData = this.filterEngine.filter(this.data, this.filter)\n this.filteredData = this.filteredData\n .map((entry, index) => ({ entry, index }))\n .sort((a, b) => {\n const left = new Date(a.entry.timestamp).getTime()\n const right = new Date(b.entry.timestamp).getTime()\n const leftTime = Number.isFinite(left) ? left : Number.MIN_SAFE_INTEGER\n const rightTime = Number.isFinite(right)\n ? right\n : Number.MIN_SAFE_INTEGER\n return rightTime - leftTime || a.index - b.index\n })\n .map(({ entry }) => entry)\n\n const totalPages = Math.max(\n 1,\n Math.ceil(this.filteredData.length / this.pagination.pageSize)\n )\n this.pagination.page = Math.min(this.pagination.page, totalPages)\n this.pagination.total = this.filteredData.length\n this.renderTimeline()\n }\n\n private getPageData(): LogEntry[] {\n const { page, pageSize } = this.pagination\n const start = (page - 1) * pageSize\n return this.filteredData.slice(start, start + pageSize)\n }\n\n private renderFilterBar(): HTMLElement | null {\n if (this.config.showFilter === false) return null\n\n const filter = document.createElement('div')\n filter.className = 'lv-filter'\n filter.setAttribute('role', 'search')\n\n const addInput = (\n field: 'user' | 'module' | 'ip' | 'keyword',\n label: string\n ) => {\n const item = document.createElement('label')\n item.className = 'lv-filter-item'\n const text = document.createElement('span')\n text.className = 'lv-filter-label'\n text.textContent = label\n const input = document.createElement('input')\n input.className = 'lv-filter-input'\n input.type = 'search'\n input.value = String(this.filter[field] || '')\n input.setAttribute('data-filter-field', field)\n input.setAttribute('aria-label', label)\n item.append(text, input)\n filter.appendChild(item)\n }\n\n addInput('keyword', this.config.locale === 'en-US' ? 'Keyword' : '关键词')\n addInput('user', this.config.locale === 'en-US' ? 'User' : '用户')\n addInput('module', this.config.locale === 'en-US' ? 'Module' : '模块')\n addInput('ip', 'IP')\n\n const actionItem = document.createElement('label')\n actionItem.className = 'lv-filter-item'\n const actionLabel = document.createElement('span')\n actionLabel.className = 'lv-filter-label'\n actionLabel.textContent = this.config.locale === 'en-US' ? 'Action' : '操作'\n const action = document.createElement('select')\n action.className = 'lv-filter-select'\n action.setAttribute('data-filter-field', 'action')\n action.setAttribute('aria-label', actionLabel.textContent)\n const allOption = document.createElement('option')\n allOption.value = ''\n allOption.textContent = this.config.locale === 'en-US' ? 'All' : '全部'\n action.appendChild(allOption)\n for (const [value, label] of Object.entries(ACTION_LABELS)) {\n const option = document.createElement('option')\n option.value = value\n option.textContent = label\n action.appendChild(option)\n }\n const selectedAction = Array.isArray(this.filter.action)\n ? ''\n : this.filter.action || ''\n action.value = selectedAction\n actionItem.append(actionLabel, action)\n filter.appendChild(actionItem)\n\n const reset = document.createElement('button')\n reset.type = 'button'\n reset.className = 'lv-filter-btn'\n reset.setAttribute('data-filter-reset', 'true')\n reset.textContent = this.config.locale === 'en-US' ? 'Reset' : '重置'\n filter.appendChild(reset)\n return filter\n }\n\n private updateFilterField(field: string, value: string): void {\n const next = this.getFilter()\n if (!value.trim()) {\n delete next[field as keyof FilterConfig]\n } else if (field === 'action' && isActionType(value)) {\n next.action = value\n } else if (field !== 'action') {\n next[field as 'user' | 'module' | 'ip' | 'keyword'] = value\n }\n this.setFilter(next)\n }\n\n private renderTimeline(): void {\n if (this.destroyed) return\n\n const pageData = this.getPageData()\n const timeline = this.timelineRenderer.render(pageData, this.expandedIds, {\n showDiff: this.config.showDiff,\n showAnomalyBadge: this.config.showAnomalyBadge,\n locale: this.config.locale,\n })\n\n if (this.config.showDiff !== false) {\n for (const entry of pageData) {\n if (!this.expandedIds.has(entry.id)) continue\n const item = [...timeline.children].find(\n child => child.getAttribute('data-id') === entry.id\n )\n const card = item?.querySelector('.lv-timeline-card')\n card?.appendChild(this.diffRenderer.renderDetail(entry))\n }\n }\n\n this.filterEl?.remove()\n this.timelineEl?.remove()\n this.paginationEl?.remove()\n\n this.filterEl = this.renderFilterBar()\n this.timelineEl = timeline\n this.paginationEl = this.timelineRenderer.renderPagination(\n this.pagination.page,\n this.pagination.pageSize,\n this.filteredData.length\n )\n\n if (this.filterEl) this.root.appendChild(this.filterEl)\n this.root.append(this.timelineEl, this.paginationEl)\n }\n\n private bindEvents(): void {\n this.root.addEventListener('change', event => {\n const target = event.target\n if (\n !(target instanceof HTMLInputElement) &&\n !(target instanceof HTMLSelectElement)\n )\n return\n const field = target.getAttribute('data-filter-field')\n if (field) this.updateFilterField(field, target.value)\n })\n\n this.root.addEventListener('click', event => {\n const target = event.target\n if (!(target instanceof Element)) return\n\n const reset = target.closest('[data-filter-reset]')\n if (reset) {\n this.resetFilter()\n return\n }\n\n const hint = target.closest('.lv-timeline-expand-hint')\n const item =\n hint?.closest('.lv-timeline-item') ||\n target.closest('.lv-timeline-item')\n const id = item?.getAttribute('data-id')\n if (hint && id) {\n if (this.expandedIds.has(id)) this.collapseEntry(id)\n else this.expandEntry(id)\n return\n }\n\n const pageButton = target.closest(\n '.lv-pagination-btn'\n ) as HTMLButtonElement | null\n if (pageButton && !pageButton.disabled) {\n const page = Number(pageButton.getAttribute('data-page'))\n if (Number.isFinite(page)) this.goToPage(page)\n return\n }\n\n const card = target.closest('.lv-timeline-card')\n if (!card || !id) return\n const entry = this.filteredData.find(candidate => candidate.id === id)\n if (entry) {\n const snapshot = deepClone(entry)\n this.emitter.emit('entry:click', snapshot)\n this.config.onEntryClick?.(snapshot)\n }\n })\n }\n}\n","/**\r\n * @composy/log-viewer-core\r\n * 审计日志查看器 - 操作日志可视化与追溯\r\n */\r\n\r\n/**\r\n * 创建 LogViewer 实例 - 工厂函数\r\n */\r\nimport type { LogViewerConfig } from './types'\r\nimport { LogViewer } from './core/LogViewer'\r\n\r\nexport const VERSION = '0.1.0'\r\n\r\n// 类型\r\nexport type {\r\n ActionType,\r\n ThemeMode,\r\n AnomalyType,\r\n DiffEntry,\r\n LogEntry,\r\n FilterConfig,\r\n PaginationConfig,\r\n LogViewerConfig,\r\n LogViewerInstance,\r\n LogViewerEvents,\r\n} from './types'\r\nexport { ACTION_LABELS, ACTION_COLORS } from './types'\r\n\r\n// 核心\r\nexport { LogViewer } from './core/LogViewer'\r\nexport { EventEmitter } from './core/EventEmitter'\r\n\r\n// 筛选\r\nexport { FilterEngine } from './filters/FilterEngine'\r\n\r\n// 渲染器\r\nexport { TimelineRenderer } from './renderers/TimelineRenderer'\r\nexport type { TimelineRendererOptions } from './renderers/TimelineRenderer'\r\nexport { DiffRenderer } from './renderers/DiffRenderer'\r\n\r\n// 工具\r\nexport {\r\n formatDate,\r\n formatRelativeTime,\r\n escapeHtml,\r\n debounce,\r\n uid,\r\n formatValue,\r\n deepClone,\r\n} from './utils'\r\n\r\n// 样式\r\nexport { injectStyles } from './styles'\r\n\r\n/**\r\n * createLogViewer - create Log Viewer function\r\n * @param config - 参数说明\r\n * @returns 返回值说明\r\n */\r\nexport function createLogViewer(config: LogViewerConfig): LogViewer {\r\n return new LogViewer(config)\r\n}\r\n"],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":1,"configuration":"f71ff8522a792c154fee4c8b907087e8e68c7058d4b96ce1af14db3ddde31259","sources":{"D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\src\\core\\EventEmitter.ts":["D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\es\\core\\EventEmitter.d.ts"],"D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\src\\types\\index.ts":["D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\es\\types\\index.d.ts"],"D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\src\\filters\\FilterEngine.ts":["D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\es\\filters\\FilterEngine.d.ts"],"D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\src\\utils\\index.ts":["D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\es\\utils\\index.d.ts"],"D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\src\\renderers\\DiffRenderer.ts":["D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\es\\renderers\\DiffRenderer.d.ts"],"D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\src\\renderers\\TimelineRenderer.ts":["D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\es\\renderers\\TimelineRenderer.d.ts"],"D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\src\\styles\\index.ts":["D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\es\\styles\\index.d.ts"],"D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\src\\core\\LogViewer.ts":["D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\es\\core\\LogViewer.d.ts"],"D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\src\\index.ts":["D:\\WorkBench\\ldesign\\libraries\\log-viewer\\packages\\core\\es\\index.d.ts"]}}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"fileNames":["../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es5.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2015.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2016.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2017.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2018.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2019.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2020.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.dom.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.dom.iterable.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.dom.asynciterable.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.webworker.importscripts.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.scripthost.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2015.core.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2015.collection.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2015.generator.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2015.iterable.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2015.promise.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2015.proxy.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2015.reflect.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2015.symbol.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2015.symbol.wellknown.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2016.array.include.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2016.intl.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2017.arraybuffer.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2017.date.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2017.object.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2017.sharedmemory.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2017.string.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2017.intl.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2017.typedarrays.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2018.asyncgenerator.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2018.asynciterable.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2018.intl.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2018.promise.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2018.regexp.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2019.array.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2019.object.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2019.string.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2019.symbol.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2019.intl.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2020.bigint.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2020.date.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2020.promise.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2020.sharedmemory.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2020.string.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2020.symbol.wellknown.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2020.intl.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2020.number.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.decorators.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.decorators.legacy.d.ts","../../../../../node_modules/.pnpm/typescript@5.9.3/node_modules/typescript/lib/lib.es2020.full.d.ts","../src/core/eventemitter.ts","../src/types/index.ts","../src/filters/filterengine.ts","../src/utils/index.ts","../src/renderers/diffrenderer.ts","../src/renderers/timelinerenderer.ts","../src/styles/index.ts","../src/core/logviewer.ts","../src/index.ts"],"fileIdsList":[[52,53,54,55,56,57,58],[53],[52,53,54,55,56,57,58,59],[53,55]],"fileInfos":[{"version":"c430d44666289dae81f30fa7b2edebf186ecc91a2d4c71266ea6ae76388792e1","affectsGlobalScope":true,"impliedFormat":1},{"version":"45b7ab580deca34ae9729e97c13cfd999df04416a79116c3bfb483804f85ded4","impliedFormat":1},{"version":"3facaf05f0c5fc569c5649dd359892c98a85557e3e0c847964caeb67076f4d75","impliedFormat":1},{"version":"e44bb8bbac7f10ecc786703fe0a6a4b952189f908707980ba8f3c8975a760962","impliedFormat":1},{"version":"5e1c4c362065a6b95ff952c0eab010f04dcd2c3494e813b493ecfd4fcb9fc0d8","impliedFormat":1},{"version":"68d73b4a11549f9c0b7d352d10e91e5dca8faa3322bfb77b661839c42b1ddec7","impliedFormat":1},{"version":"5efce4fc3c29ea84e8928f97adec086e3dc876365e0982cc8479a07954a3efd4","impliedFormat":1},{"version":"080941d9f9ff9307f7e27a83bcd888b7c8270716c39af943532438932ec1d0b9","affectsGlobalScope":true,"impliedFormat":1},{"version":"2e80ee7a49e8ac312cc11b77f1475804bee36b3b2bc896bead8b6e1266befb43","affectsGlobalScope":true,"impliedFormat":1},{"version":"d7a3c8b952931daebdfc7a2897c53c0a1c73624593fa070e46bd537e64dcd20a","affectsGlobalScope":true,"impliedFormat":1},{"version":"80e18897e5884b6723488d4f5652167e7bb5024f946743134ecc4aa4ee731f89","affectsGlobalScope":true,"impliedFormat":1},{"version":"cd034f499c6cdca722b60c04b5b1b78e058487a7085a8e0d6fb50809947ee573","affectsGlobalScope":true,"impliedFormat":1},{"version":"c57796738e7f83dbc4b8e65132f11a377649c00dd3eee333f672b8f0a6bea671","affectsGlobalScope":true,"impliedFormat":1},{"version":"dc2df20b1bcdc8c2d34af4926e2c3ab15ffe1160a63e58b7e09833f616efff44","affectsGlobalScope":true,"impliedFormat":1},{"version":"515d0b7b9bea2e31ea4ec968e9edd2c39d3eebf4a2d5cbd04e88639819ae3b71","affectsGlobalScope":true,"impliedFormat":1},{"version":"0559b1f683ac7505ae451f9a96ce4c3c92bdc71411651ca6ddb0e88baaaad6a3","affectsGlobalScope":true,"impliedFormat":1},{"version":"0dc1e7ceda9b8b9b455c3a2d67b0412feab00bd2f66656cd8850e8831b08b537","affectsGlobalScope":true,"impliedFormat":1},{"version":"ce691fb9e5c64efb9547083e4a34091bcbe5bdb41027e310ebba8f7d96a98671","affectsGlobalScope":true,"impliedFormat":1},{"version":"8d697a2a929a5fcb38b7a65594020fcef05ec1630804a33748829c5ff53640d0","affectsGlobalScope":true,"impliedFormat":1},{"version":"4ff2a353abf8a80ee399af572debb8faab2d33ad38c4b4474cff7f26e7653b8d","affectsGlobalScope":true,"impliedFormat":1},{"version":"fb0f136d372979348d59b3f5020b4cdb81b5504192b1cacff5d1fbba29378aa1","affectsGlobalScope":true,"impliedFormat":1},{"version":"d15bea3d62cbbdb9797079416b8ac375ae99162a7fba5de2c6c505446486ac0a","affectsGlobalScope":true,"impliedFormat":1},{"version":"68d18b664c9d32a7336a70235958b8997ebc1c3b8505f4f1ae2b7e7753b87618","affectsGlobalScope":true,"impliedFormat":1},{"version":"eb3d66c8327153d8fa7dd03f9c58d351107fe824c79e9b56b462935176cdf12a","affectsGlobalScope":true,"impliedFormat":1},{"version":"38f0219c9e23c915ef9790ab1d680440d95419ad264816fa15009a8851e79119","affectsGlobalScope":true,"impliedFormat":1},{"version":"69ab18c3b76cd9b1be3d188eaf8bba06112ebbe2f47f6c322b5105a6fbc45a2e","affectsGlobalScope":true,"impliedFormat":1},{"version":"a680117f487a4d2f30ea46f1b4b7f58bef1480456e18ba53ee85c2746eeca012","affectsGlobalScope":true,"impliedFormat":1},{"version":"2f11ff796926e0832f9ae148008138ad583bd181899ab7dd768a2666700b1893","affectsGlobalScope":true,"impliedFormat":1},{"version":"4de680d5bb41c17f7f68e0419412ca23c98d5749dcaaea1896172f06435891fc","affectsGlobalScope":true,"impliedFormat":1},{"version":"954296b30da6d508a104a3a0b5d96b76495c709785c1d11610908e63481ee667","affectsGlobalScope":true,"impliedFormat":1},{"version":"ac9538681b19688c8eae65811b329d3744af679e0bdfa5d842d0e32524c73e1c","affectsGlobalScope":true,"impliedFormat":1},{"version":"0a969edff4bd52585473d24995c5ef223f6652d6ef46193309b3921d65dd4376","affectsGlobalScope":true,"impliedFormat":1},{"version":"9e9fbd7030c440b33d021da145d3232984c8bb7916f277e8ffd3dc2e3eae2bdb","affectsGlobalScope":true,"impliedFormat":1},{"version":"811ec78f7fefcabbda4bfa93b3eb67d9ae166ef95f9bff989d964061cbf81a0c","affectsGlobalScope":true,"impliedFormat":1},{"version":"717937616a17072082152a2ef351cb51f98802fb4b2fdabd32399843875974ca","affectsGlobalScope":true,"impliedFormat":1},{"version":"d7e7d9b7b50e5f22c915b525acc5a49a7a6584cf8f62d0569e557c5cfc4b2ac2","affectsGlobalScope":true,"impliedFormat":1},{"version":"71c37f4c9543f31dfced6c7840e068c5a5aacb7b89111a4364b1d5276b852557","affectsGlobalScope":true,"impliedFormat":1},{"version":"576711e016cf4f1804676043e6a0a5414252560eb57de9faceee34d79798c850","affectsGlobalScope":true,"impliedFormat":1},{"version":"89c1b1281ba7b8a96efc676b11b264de7a8374c5ea1e6617f11880a13fc56dc6","affectsGlobalScope":true,"impliedFormat":1},{"version":"74f7fa2d027d5b33eb0471c8e82a6c87216223181ec31247c357a3e8e2fddc5b","affectsGlobalScope":true,"impliedFormat":1},{"version":"d6d7ae4d1f1f3772e2a3cde568ed08991a8ae34a080ff1151af28b7f798e22ca","affectsGlobalScope":true,"impliedFormat":1},{"version":"063600664504610fe3e99b717a1223f8b1900087fab0b4cad1496a114744f8df","affectsGlobalScope":true,"impliedFormat":1},{"version":"934019d7e3c81950f9a8426d093458b65d5aff2c7c1511233c0fd5b941e608ab","affectsGlobalScope":true,"impliedFormat":1},{"version":"52ada8e0b6e0482b728070b7639ee42e83a9b1c22d205992756fe020fd9f4a47","affectsGlobalScope":true,"impliedFormat":1},{"version":"3bdefe1bfd4d6dee0e26f928f93ccc128f1b64d5d501ff4a8cf3c6371200e5e6","affectsGlobalScope":true,"impliedFormat":1},{"version":"59fb2c069260b4ba00b5643b907ef5d5341b167e7d1dbf58dfd895658bda2867","affectsGlobalScope":true,"impliedFormat":1},{"version":"639e512c0dfc3fad96a84caad71b8834d66329a1f28dc95e3946c9b58176c73a","affectsGlobalScope":true,"impliedFormat":1},{"version":"368af93f74c9c932edd84c58883e736c9e3d53cec1fe24c0b0ff451f529ceab1","affectsGlobalScope":true,"impliedFormat":1},{"version":"8e7f8264d0fb4c5339605a15daadb037bf238c10b654bb3eee14208f860a32ea","affectsGlobalScope":true,"impliedFormat":1},{"version":"782dec38049b92d4e85c1585fbea5474a219c6984a35b004963b00beb1aab538","affectsGlobalScope":true,"impliedFormat":1},{"version":"1305d1e76ca44e30fb8b2b8075fa522b83f60c0bcf5d4326a9d2cf79b53724f8","impliedFormat":1},{"version":"370b83d7526dfe6ed470f420effa3c2dd12dbfb61efe28b3b3b640d4e6d01d40","signature":"20825ce5ce9ce1f472e142dab927ef00534686769cf02ec1cd972073a8c605f7"},{"version":"d470a2d779b7cdd4c27175222fbea4365a80e1e07f1547f0a68f3f6b6957449a","signature":"465fec685e813623beccaca6559552ad158d8520eb14ed3b41ab6962e6f49269"},{"version":"857aab30c8e9182ee2a2a50b8849335fe6b82494d380e9633204206066bdc833","signature":"499f7c2b37df052ed613e236dc19c25859260394c918edcd3233c264eb4e4dcc"},{"version":"ba5d10df483c20964ed4539d17f5296f3e5ac29718c769fe9339e51b47573831","signature":"2420edf558119a55288f150c77340e94dadcbbf3d776f49847b7391a6c732a60"},{"version":"fa594326733313604c730bc96c702f1321759782a79276f41ddf2164cf2f9a9b","signature":"0239dad76d464e94ba94dc6c1fe8d4ce86c6a20a7764fa17dc444bc930fb473a"},{"version":"93a45c6929d57189f2e90cc67e3bce175f68e7753f65939d551410f2a58dfebd","signature":"c1338c0a1884a2bdf5cf38aee21aee9f6a4463eaf32e1e3d91237158dfd7ecc7"},{"version":"7f7dd5b320324717f23cb90cdffd8258aad523d84d169063248920807e61b6a5","signature":"bb88cad0b8300261e75d2c1583b6ba0fbf4cbcc143c9feaa461b685f8817ea7c"},{"version":"88f7e512d0f3033afb90c603dddb19cbed56dd634d21fdadfb9ba31a294c70a4","signature":"8245e252f579bb959a411bd99d709dbbcd5bcdff800f24969a8e0410a2d3fa49"},{"version":"92211ebbe843c8b56246248301183d0e6bba540238e8444f5a3324b23393dc6d","signature":"432ad2a0e5cdfa8493d261b04ad35b43f8243e72d16c7448b7b2dae624132be2"}],"root":[[52,60]],"options":{"allowJs":false,"declaration":true,"declarationDir":"./","declarationMap":false,"emitDeclarationOnly":true,"esModuleInterop":true,"module":99,"noImplicitAny":false,"outDir":"./","rootDir":"../src","skipLibCheck":true,"strict":false,"target":7,"tsBuildInfoFile":"./.dts.tsbuildinfo"},"referencedMap":[[59,1],[54,2],[60,3],[56,4],[57,4]],"semanticDiagnosticsPerFile":[1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60],"version":"5.9.3"}
|
package/es/core/EventEmitter.js
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
* ***********************************
|
|
3
3
|
* @composy/log-viewer-core v0.0.1 *
|
|
4
4
|
* Built with rollup *
|
|
5
|
-
* Build time: 2024-
|
|
5
|
+
* Build time: 2024-10-12 17:29:20 *
|
|
6
6
|
* Build mode: production *
|
|
7
7
|
* Minified: No *
|
|
8
8
|
* ***********************************
|
|
@@ -13,21 +13,25 @@ var EventEmitter = class {
|
|
|
13
13
|
this.listeners = /* @__PURE__ */ new Map();
|
|
14
14
|
}
|
|
15
15
|
on(event, callback) {
|
|
16
|
+
if (!event || typeof callback !== "function") return () => void 0;
|
|
16
17
|
if (!this.listeners.has(event)) this.listeners.set(event, /* @__PURE__ */ new Set());
|
|
17
18
|
this.listeners.get(event).add(callback);
|
|
18
19
|
return () => this.off(event, callback);
|
|
19
20
|
}
|
|
20
21
|
off(event, callback) {
|
|
21
|
-
this.listeners.get(event)
|
|
22
|
+
const listeners = this.listeners.get(event);
|
|
23
|
+
if (!listeners) return;
|
|
24
|
+
listeners.delete(callback);
|
|
25
|
+
if (listeners.size === 0) this.listeners.delete(event);
|
|
22
26
|
}
|
|
23
27
|
emit(event, ...args) {
|
|
24
|
-
this.listeners.get(event)
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
}
|
|
30
|
-
}
|
|
28
|
+
const listeners = this.listeners.get(event);
|
|
29
|
+
if (!listeners) return;
|
|
30
|
+
for (const cb of [...listeners]) try {
|
|
31
|
+
cb(...args);
|
|
32
|
+
} catch (e) {
|
|
33
|
+
console.error(`[LogViewer] Event handler error (${event}):`, e);
|
|
34
|
+
}
|
|
31
35
|
}
|
|
32
36
|
removeAllListeners(event) {
|
|
33
37
|
if (event) this.listeners.delete(event);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"EventEmitter.js","names":[],"sources":["../../src/core/EventEmitter.ts"],"sourcesContent":["/**\n * 简单的事件发射器\n */\nexport class EventEmitter {\n private listeners = new Map<string, Set<(...args: unknown[]) => void>>()\n\n on(event: string, callback: (...args: unknown[]) => void): () => void {\n if (!this.listeners.has(event)) {\n this.listeners.set(event, new Set())\n }\n this.listeners.get(event)
|
|
1
|
+
{"version":3,"file":"EventEmitter.js","names":[],"sources":["../../src/core/EventEmitter.ts"],"sourcesContent":["/**\r\n * 简单的事件发射器\r\n */\r\nexport class EventEmitter {\r\n private listeners = new Map<string, Set<(...args: unknown[]) => void>>()\r\n\r\n on(event: string, callback: (...args: unknown[]) => void): () => void {\r\n if (!event || typeof callback !== 'function') {\r\n return () => undefined\r\n }\r\n if (!this.listeners.has(event)) {\r\n this.listeners.set(event, new Set())\r\n }\r\n const listeners = this.listeners.get(event)!\r\n listeners.add(callback)\r\n return () => this.off(event, callback)\r\n }\r\n\r\n off(event: string, callback: (...args: unknown[]) => void): void {\r\n const listeners = this.listeners.get(event)\r\n if (!listeners) return\r\n listeners.delete(callback)\r\n if (listeners.size === 0) this.listeners.delete(event)\r\n }\r\n\r\n emit(event: string, ...args: unknown[]): void {\r\n const listeners = this.listeners.get(event)\r\n if (!listeners) return\r\n\r\n // Snapshot the set so listeners can unsubscribe or subscribe while the\r\n // current event is being delivered without changing this dispatch cycle.\r\n for (const cb of [...listeners]) {\r\n try {\r\n cb(...args)\r\n } catch (e) {\r\n console.error(`[LogViewer] Event handler error (${event}):`, e)\r\n }\r\n }\r\n }\r\n\r\n removeAllListeners(event?: string): void {\r\n if (event) {\r\n this.listeners.delete(event)\r\n } else {\r\n this.listeners.clear()\r\n }\r\n }\r\n}\r\n"],"mappings":";;;;;;;;;;AAGO,IAAM,eAAN,MAAmB;CAAnB,cAAA;EACL,KAAQ,4BAAY,IAAI,IAA+C;CAAA;CAEvE,GAAG,OAAe,UAAoD;EACpE,IAAI,CAAC,SAAS,OAAO,aAAa,YAChC,aAAa,KAAA;EAEf,IAAI,CAAC,KAAK,UAAU,IAAI,KAAK,GAC3B,KAAK,UAAU,IAAI,uBAAO,IAAI,IAAI,CAAC;EAGrC,KADuB,UAAU,IAAI,KACrC,CAAA,CAAU,IAAI,QAAQ;EACtB,aAAa,KAAK,IAAI,OAAO,QAAQ;CACvC;CAEA,IAAI,OAAe,UAA8C;EAC/D,MAAM,YAAY,KAAK,UAAU,IAAI,KAAK;EAC1C,IAAI,CAAC,WAAW;EAChB,UAAU,OAAO,QAAQ;EACzB,IAAI,UAAU,SAAS,GAAG,KAAK,UAAU,OAAO,KAAK;CACvD;CAEA,KAAK,OAAA,GAAkB,MAAuB;EAC5C,MAAM,YAAY,KAAK,UAAU,IAAI,KAAK;EAC1C,IAAI,CAAC,WAAW;EAIhB,KAAA,MAAW,MAAM,CAAC,GAAG,SAAS,GAC5B,IAAI;GACF,GAAG,GAAG,IAAI;EACZ,SAAS,GAAG;GACV,QAAQ,MAAM,oCAAoC,MAAK,KAAM,CAAC;EAChE;CAEJ;CAEA,mBAAmB,OAAsB;EACvC,IAAI,OACF,KAAK,UAAU,OAAO,KAAK;OAE3B,KAAK,UAAU,MAAM;CAEzB;AACF"}
|
package/es/core/LogViewer.d.ts
CHANGED
|
@@ -1,26 +1,27 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* LogViewer 核心引擎
|
|
3
3
|
*/
|
|
4
|
-
import type { LogEntry, LogViewerConfig, LogViewerInstance,
|
|
5
|
-
/**
|
|
6
|
-
* LogViewer - Log Viewer class
|
|
7
|
-
*/
|
|
4
|
+
import type { FilterConfig, LogEntry, LogViewerConfig, LogViewerInstance, PaginationConfig, ThemeMode } from '../types';
|
|
5
|
+
/** LogViewer - framework-neutral audit log viewer. */
|
|
8
6
|
export declare class LogViewer implements LogViewerInstance {
|
|
9
|
-
private root;
|
|
10
|
-
private emitter;
|
|
11
|
-
private filterEngine;
|
|
12
|
-
private timelineRenderer;
|
|
13
|
-
private diffRenderer;
|
|
7
|
+
private readonly root;
|
|
8
|
+
private readonly emitter;
|
|
9
|
+
private readonly filterEngine;
|
|
10
|
+
private readonly timelineRenderer;
|
|
11
|
+
private readonly diffRenderer;
|
|
12
|
+
private readonly config;
|
|
14
13
|
private data;
|
|
15
14
|
private filteredData;
|
|
16
15
|
private filter;
|
|
17
16
|
private pagination;
|
|
18
17
|
private theme;
|
|
19
18
|
private expandedIds;
|
|
20
|
-
private
|
|
19
|
+
private filterEl;
|
|
21
20
|
private timelineEl;
|
|
22
21
|
private paginationEl;
|
|
23
22
|
private destroyed;
|
|
23
|
+
private requestId;
|
|
24
|
+
private abortController;
|
|
24
25
|
constructor(config: LogViewerConfig);
|
|
25
26
|
getData(): LogEntry[];
|
|
26
27
|
setData(entries: LogEntry[]): void;
|
|
@@ -37,10 +38,12 @@ export declare class LogViewer implements LogViewerInstance {
|
|
|
37
38
|
getPagination(): PaginationConfig;
|
|
38
39
|
on(event: string, callback: (...args: unknown[]) => void): () => void;
|
|
39
40
|
refresh(): void;
|
|
41
|
+
loadData(): Promise<void>;
|
|
40
42
|
destroy(): void;
|
|
41
43
|
private applyFilterAndRender;
|
|
42
44
|
private getPageData;
|
|
45
|
+
private renderFilterBar;
|
|
46
|
+
private updateFilterField;
|
|
43
47
|
private renderTimeline;
|
|
44
48
|
private bindEvents;
|
|
45
49
|
}
|
|
46
|
-
//# sourceMappingURL=LogViewer.d.ts.map
|