asaihost-nodejs 0.0.1
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/README.md +518 -0
- package/dist/InterventionLog-25EHE4QR.cjs +30 -0
- package/dist/InterventionLog-25EHE4QR.cjs.map +1 -0
- package/dist/InterventionLog-R6CCPU2B.es.js +30 -0
- package/dist/InterventionLog-R6CCPU2B.es.js.map +1 -0
- package/dist/LogStore-ECXX34WC.es.js +54 -0
- package/dist/LogStore-ECXX34WC.es.js.map +1 -0
- package/dist/LogStore-M2AUBNGO.cjs +54 -0
- package/dist/LogStore-M2AUBNGO.cjs.map +1 -0
- package/dist/asaihost-nodejs.cjs +6761 -0
- package/dist/asaihost-nodejs.cjs.map +1 -0
- package/dist/asaihost-nodejs.d.cts +406 -0
- package/dist/asaihost-nodejs.d.ts +406 -0
- package/dist/asaihost-nodejs.es.js +6761 -0
- package/dist/asaihost-nodejs.es.js.map +1 -0
- package/dist/chunk-4WJDC4M4.es.js +311 -0
- package/dist/chunk-4WJDC4M4.es.js.map +1 -0
- package/dist/chunk-6U2I5EON.es.js +12 -0
- package/dist/chunk-6U2I5EON.es.js.map +1 -0
- package/dist/chunk-DROOHKB3.es.js +87 -0
- package/dist/chunk-DROOHKB3.es.js.map +1 -0
- package/dist/chunk-E7V3EBDB.es.js +435 -0
- package/dist/chunk-E7V3EBDB.es.js.map +1 -0
- package/dist/chunk-EOGZPRML.es.js +740 -0
- package/dist/chunk-EOGZPRML.es.js.map +1 -0
- package/dist/chunk-G4WVDUBH.cjs +463 -0
- package/dist/chunk-G4WVDUBH.cjs.map +1 -0
- package/dist/chunk-HHPGUJ75.cjs +162 -0
- package/dist/chunk-HHPGUJ75.cjs.map +1 -0
- package/dist/chunk-KOFCBB3N.cjs +87 -0
- package/dist/chunk-KOFCBB3N.cjs.map +1 -0
- package/dist/chunk-KUZQ36IJ.es.js +162 -0
- package/dist/chunk-KUZQ36IJ.es.js.map +1 -0
- package/dist/chunk-LOMSUPPU.es.js +1202 -0
- package/dist/chunk-LOMSUPPU.es.js.map +1 -0
- package/dist/chunk-MCMADJQR.es.js +463 -0
- package/dist/chunk-MCMADJQR.es.js.map +1 -0
- package/dist/chunk-NLBFIRDB.cjs +105 -0
- package/dist/chunk-NLBFIRDB.cjs.map +1 -0
- package/dist/chunk-O6LVLSNB.cjs +40 -0
- package/dist/chunk-O6LVLSNB.cjs.map +1 -0
- package/dist/chunk-QWVR2HNT.cjs +435 -0
- package/dist/chunk-QWVR2HNT.cjs.map +1 -0
- package/dist/chunk-SMVZ3ZDJ.cjs +12 -0
- package/dist/chunk-SMVZ3ZDJ.cjs.map +1 -0
- package/dist/chunk-UTKVJE7N.es.js +40 -0
- package/dist/chunk-UTKVJE7N.es.js.map +1 -0
- package/dist/chunk-VLMM735Q.cjs +1202 -0
- package/dist/chunk-VLMM735Q.cjs.map +1 -0
- package/dist/chunk-W7DVKGX5.cjs +311 -0
- package/dist/chunk-W7DVKGX5.cjs.map +1 -0
- package/dist/chunk-X7VHW2TD.cjs +740 -0
- package/dist/chunk-X7VHW2TD.cjs.map +1 -0
- package/dist/chunk-XBIN4C2V.es.js +105 -0
- package/dist/chunk-XBIN4C2V.es.js.map +1 -0
- package/dist/intervention-hooks-FI4EHOL5.es.js +21 -0
- package/dist/intervention-hooks-FI4EHOL5.es.js.map +1 -0
- package/dist/intervention-hooks-LE6X4C6N.cjs +21 -0
- package/dist/intervention-hooks-LE6X4C6N.cjs.map +1 -0
- package/dist/log-alert-GLCULMQP.es.js +51 -0
- package/dist/log-alert-GLCULMQP.es.js.map +1 -0
- package/dist/log-alert-LAJ6VSAG.cjs +51 -0
- package/dist/log-alert-LAJ6VSAG.cjs.map +1 -0
- package/dist/log-formats-FKFMQKNO.cjs +31 -0
- package/dist/log-formats-FKFMQKNO.cjs.map +1 -0
- package/dist/log-formats-I5E32H5F.es.js +31 -0
- package/dist/log-formats-I5E32H5F.es.js.map +1 -0
- package/dist/password-63OY27RX.es.js +20 -0
- package/dist/password-63OY27RX.es.js.map +1 -0
- package/dist/password-NZ5EGDWG.cjs +20 -0
- package/dist/password-NZ5EGDWG.cjs.map +1 -0
- package/dist/user-store-J7LWEXSW.es.js +12 -0
- package/dist/user-store-J7LWEXSW.es.js.map +1 -0
- package/dist/user-store-SX4N6PQ4.cjs +12 -0
- package/dist/user-store-SX4N6PQ4.cjs.map +1 -0
- package/package.json +79 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/sysserver/lib/common/InterventionLog.ts"],"sourcesContent":["/**\r\n * IEC 62443-4-2 干预日志(Intervention Log)— CEF 格式安全事件记录引擎\r\n *\r\n * 依据标准要求实现:\r\n * - 留存 ≥5 年(retentionYears,默认 5),删除前校验留存期,删除动作本身必须被记录\r\n * - 自动记录:仅由服务端业务代码在真实干预发生时调用 logIntervention(),客户端无法直接写入任意日志内容\r\n * - 关联手段:绝对时间戳(rt) + 启动计数(cn1) + 运行计数(cn2) + 进程运行时长(cn3)\r\n * - 篡改证据:哈希链(每条记录携带对前一条记录的 sha256 摘要 cs4),任意历史记录被删改都会导致后续链路校验失败\r\n * - 日志格式:CEF:Version|DeviceVendor|DeviceProduct|DeviceVersion|SignatureID|Name|Severity|Extension\r\n *\r\n * 需要记录的干预类型(对应 IEC 62443-4-2 4-2 章节要求):\r\n * - SAFETY_PARAM 安全参数化/配置参数变更(使用 CRC 等标识手段)\r\n * - SRESW_UPDATE 嵌入式安全相关软件(SRESW)更新/修改\r\n * - SRASW_UPDATE 应用安全相关软件(SRASW)更新/修改\r\n * - HMI_PARAM 可能导致危险的人机界面参数化\r\n * - SAFETY_DISPLAY_SW 与安全相关指令显示相关的软件变更\r\n * - LOG_DELETE 日志文件删除(无论成功与否,均须记录)\r\n * - PROCESS_GUARD 进程守护/优雅退出/频繁崩溃重启(控制系统事件)\r\n *\r\n * 豁免(不应写入本日志):\r\n * - 未改变上述数据的干预(如成功/失败的常规鉴权动作)\r\n * - 触发机器安全状态的动作(如安全光幕开启)\r\n *\r\n * 测试/演示隔离(testPath):\r\n * - testkdd/testlog 等演示、自动化测试触发的干预动作一律写入独立的 'test' 命名空间目录\r\n * (logger.intervention.testPath),与承担 5 年合规留存义务的 'prod' 生产目录完全物理隔离。\r\n * - 两个命名空间各自拥有独立的哈希链状态、独立的删除审计文件,互不污染、互不计数,\r\n * 可反复清空 'test' 目录用于回归测试,不影响生产留存证据的完整性。\r\n */\r\nimport fsp from 'node:fs/promises';\r\nimport path from 'node:path';\r\nimport { createHash } from 'node:crypto';\r\nimport { getNowTime } from '../../../core/time';\r\nimport { mirrorInterventionLog, purgeSqliteEntriesForFile } from './LogStore';\r\nimport { getLogFormatTaxonomy } from './log-formats';\r\n\r\n/** 'prod' = 受5年留存保护的生产干预日志;'test' = 演示/自动化测试专用,完全隔离、不计入合规留存 */\r\nexport type LogNamespace = 'prod' | 'test';\r\n\r\nexport type InterventionType =\r\n\t| 'SAFETY_PARAM'\r\n\t| 'SRESW_UPDATE'\r\n\t| 'SRASW_UPDATE'\r\n\t| 'HMI_PARAM'\r\n\t| 'SAFETY_DISPLAY_SW'\r\n\t| 'LOG_DELETE'\r\n\t| 'PROCESS_GUARD';\r\n\r\nexport type InterventionCategory =\r\n\t| 'AccessControl'\r\n\t| 'RequestErrors'\r\n\t| 'ControlSystemEvents'\r\n\t| 'BackupRestore'\r\n\t| 'ConfigurationChanges'\r\n\t| 'AuditLogEvents';\r\n\r\nexport interface InterventionEvent {\r\n\ttype: InterventionType;\r\n\tname: string;\r\n\tcategory?: InterventionCategory;\r\n\tseverity?: number;\r\n\tus?: string;\r\n\tsrc?: string;\r\n\tdst?: string;\r\n\tproto?: string;\r\n\t/** CRC/哈希/版本号等标识手段,不要求存放二进制文件的真实版本号 */\r\n\tidentification?: string;\r\n\toutcome?: 'Success' | 'Failure';\r\n\tdetail?: string;\r\n\tfname?: string;\r\n}\r\n\r\nconst FILE_NAME_RE = /^intervention-\\d{4}-\\d{2}-\\d{2}\\.cef\\.log$/;\r\n\r\n/**\r\n * 删除动作的审计证据必须独立于被删除的内容文件存放,否则\"删除今天的日志文件\"这一操作\r\n * 会把记录删除行为本身的那条 CEF 记录也一并删掉,违反\"删除日志文件必须被记录\"的强制要求。\r\n * 该文件名不匹配 FILE_NAME_RE,deleteInterventionFile 会天然拒绝对它的删除请求。\r\n */\r\nconst DELETION_AUDIT_FILE = 'intervention-deletion-audit.cef.log';\r\n\r\nconst SIGNATURE_ID: Record<InterventionType, string> = {\r\n\tSAFETY_PARAM: 'ASAI.SAFETY.PARAM.001',\r\n\tSRESW_UPDATE: 'ASAI.SRESW.UPDATE.001',\r\n\tSRASW_UPDATE: 'ASAI.SRASW.UPDATE.001',\r\n\tHMI_PARAM: 'ASAI.HMI.PARAM.001',\r\n\tSAFETY_DISPLAY_SW: 'ASAI.SAFETY.DISPLAY.001',\r\n\tLOG_DELETE: 'ASAI.AUDIT.LOGDELETE.001',\r\n\tPROCESS_GUARD: 'ASAI.PROCESS.GUARD.001',\r\n};\r\n\r\nconst DEFAULT_CATEGORY: Record<InterventionType, InterventionCategory> = {\r\n\tSAFETY_PARAM: 'ConfigurationChanges',\r\n\tSRESW_UPDATE: 'ConfigurationChanges',\r\n\tSRASW_UPDATE: 'ConfigurationChanges',\r\n\tHMI_PARAM: 'ConfigurationChanges',\r\n\tSAFETY_DISPLAY_SW: 'ConfigurationChanges',\r\n\tLOG_DELETE: 'AuditLogEvents',\r\n\tPROCESS_GUARD: 'ControlSystemEvents',\r\n};\r\n\r\nconst DEFAULT_SEVERITY: Record<InterventionType, number> = {\r\n\tSAFETY_PARAM: 8,\r\n\tSRESW_UPDATE: 9,\r\n\tSRASW_UPDATE: 8,\r\n\tHMI_PARAM: 7,\r\n\tSAFETY_DISPLAY_SW: 8,\r\n\tLOG_DELETE: 7,\r\n\tPROCESS_GUARD: 9,\r\n};\r\n\r\n/** 用户提供的 6 类 CEF Severity 分级指引(中英文说明保留原文,便于前端展示) */\r\nconst CATEGORY_GUIDE: Record<InterventionCategory, { min: number; max: number; en: string; zh: string; note: string }> = {\r\n\tAccessControl: { min: 7, max: 8, en: 'Access Control', zh: '访问控制', note: '登录失败、权限提升、未授权访问尝试' },\r\n\tRequestErrors: { min: 2, max: 4, en: 'Request Errors', zh: '请求错误', note: '协议格式错误、无效命令、通信异常' },\r\n\tControlSystemEvents: { min: 8, max: 10, en: 'Control System Events', zh: '控制系统事件', note: '安全功能触发、PLC 模式切换、I/O 强制值' },\r\n\tBackupRestore: { min: 6, max: 7, en: 'Backup and Restore Events', zh: '备份与恢复', note: '正常备份偏低,恢复操作风险很高' },\r\n\tConfigurationChanges: { min: 7, max: 9, en: 'Configuration Changes', zh: '配置更改', note: '安全参数、控制逻辑、网络设置变更' },\r\n\tAuditLogEvents: { min: 7, max: 8, en: 'Audit Log Events', zh: '审计日志事件', note: '日志清除、日志篡改、日志系统故障' },\r\n};\r\n\r\nfunction getInterventionDir($asai: any, ns: LogNamespace = 'prod'): string {\r\n\tconst cfg = $asai?.hostconfig?.logger?.intervention || {};\r\n\tif (ns === 'test') return cfg.testPath || './webdata/webdb/log/intervention-test/';\r\n\treturn cfg.path || './webdata/webdb/log/intervention/';\r\n}\r\n\r\nfunction getRetentionYears($asai: any): number {\r\n\tconst y = $asai?.hostconfig?.logger?.intervention?.retentionYears;\r\n\treturn typeof y === 'number' && y > 0 ? y : 5;\r\n}\r\n\r\nfunction escHeader(v: unknown): string {\r\n\treturn String(v ?? '')\r\n\t\t.replace(/\\\\/g, '\\\\\\\\')\r\n\t\t.replace(/\\|/g, '\\\\|')\r\n\t\t.replace(/[\\r\\n]+/g, ' ');\r\n}\r\n\r\nfunction escExt(v: unknown): string {\r\n\treturn String(v ?? '')\r\n\t\t.replace(/\\\\/g, '\\\\\\\\')\r\n\t\t.replace(/=/g, '\\\\=')\r\n\t\t.replace(/[\\r\\n]+/g, ' ');\r\n}\r\n\r\nexport function sha256Hex(input: string): string {\r\n\treturn createHash('sha256').update(input, 'utf8').digest('hex');\r\n}\r\n\r\nconst CRC_TABLE: Uint32Array = (() => {\r\n\tconst table = new Uint32Array(256);\r\n\tfor (let n = 0; n < 256; n++) {\r\n\t\tlet c = n;\r\n\t\tfor (let k = 0; k < 8; k++) {\r\n\t\t\tc = c & 1 ? 0xedb88320 ^ (c >>> 1) : c >>> 1;\r\n\t\t}\r\n\t\ttable[n] = c >>> 0;\r\n\t}\r\n\treturn table;\r\n})();\r\n\r\n/** CRC32 标识计算 — 用于安全参数/配置变更的\"标识手段\"(不存储真实版本号) */\r\nexport function crc32(input: string): string {\r\n\tlet crc = 0xffffffff;\r\n\tconst buf = Buffer.from(input, 'utf8');\r\n\tfor (let i = 0; i < buf.length; i++) {\r\n\t\tcrc = CRC_TABLE[(crc ^ buf[i]) & 0xff] ^ (crc >>> 8);\r\n\t}\r\n\tcrc = (crc ^ 0xffffffff) >>> 0;\r\n\treturn crc.toString(16).padStart(8, '0');\r\n}\r\n\r\ninterface ChainState {\r\n\t/** 全局最新哈希 — 仅用于给\"新文件\"生成创建锚点,不直接参与任何单个文件的链式计算 */\r\n\tlastHash: string;\r\n\trunningCounter: number;\r\n\tbootCounter: number;\r\n\t/** 每个文件创建时刻的锚点(该文件第一条记录的 prevHash) */\r\n\tfileAnchors: Record<string, string>;\r\n\t/**\r\n\t * 每个文件\"当前链尾哈希\",按文件独立维护、独立递增。\r\n\t * 关键点:同一目录下可能存在多个文件交替写入(如内容文件与删除审计文件),\r\n\t * 若所有文件共用同一个全局 prevHash,其他文件的穿插写入会打断本文件的链式重放,\r\n\t * 导致 verifyChainForFile 对着一份完全没被篡改的文件也报\"校验失败\"(误报)。\r\n\t * 因此每个文件的下一条记录必须以\"这个文件自己上一条记录的哈希\"为 prevHash,\r\n\t * 不受目录内其他文件并发写入的影响,链条本身仍然对该文件内的任何删改保持完全敏感。\r\n\t */\r\n\tfileTip: Record<string, string>;\r\n}\r\n\r\n/** 状态/写队列按目录(即按命名空间)隔离缓存,确保 prod / test 互不干扰 */\r\nconst cachedStateByDir = new Map<string, ChainState>();\r\nconst bootHandledDirs = new Set<string>();\r\n\r\nfunction statePath($asai: any, ns: LogNamespace): string {\r\n\treturn path.join(getInterventionDir($asai, ns), '.chain-state.json');\r\n}\r\n\r\nasync function loadState($asai: any, ns: LogNamespace): Promise<ChainState> {\r\n\tconst dir = getInterventionDir($asai, ns);\r\n\tconst cached = cachedStateByDir.get(dir);\r\n\tif (cached) return cached;\r\n\tawait fsp.mkdir(dir, { recursive: true });\r\n\tlet state: ChainState = { lastHash: 'GENESIS', runningCounter: 0, bootCounter: 0, fileAnchors: {}, fileTip: {} };\r\n\ttry {\r\n\t\tconst raw = await fsp.readFile(statePath($asai, ns), 'utf8');\r\n\t\tconst loaded = JSON.parse(raw);\r\n\t\tstate = { ...state, ...loaded, fileAnchors: loaded.fileAnchors || {}, fileTip: loaded.fileTip || {} };\r\n\t} catch {\r\n\t\t/* 首次运行,使用初始状态 */\r\n\t}\r\n\tif (!bootHandledDirs.has(dir)) {\r\n\t\tstate.bootCounter += 1;\r\n\t\tbootHandledDirs.add(dir);\r\n\t\tawait fsp.writeFile(statePath($asai, ns), JSON.stringify(state), 'utf8');\r\n\t}\r\n\tcachedStateByDir.set(dir, state);\r\n\treturn state;\r\n}\r\n\r\nasync function saveState($asai: any, ns: LogNamespace, state: ChainState): Promise<void> {\r\n\tawait fsp.writeFile(statePath($asai, ns), JSON.stringify(state), 'utf8');\r\n\tcachedStateByDir.set(getInterventionDir($asai, ns), state);\r\n}\r\n\r\n/** 每个命名空间目录各自串行化写入,避免并发请求下运行计数/哈希链错序 */\r\nconst writeQueueByDir = new Map<string, Promise<void>>();\r\n\r\nasync function doLogIntervention(\r\n\t$asai: any,\r\n\tevent: InterventionEvent,\r\n\tns: LogNamespace,\r\n): Promise<{ line: string; file: string }> {\r\n\tconst state = await loadState($asai, ns);\r\n\tstate.runningCounter += 1;\r\n\r\n\tconst category = event.category || DEFAULT_CATEGORY[event.type];\r\n\tconst severity = event.severity ?? DEFAULT_SEVERITY[event.type] ?? 7;\r\n\tconst sigId = SIGNATURE_ID[event.type];\r\n\tconst nowIso = new Date().toISOString();\r\n\r\n\tconst ext: string[] = [];\r\n\text.push(`rt=${escExt(nowIso)}`);\r\n\tif (event.src) ext.push(`src=${escExt(event.src)}`);\r\n\tif (event.dst) ext.push(`dst=${escExt(event.dst)}`);\r\n\text.push(`proto=${escExt(event.proto || 'HTTPS')}`);\r\n\text.push(`cs1=${escExt(CATEGORY_GUIDE[category].en)}`);\r\n\text.push('cs1Label=EventCategory');\r\n\text.push(`cs2=${escExt(event.type)}`);\r\n\text.push('cs2Label=EventType');\r\n\tif (event.identification) {\r\n\t\text.push(`cs3=${escExt(event.identification)}`);\r\n\t\text.push('cs3Label=Identification');\r\n\t}\r\n\text.push(`cn1=${state.bootCounter}`);\r\n\text.push('cn1Label=BootCounter');\r\n\text.push(`cn2=${state.runningCounter}`);\r\n\text.push('cn2Label=RunningCounter');\r\n\text.push(`cn3=${Math.round(process.uptime() * 1000)}`);\r\n\text.push('cn3Label=UptimeMs');\r\n\tif (event.us) ext.push(`suser=${escExt(event.us)}`);\r\n\text.push(`outcome=${escExt(event.outcome || 'Success')}`);\r\n\tif (event.detail) ext.push(`msg=${escExt(event.detail)}`);\r\n\tif (event.fname) ext.push(`fname=${escExt(event.fname)}`);\r\n\r\n\tconst header = [\r\n\t\t'CEF:0',\r\n\t\tescHeader($asai?.hostconfig?.website?.title || 'AsaiCMS'),\r\n\t\tescHeader('AsaiHost'),\r\n\t\tescHeader($asai?.hostconfig?.website?.ver || '1.0.0.0'),\r\n\t\tescHeader(sigId),\r\n\t\tescHeader(event.name),\r\n\t\tString(severity),\r\n\t].join('|');\r\n\r\n\tconst bodyLine = `${header}|${ext.join(' ')}`;\r\n\tconst dir = getInterventionDir($asai, ns);\r\n\tconst fileName = event.type === 'LOG_DELETE' ? DELETION_AUDIT_FILE : `intervention-${getNowTime(2)}.cef.log`;\r\n\r\n\tif (!state.fileAnchors[fileName]) {\r\n\t\tstate.fileAnchors[fileName] = state.lastHash;\r\n\t}\r\n\tconst prevHashForFile = state.fileTip[fileName] ?? state.fileAnchors[fileName];\r\n\r\n\tconst chainHash = sha256Hex(`${prevHashForFile}|${bodyLine}`);\r\n\tconst fullLine = `${bodyLine} cs4=${chainHash} cs4Label=ChainHash\\n`;\r\n\r\n\tconst filePath = path.join(dir, fileName);\r\n\tawait fsp.mkdir(dir, { recursive: true });\r\n\tawait fsp.appendFile(filePath, fullLine, 'utf8');\r\n\r\n\tstate.fileTip[fileName] = chainHash;\r\n\tstate.lastHash = chainHash;\r\n\tawait saveState($asai, ns, state);\r\n\r\n\tvoid mirrorInterventionLog($asai, {\r\n\t\tns,\r\n\t\tfileName,\r\n\t\tevent,\r\n\t\trawLine: fullLine,\r\n\t\tchainHash,\r\n\t\tprevHash: prevHashForFile,\r\n\t\tcategory,\r\n\t\tseverity,\r\n\t}).catch(() => undefined);\r\n\r\n\t($asai?.$log || console.log)('INTERVENTION', `[${ns}]`, event.type, sigId, event.outcome || 'Success');\r\n\r\n\treturn { line: fullLine, file: fileName };\r\n}\r\n\r\n/**\r\n * 记录一条干预日志(IEC 62443-4-2 强制项)。\r\n * 仅应由服务端业务逻辑在真实干预发生时自动调用,禁止暴露\"任意写入\"接口给客户端。\r\n * ns 默认 'prod'(受5年留存保护的生产日志);演示/自动化测试触发的动作必须显式传入 'test',\r\n * 使其落入完全隔离、不计入合规留存的测试命名空间,避免测试足迹污染生产审计证据。\r\n */\r\nexport function logIntervention(\r\n\t$asai: any,\r\n\tevent: InterventionEvent,\r\n\tns: LogNamespace = 'prod',\r\n): Promise<{ line: string; file: string }> {\r\n\tconst dir = getInterventionDir($asai, ns);\r\n\tconst prevQueue = writeQueueByDir.get(dir) || Promise.resolve();\r\n\tconst task = prevQueue.then(() => doLogIntervention($asai, event, ns));\r\n\twriteQueueByDir.set(\r\n\t\tdir,\r\n\t\ttask.then(\r\n\t\t\t() => undefined,\r\n\t\t\t() => undefined,\r\n\t\t),\r\n\t);\r\n\treturn task;\r\n}\r\n\r\nfunction parseDateFromFileName(fileName: string): Date | null {\r\n\tconst m = fileName.match(/intervention-(\\d{4})-(\\d{2})-(\\d{2})\\.cef\\.log$/);\r\n\tif (!m) return null;\r\n\treturn new Date(Number(m[1]), Number(m[2]) - 1, Number(m[3]));\r\n}\r\n\r\nexport interface RetentionMeta {\r\n\tfilePath: string;\r\n\tageDays: number;\r\n\tretentionDays: number;\r\n\tretentionYears: number;\r\n\texpired: boolean;\r\n}\r\n\r\nexport function getRetentionMeta($asai: any, fileName: string, ns: LogNamespace = 'prod'): RetentionMeta {\r\n\tconst dir = getInterventionDir($asai, ns);\r\n\tconst filePath = path.join(dir, fileName);\r\n\tconst fileDate = parseDateFromFileName(fileName) || new Date(0);\r\n\tconst ageDays = Math.floor((Date.now() - fileDate.getTime()) / 86400000);\r\n\tconst retentionYears = getRetentionYears($asai);\r\n\tconst retentionDays = Math.round(retentionYears * 365.25);\r\n\treturn { filePath, ageDays, retentionDays, retentionYears, expired: ageDays >= retentionDays };\r\n}\r\n\r\nexport async function listInterventionFiles($asai: any, ns: LogNamespace = 'prod') {\r\n\tconst dir = getInterventionDir($asai, ns);\r\n\tawait fsp.mkdir(dir, { recursive: true });\r\n\tconst entries = await fsp.readdir(dir, { withFileTypes: true });\r\n\tconst files = entries.filter((e) => e.isFile() && (FILE_NAME_RE.test(e.name) || e.name === DELETION_AUDIT_FILE));\r\n\tconst list = await Promise.all(\r\n\t\tfiles.map(async (e) => {\r\n\t\t\tconst isAuditFile = e.name === DELETION_AUDIT_FILE;\r\n\t\t\tconst filePath = path.join(dir, e.name);\r\n\t\t\tconst stat = await fsp.stat(filePath);\r\n\t\t\tconst meta = isAuditFile\r\n\t\t\t\t? { ageDays: 0, retentionDays: 0, retentionYears: getRetentionYears($asai), expired: false }\r\n\t\t\t\t: getRetentionMeta($asai, e.name, ns);\r\n\t\t\tlet entryCount = 0;\r\n\t\t\ttry {\r\n\t\t\t\tconst content = await fsp.readFile(filePath, 'utf8');\r\n\t\t\t\tentryCount = content.split('\\n').filter((l) => l.trim().startsWith('CEF:')).length;\r\n\t\t\t} catch {\r\n\t\t\t\t/* 忽略读取失败,entryCount 保持 0 */\r\n\t\t\t}\r\n\t\t\treturn {\r\n\t\t\t\tname: e.name,\r\n\t\t\t\tns,\r\n\t\t\t\tsize: stat.size,\r\n\t\t\t\tmtime: stat.mtime.toISOString(),\r\n\t\t\t\tentryCount,\r\n\t\t\t\tageDays: meta.ageDays,\r\n\t\t\t\tretentionDays: meta.retentionDays,\r\n\t\t\t\tretentionYears: meta.retentionYears,\r\n\t\t\t\texpired: meta.expired,\r\n\t\t\t\tprotectedAudit: isAuditFile,\r\n\t\t\t};\r\n\t\t}),\r\n\t);\r\n\tlist.sort((a, b) => (a.name < b.name ? 1 : -1));\r\n\treturn list;\r\n}\r\n\r\n/** 手动扫描 CEF 头部(Version|Vendor|Product|DeviceVersion|SignatureID|Name|Severity),避免转义竖线干扰扩展字段解析 */\r\nfunction splitCefHeader(line: string): { header: string[]; extensionStr: string } | null {\r\n\tif (!line.startsWith('CEF:')) return null;\r\n\tconst header: string[] = [];\r\n\tlet cur = '';\r\n\tlet i = 4;\r\n\tlet count = 0;\r\n\twhile (i < line.length && count < 7) {\r\n\t\tconst ch = line[i];\r\n\t\tif (ch === '\\\\' && i + 1 < line.length) {\r\n\t\t\tcur += line[i + 1];\r\n\t\t\ti += 2;\r\n\t\t\tcontinue;\r\n\t\t}\r\n\t\tif (ch === '|') {\r\n\t\t\theader.push(cur);\r\n\t\t\tcur = '';\r\n\t\t\tcount++;\r\n\t\t\ti++;\r\n\t\t\tcontinue;\r\n\t\t}\r\n\t\tcur += ch;\r\n\t\ti++;\r\n\t}\r\n\tif (count < 7) return null;\r\n\treturn { header, extensionStr: line.slice(i) };\r\n}\r\n\r\nfunction parseExtension(extStr: string): Record<string, string> {\r\n\tconst extension: Record<string, string> = {};\r\n\tconst re = /([A-Za-z0-9]+)=((?:\\\\.|[^\\\\])*?)(?=\\s+[A-Za-z0-9]+=|$)/g;\r\n\tlet m: RegExpExecArray | null;\r\n\twhile ((m = re.exec(extStr))) {\r\n\t\textension[m[1]] = m[2].replace(/\\\\=/g, '=').replace(/\\\\\\\\/g, '\\\\').trim();\r\n\t}\r\n\treturn extension;\r\n}\r\n\r\nexport interface ParsedCefLine {\r\n\tlineNo: number;\r\n\tvalid: boolean;\r\n\traw: string;\r\n\tcefVersion?: string;\r\n\tvendor?: string;\r\n\tproduct?: string;\r\n\tversion?: string;\r\n\tsignatureId?: string;\r\n\tname?: string;\r\n\tseverity?: number;\r\n\tcategory?: string;\r\n\teventType?: string;\r\n\tidentification?: string;\r\n\tbootCounter?: string;\r\n\trunningCounter?: string;\r\n\tuptimeMs?: string;\r\n\toperator?: string;\r\n\toutcome?: string;\r\n\tdetail?: string;\r\n\ttimestamp?: string;\r\n\tchainHash?: string;\r\n}\r\n\r\nexport function parseCefLine(line: string, lineNo = 0): ParsedCefLine {\r\n\tconst split = splitCefHeader(line);\r\n\tif (!split) return { lineNo, valid: false, raw: line };\r\n\tconst [cefVersion, vendor, product, version, signatureId, name, severity] = split.header;\r\n\tconst ext = parseExtension(split.extensionStr);\r\n\treturn {\r\n\t\tlineNo,\r\n\t\tvalid: true,\r\n\t\traw: line,\r\n\t\tcefVersion,\r\n\t\tvendor,\r\n\t\tproduct,\r\n\t\tversion,\r\n\t\tsignatureId,\r\n\t\tname,\r\n\t\tseverity: Number(severity),\r\n\t\tcategory: ext.cs1,\r\n\t\teventType: ext.cs2,\r\n\t\tidentification: ext.cs3,\r\n\t\tbootCounter: ext.cn1,\r\n\t\trunningCounter: ext.cn2,\r\n\t\tuptimeMs: ext.cn3,\r\n\t\toperator: ext.suser,\r\n\t\toutcome: ext.outcome,\r\n\t\tdetail: ext.msg,\r\n\t\ttimestamp: ext.rt,\r\n\t\tchainHash: ext.cs4,\r\n\t};\r\n}\r\n\r\nexport interface ChainVerifyResult {\r\n\tok: boolean;\r\n\tresults: { line: number; ok: boolean; expected?: string; found?: string }[];\r\n}\r\n\r\n/** 依据文件锚点哈希重放整条链,任意历史记录被删改都会导致自该行起全部校验失败 */\r\nexport async function verifyChainForFile(\r\n\t$asai: any,\r\n\tfileName: string,\r\n\tlines: string[],\r\n\tns: LogNamespace = 'prod',\r\n): Promise<ChainVerifyResult> {\r\n\tconst state = await loadState($asai, ns);\r\n\tlet prevHash = state.fileAnchors?.[fileName] ?? 'GENESIS';\r\n\tconst results: ChainVerifyResult['results'] = [];\r\n\tlet lineNo = 0;\r\n\tfor (const raw of lines) {\r\n\t\tlineNo++;\r\n\t\tif (!raw.trim()) continue;\r\n\t\tconst m = raw.match(/\\bcs4=([0-9a-f]{64})\\b/);\r\n\t\tconst found = m ? m[1] : '';\r\n\t\tconst bodyLine = raw.replace(/\\s+cs4=[0-9a-f]{64}\\s+cs4Label=ChainHash\\s*$/, '');\r\n\t\tconst expected = sha256Hex(`${prevHash}|${bodyLine}`);\r\n\t\tconst ok = !!found && found === expected;\r\n\t\tresults.push({ line: lineNo, ok, expected, found });\r\n\t\tprevHash = found || expected;\r\n\t}\r\n\treturn { ok: results.every((r) => r.ok), results };\r\n}\r\n\r\nexport interface InterventionFileContent {\r\n\tfileName: string;\r\n\traw: string;\r\n\tparsed: ParsedCefLine[];\r\n\tchain: ChainVerifyResult;\r\n\tmeta: RetentionMeta;\r\n}\r\n\r\nexport async function readInterventionFile(\r\n\t$asai: any,\r\n\tfileName: string,\r\n\tns: LogNamespace = 'prod',\r\n): Promise<InterventionFileContent> {\r\n\tif (!FILE_NAME_RE.test(fileName) && fileName !== DELETION_AUDIT_FILE) throw new Error('Invalid file name');\r\n\tconst dir = getInterventionDir($asai, ns);\r\n\tconst filePath = path.join(dir, fileName);\r\n\tconst raw = await fsp.readFile(filePath, 'utf8');\r\n\tconst lines = raw.split('\\n').filter((l) => l.trim().length > 0);\r\n\tconst parsed = lines.map((l, idx) => parseCefLine(l, idx + 1));\r\n\tconst chain = await verifyChainForFile($asai, fileName, lines, ns);\r\n\tif (!chain.ok) {\r\n\t\tconst { maybeAlertChainBreak } = await import('../../../infra/log-alert');\r\n\t\tmaybeAlertChainBreak($asai, fileName, false, ns);\r\n\t}\r\n\tconst meta =\r\n\t\tfileName === DELETION_AUDIT_FILE\r\n\t\t\t? { filePath, ageDays: 0, retentionDays: 0, retentionYears: getRetentionYears($asai), expired: false }\r\n\t\t\t: getRetentionMeta($asai, fileName, ns);\r\n\treturn { fileName, raw, parsed, chain, meta };\r\n}\r\n\r\nexport interface DeleteOptions {\r\n\tus?: string;\r\n\tlv?: number;\r\n\treason?: string;\r\n\tforce?: boolean;\r\n}\r\n\r\n/**\r\n * 删除干预日志文件 — 留存期内(默认5年)仅允许 lv≥3 且提供 reason + force 的强制覆盖;\r\n * 无论是否放行,删除动作本身都会作为 LOG_DELETE 事件被记录(标准强制要求项)。\r\n */\r\nexport async function deleteInterventionFile(\r\n\t$asai: any,\r\n\tfileName: string,\r\n\topt: DeleteOptions = {},\r\n\tns: LogNamespace = 'prod',\r\n) {\r\n\tif (!FILE_NAME_RE.test(fileName)) throw new Error('Invalid file name');\r\n\tconst meta = getRetentionMeta($asai, fileName, ns);\r\n\tconst lv = opt.lv ?? -1;\r\n\r\n\tlet allowed = false;\r\n\tlet reasonCode = '';\r\n\tif (meta.expired) {\r\n\t\tallowed = lv >= 2;\r\n\t\treasonCode = allowed ? '' : 'INSUFFICIENT_LEVEL';\r\n\t} else if (!opt.force) {\r\n\t\treasonCode = 'RETENTION_NOT_EXPIRED';\r\n\t} else if (lv < 3) {\r\n\t\treasonCode = 'INSUFFICIENT_LEVEL';\r\n\t} else if (!opt.reason) {\r\n\t\treasonCode = 'REASON_REQUIRED';\r\n\t} else {\r\n\t\tallowed = true;\r\n\t}\r\n\r\n\tawait logIntervention(\r\n\t\t$asai,\r\n\t\t{\r\n\t\t\ttype: 'LOG_DELETE',\r\n\t\t\tname: `Delete intervention log file: ${fileName}`,\r\n\t\t\tus: opt.us || 'system',\r\n\t\t\toutcome: allowed ? 'Success' : 'Failure',\r\n\t\t\tidentification: fileName,\r\n\t\t\tseverity: allowed ? 7 : 8,\r\n\t\t\tdetail: `${allowed ? 'deleted' : 'denied'} reason=\"${opt.reason || ''}\" ageDays=${meta.ageDays} retentionDays=${meta.retentionDays} force=${!!opt.force} code=${reasonCode}`,\r\n\t\t},\r\n\t\tns,\r\n\t);\r\n\r\n\tif (!allowed) {\r\n\t\tconst err: any = new Error(reasonCode || 'DELETE_DENIED');\r\n\t\tthrow err;\r\n\t}\r\n\tawait fsp.unlink(meta.filePath);\r\n\tvoid purgeSqliteEntriesForFile($asai, fileName, ns).catch(() => undefined);\r\n\t/**\r\n\t * 物理内容已被删除(该删除动作已通过上面的 LOG_DELETE 写入不可删的审计文件),\r\n\t * 若同名文件之后被重新创建(如当日再次触发同类型事件),必须视为一份全新文件从头计链,\r\n\t * 而不是继续沿用已被删除内容的旧链尾/旧锚点——否则新文件的第一行会因为 prevHash\r\n\t * 对不上\"重新计算出的锚点\"而被误判为篡改。\r\n\t */\r\n\tconst state = await loadState($asai, ns);\r\n\tdelete state.fileAnchors[fileName];\r\n\tdelete state.fileTip[fileName];\r\n\tawait saveState($asai, ns, state);\r\n\treturn { deleted: true, fileName };\r\n}\r\n\r\nexport function getInterventionTaxonomy($asai?: any) {\r\n\treturn {\r\n\t\tformats: getLogFormatTaxonomy($asai).formats,\r\n\t\ttypes: (Object.keys(SIGNATURE_ID) as InterventionType[]).map((type) => ({\r\n\t\t\ttype,\r\n\t\t\tsignatureId: SIGNATURE_ID[type],\r\n\t\t\tcategory: DEFAULT_CATEGORY[type],\r\n\t\t\tdefaultSeverity: DEFAULT_SEVERITY[type],\r\n\t\t})),\r\n\t\tcategories: (Object.keys(CATEGORY_GUIDE) as InterventionCategory[]).map((key) => ({\r\n\t\t\tkey,\r\n\t\t\t...CATEGORY_GUIDE[key],\r\n\t\t})),\r\n\t\tretentionYears: 5,\r\n\t\texceptions: [\r\n\t\t\t'未改变安全参数/配置/软件/HMI 危险参数/安全指令显示软件的干预无需记录(如常规鉴权成功/失败)',\r\n\t\t\t'触发机器安全状态的动作(如安全光幕开启)不在记录范围内',\r\n\t\t\t'无需在日志中存储 SRASW/SRESW 二进制文件的真实版本号,使用 CRC/哈希等标识手段即可',\r\n\t\t],\r\n\t};\r\n}\r\n"],"mappings":"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","names":[]}
|
|
@@ -0,0 +1,105 @@
|
|
|
1
|
+
"use strict";Object.defineProperty(exports, "__esModule", {value: true}); function _nullishCoalesce(lhs, rhsFn) { if (lhs != null) { return lhs; } else { return rhsFn(); } }
|
|
2
|
+
|
|
3
|
+
|
|
4
|
+
var _chunkG4WVDUBHcjs = require('./chunk-G4WVDUBH.cjs');
|
|
5
|
+
|
|
6
|
+
|
|
7
|
+
|
|
8
|
+
var _chunkSMVZ3ZDJcjs = require('./chunk-SMVZ3ZDJ.cjs');
|
|
9
|
+
|
|
10
|
+
// src/sysserver/lib/common/intervention-hooks.ts
|
|
11
|
+
var intervention_hooks_exports = {};
|
|
12
|
+
_chunkSMVZ3ZDJcjs.__export.call(void 0, intervention_hooks_exports, {
|
|
13
|
+
logAccountPurge: () => logAccountPurge,
|
|
14
|
+
logProcessGuardEvent: () => logProcessGuardEvent,
|
|
15
|
+
logSecurityConfigIntervention: () => logSecurityConfigIntervention,
|
|
16
|
+
logSessionTerminate: () => logSessionTerminate,
|
|
17
|
+
logUserRbacChange: () => logUserRbacChange
|
|
18
|
+
});
|
|
19
|
+
async function logUserRbacChange($asai, opts) {
|
|
20
|
+
const identification = _chunkG4WVDUBHcjs.crc32.call(void 0, JSON.stringify({ us: opts.targetUs, ...opts.patch }));
|
|
21
|
+
return _chunkG4WVDUBHcjs.logIntervention.call(void 0, $asai, {
|
|
22
|
+
type: "SAFETY_PARAM",
|
|
23
|
+
name: `User RBAC changed: ${opts.targetUs}`,
|
|
24
|
+
category: "ConfigurationChanges",
|
|
25
|
+
severity: 8,
|
|
26
|
+
us: opts.operator,
|
|
27
|
+
src: opts.ip,
|
|
28
|
+
identification,
|
|
29
|
+
fname: `user.rbac.${opts.targetUs}`,
|
|
30
|
+
detail: JSON.stringify(opts.patch),
|
|
31
|
+
outcome: "Success"
|
|
32
|
+
});
|
|
33
|
+
}
|
|
34
|
+
_chunkSMVZ3ZDJcjs.__name.call(void 0, logUserRbacChange, "logUserRbacChange");
|
|
35
|
+
async function logProcessGuardEvent($asai, opts) {
|
|
36
|
+
const identification = _chunkG4WVDUBHcjs.crc32.call(void 0, `${opts.action}|${opts.detail || ""}|${Date.now()}`);
|
|
37
|
+
return _chunkG4WVDUBHcjs.logIntervention.call(void 0, $asai, {
|
|
38
|
+
type: "PROCESS_GUARD",
|
|
39
|
+
name: `Process guard: ${opts.action}`,
|
|
40
|
+
category: "ControlSystemEvents",
|
|
41
|
+
severity: _nullishCoalesce(opts.severity, () => ( 9)),
|
|
42
|
+
identification,
|
|
43
|
+
detail: opts.detail,
|
|
44
|
+
outcome: opts.outcome || "Success"
|
|
45
|
+
});
|
|
46
|
+
}
|
|
47
|
+
_chunkSMVZ3ZDJcjs.__name.call(void 0, logProcessGuardEvent, "logProcessGuardEvent");
|
|
48
|
+
async function logSecurityConfigIntervention($asai, opts) {
|
|
49
|
+
const identification = _chunkG4WVDUBHcjs.crc32.call(void 0, `${opts.section}|${opts.detail}`);
|
|
50
|
+
return _chunkG4WVDUBHcjs.logIntervention.call(void 0, $asai, {
|
|
51
|
+
type: "SAFETY_PARAM",
|
|
52
|
+
name: `Security config: ${opts.section}`,
|
|
53
|
+
category: "ConfigurationChanges",
|
|
54
|
+
severity: 7,
|
|
55
|
+
us: opts.operator || "system",
|
|
56
|
+
src: opts.ip,
|
|
57
|
+
identification,
|
|
58
|
+
fname: `security.${opts.section}`,
|
|
59
|
+
detail: opts.detail,
|
|
60
|
+
outcome: "Success"
|
|
61
|
+
});
|
|
62
|
+
}
|
|
63
|
+
_chunkSMVZ3ZDJcjs.__name.call(void 0, logSecurityConfigIntervention, "logSecurityConfigIntervention");
|
|
64
|
+
async function logSessionTerminate($asai, opts) {
|
|
65
|
+
const identification = _chunkG4WVDUBHcjs.crc32.call(void 0, `${opts.sessionId}|${opts.targetUs || ""}`);
|
|
66
|
+
return _chunkG4WVDUBHcjs.logIntervention.call(void 0, $asai, {
|
|
67
|
+
type: "SAFETY_PARAM",
|
|
68
|
+
name: `Session terminated: ${opts.sessionId}`,
|
|
69
|
+
category: "AccessControl",
|
|
70
|
+
severity: 8,
|
|
71
|
+
us: opts.operator,
|
|
72
|
+
src: opts.ip,
|
|
73
|
+
identification,
|
|
74
|
+
fname: `session.kick.${opts.sessionId}`,
|
|
75
|
+
detail: opts.targetUs ? `target=${opts.targetUs}` : void 0,
|
|
76
|
+
outcome: "Success"
|
|
77
|
+
});
|
|
78
|
+
}
|
|
79
|
+
_chunkSMVZ3ZDJcjs.__name.call(void 0, logSessionTerminate, "logSessionTerminate");
|
|
80
|
+
async function logAccountPurge($asai, opts) {
|
|
81
|
+
const identification = _chunkG4WVDUBHcjs.crc32.call(void 0, `purge|${opts.targetUs}`);
|
|
82
|
+
return _chunkG4WVDUBHcjs.logIntervention.call(void 0, $asai, {
|
|
83
|
+
type: "SAFETY_PARAM",
|
|
84
|
+
name: `Account purged: ${opts.targetUs}`,
|
|
85
|
+
category: "ConfigurationChanges",
|
|
86
|
+
severity: 8,
|
|
87
|
+
us: opts.operator,
|
|
88
|
+
src: opts.ip,
|
|
89
|
+
identification,
|
|
90
|
+
fname: `user.purge.${opts.targetUs}`,
|
|
91
|
+
detail: `operator=${opts.operator}`,
|
|
92
|
+
outcome: "Success"
|
|
93
|
+
});
|
|
94
|
+
}
|
|
95
|
+
_chunkSMVZ3ZDJcjs.__name.call(void 0, logAccountPurge, "logAccountPurge");
|
|
96
|
+
|
|
97
|
+
|
|
98
|
+
|
|
99
|
+
|
|
100
|
+
|
|
101
|
+
|
|
102
|
+
|
|
103
|
+
|
|
104
|
+
exports.logUserRbacChange = logUserRbacChange; exports.logProcessGuardEvent = logProcessGuardEvent; exports.logSecurityConfigIntervention = logSecurityConfigIntervention; exports.logSessionTerminate = logSessionTerminate; exports.logAccountPurge = logAccountPurge; exports.intervention_hooks_exports = intervention_hooks_exports;
|
|
105
|
+
//# sourceMappingURL=chunk-NLBFIRDB.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["d:\\Web\\Git\\asaicms-v1\\webserver\\src\\plugs\\asaihost-nodejs\\dist\\chunk-NLBFIRDB.cjs"],"names":[],"mappings":"AAAA;AACE;AACA;AACF,wDAA6B;AAC7B;AACE;AACA;AACF,wDAA6B;AAC7B;AACA;AACA,IAAI,2BAA2B,EAAE,CAAC,CAAC;AACnC,wCAAQ,0BAA2B,EAAE;AACrC,EAAE,eAAe,EAAE,CAAC,EAAE,GAAG,eAAe;AACxC,EAAE,oBAAoB,EAAE,CAAC,EAAE,GAAG,oBAAoB;AAClD,EAAE,6BAA6B,EAAE,CAAC,EAAE,GAAG,6BAA6B;AACpE,EAAE,mBAAmB,EAAE,CAAC,EAAE,GAAG,mBAAmB;AAChD,EAAE,iBAAiB,EAAE,CAAC,EAAE,GAAG;AAC3B,CAAC,CAAC;AACF,MAAM,SAAS,iBAAiB,CAAC,KAAK,EAAE,IAAI,EAAE;AAC9C,EAAE,MAAM,eAAe,EAAE,qCAAK,IAAK,CAAC,SAAS,CAAC,EAAE,EAAE,EAAE,IAAI,CAAC,QAAQ,EAAE,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC;AACpF,EAAE,OAAO,+CAAe,KAAM,EAAE;AAChC,IAAI,IAAI,EAAE,cAAc;AACxB,IAAI,IAAI,EAAE,CAAC,mBAAmB,EAAE,IAAI,CAAC,QAAQ,CAAC,CAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,EAAA;AACA;AACA;AACA;AACA,EAAA;AACA,EAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,EAAA;AACA;AACA;AACA;AACA,EAAA;AACA,EAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,EAAA;AACA;AACA;AACA;AACA,EAAA;AACA,EAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,EAAA;AACA;AACA;AACA;AACA,EAAA;AACA,EAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,IAAA;AACA,EAAA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA","file":"D:\\Web\\Git\\asaicms-v1\\webserver\\src\\plugs\\asaihost-nodejs\\dist\\chunk-NLBFIRDB.cjs","sourcesContent":[null]}
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
"use strict";Object.defineProperty(exports, "__esModule", {value: true});
|
|
2
|
+
|
|
3
|
+
var _chunkSMVZ3ZDJcjs = require('./chunk-SMVZ3ZDJ.cjs');
|
|
4
|
+
|
|
5
|
+
// src/core/time.ts
|
|
6
|
+
function getNowTime(type = 0, date = null) {
|
|
7
|
+
try {
|
|
8
|
+
date = date || /* @__PURE__ */ new Date();
|
|
9
|
+
const year = date.getFullYear();
|
|
10
|
+
const month = String(date.getMonth() + 1).padStart(2, "0");
|
|
11
|
+
const day = String(date.getDate()).padStart(2, "0");
|
|
12
|
+
const hours = String(date.getHours()).padStart(2, "0");
|
|
13
|
+
const minutes = String(date.getMinutes()).padStart(2, "0");
|
|
14
|
+
const seconds = String(date.getSeconds()).padStart(2, "0");
|
|
15
|
+
const milliseconds = String(date.getMilliseconds()).padStart(3, "0");
|
|
16
|
+
switch (type) {
|
|
17
|
+
case 1:
|
|
18
|
+
return `${hours}:${minutes}:${seconds}`;
|
|
19
|
+
case 2:
|
|
20
|
+
return `${year}-${month}-${day}`;
|
|
21
|
+
case 3:
|
|
22
|
+
return `${hours}:${minutes}:${seconds}.${milliseconds}`;
|
|
23
|
+
case 4:
|
|
24
|
+
return `${year}-${month}-${day} ${hours}:${minutes}:${seconds}.${milliseconds}`;
|
|
25
|
+
case 5:
|
|
26
|
+
return `${hours}-${minutes}-${seconds}-${milliseconds}`;
|
|
27
|
+
default:
|
|
28
|
+
return `${year}-${month}-${day} ${hours}:${minutes}:${seconds}`;
|
|
29
|
+
}
|
|
30
|
+
} catch (err) {
|
|
31
|
+
console.error("Date formatting error:", err);
|
|
32
|
+
return "unknown-time";
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
_chunkSMVZ3ZDJcjs.__name.call(void 0, getNowTime, "getNowTime");
|
|
36
|
+
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
exports.getNowTime = getNowTime;
|
|
40
|
+
//# sourceMappingURL=chunk-O6LVLSNB.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["d:\\Web\\Git\\asaicms-v1\\webserver\\src\\plugs\\asaihost-nodejs\\dist\\chunk-O6LVLSNB.cjs"],"names":[],"mappings":"AAAA;AACE;AACF,wDAA6B;AAC7B;AACA;AACA,SAAS,UAAU,CAAC,KAAK,EAAE,CAAC,EAAE,KAAK,EAAE,IAAI,EAAE;AAC3C,EAAE,IAAI;AACN,IAAI,KAAK,EAAE,KAAK,mBAAmB,IAAI,IAAI,CAAC,CAAC;AAC7C,IAAI,MAAM,KAAK,EAAE,IAAI,CAAC,WAAW,CAAC,CAAC;AACnC,IAAI,MAAM,MAAM,EAAE,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,EAAE,GAAG,CAAC;AAC9D,IAAI,MAAM,IAAI,EAAE,MAAM,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,EAAE,GAAG,CAAC;AACvD,IAAI,MAAM,MAAM,EAAE,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,EAAE,GAAG,CAAC;AAC1D,IAAI,MAAM,QAAQ,EAAE,MAAM,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,EAAE,GAAG,CAAC;AAC9D,IAAI,MAAM,QAAQ,EAAE,MAAM,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,EAAE,GAAG,CAAC;AAC9D,IAAI,MAAM,aAAa,EAAE,MAAM,CAAC,IAAI,CAAC,eAAe,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,EAAE,GAAG,CAAC;AACxE,IAAI,OAAO,CAAC,IAAI,EAAE;AAClB,MAAM,KAAK,CAAC;AACZ,QAAQ,OAAO,CAAC,EAAA;AACA,MAAA;AACA,QAAA;AACA,MAAA;AACA,QAAA;AACA,MAAA;AACA,QAAA;AACA,MAAA;AACA,QAAA;AACA,MAAA;AACA,QAAA;AACA,IAAA;AACA,EAAA;AACA,IAAA;AACA,IAAA;AACA,EAAA;AACA;AACA;AACA;AACA;AACA;AACA","file":"D:\\Web\\Git\\asaicms-v1\\webserver\\src\\plugs\\asaihost-nodejs\\dist\\chunk-O6LVLSNB.cjs","sourcesContent":[null]}
|