跳到主要内容

HMI 安全

Darra HMI 提供多层安全机制,覆盖用户认证、角色权限、屏幕锁定、审计日志、电子签名五个维度。WebHMI 默认启用认证,LocalHMI 可根据部署环境配置。

本文档聚焦 HMI 运行时的安全机制。PLC 级别的安全功能(如安全块、急停、双通道冗余)见 PLC 安全总览


用户认证 (RBAC)

认证架构

用户登录 (HMI 页面)


HmiAuthProvider (Service 端)

├── 密码验证 (bcrypt, 本地用户库)
├── LDAP/AD 验证 (企业域集成)
└── 双因素认证 (TOTP / U 盾) ← 可选


JWT Token (HttpOnly Cookie, 30 天)


HMI 页面请求 → 验证 Token → 授权访问

启用登录

HMIProjectDef 中启用:

{
"RequireAuth": true,
"AuthSettings": {
"SessionTimeout": 480,
"MaxLoginAttempts": 5,
"LockoutDuration": 15,
"MfaRequired": false,
"PasswordMinLength": 8,
"PasswordComplexity": "medium",
"LdapServer": "",
"LdapDomain": ""
}
}
参数默认值说明
SessionTimeout480会话超时(分钟),超时后自动登出
MaxLoginAttempts5连续登录失败次数上限
LockoutDuration15锁定时间(分钟)
MfaRequiredfalse是否强制双因素认证
PasswordMinLength8密码最小长度
PasswordComplexitymedium密码复杂度:low / medium / high

登录页面

HMI 自动提供登录页面(/login),使用 <darra-login-panel> 控件:

<darra-login-panel redirect-on-success="/"></darra-login-panel>

登录成功写入 Cookie darra-token(HttpOnly、Secure、SameSite=Strict),后续请求自动认证。

登录 API(脚本)

// 检查当前是否已登录
const isAuth = Darra.checkAuth()
// true | false

// 获取当前用户信息
const user = Darra.getUserInfo()
// { username: 'wang', role: 'engineer', displayName: '王工', permissions: [...] }

// 登出
Darra.logout()

角色与权限 (RBAC)

预定义角色

角色权限范围典型用户
viewer只读,查看变量、报警、趋势参观者、质量巡检
operator读写操作变量、确认报警、切换配方产线操作员
engineer修改配方、调整参数、更改 HMI 页面工艺工程师
admin所有权限,包括用户管理、审计查看车间主管、IT

权限门控控件

<!-- 仅 admin 可见 -->
<darra-permission-gate role="admin">
<darra-button var="M100.0">紧急停车</darra-button>
</darra-permission-gate>

<!-- 多个角色 -->
<darra-permission-gate role="admin,engineer">
<button @click="showEditDialog()">编辑参数</button>
</darra-permission-gate>

脚本权限检查

// 检查当前用户是否有指定权限
const canWrite = Darra.hasPermission('write')
const canManageUsers = Darra.hasPermission('user_manage')

// 根据权限控制 UI
if (!canWrite) {
document.getElementById('setpoint-input').disabled = true
}

权限粒度

权限标识说明默认拥有角色
read读取变量、报警所有角色
write写入变量operator / engineer / admin
alarm_ack确认报警operator / engineer / admin
recipe_activate激活配方operator / engineer / admin
recipe_edit编辑配方engineer / admin
recipe_import导入配方admin
recipe_export导出配方engineer / admin
user_manage管理用户admin
audit_view查看审计日志admin
hmi_edit编辑 HMI 页面engineer / admin
system_config修改系统配置admin
sign_offline电子签名确认operator / engineer / admin

屏幕锁定 (Screen Lock)

功能说明

HMI 长时间无人操作时自动锁定屏幕,防止误操作。锁定后需要输入密码才能解锁。

{
"ScreenLock": {
"Enabled": true,
"Timeout": 5,
"LockOnMinimize": false,
"LockOnSleep": true,
"ShowOperator": true
}
}
参数默认值说明
Enabledtrue启用屏幕锁定
Timeout5空闲超时(分钟)
LockOnMinimizefalse窗口最小化时锁定
LockOnSleeptrue系统休眠/唤醒时锁定
ShowOperatortrue锁屏界面是否显示当前操作员姓名

锁屏界面

锁屏后显示全屏覆盖层,显示当前操作员姓名、锁定时间,用户需输入密码解锁。

脚本操作

// 手动锁定
Darra.lockScreen()

// 解锁
Darra.unlockScreen(password)

// 重置空闲计时器
Darra.resetIdleTimer()

空闲超时提示

超时前 30 秒显示倒计时提示,操作员可点击"保持在线"重置计时器。超时后自动锁定。


操作审计日志

审计范围

所有影响生产安全的操作自动记录审计日志:

操作类别记录内容
登录/登出用户、时间、IP、结果(成功/失败)
变量写入用户、变量地址、写入值、原因
配方操作用户、配方名、操作(激活/修改/创建/删除)、新旧值
报警确认用户、报警 ID、确认时间、原因
系统配置变更用户、配置项、新旧值
用户管理管理员、操作类型、目标用户
电子签名用户、签名类型、关联操作、签名值

查看审计日志

// 获取最近 100 条审计日志
const logs = Darra.getAuditLogs({ limit: 100 })

// 按时间范围筛选
const todayLogs = Darra.getAuditLogs({
startTime: Date.now() - 86400000,
endTime: Date.now(),
category: 'write', // 只查看变量写入操作
user: 'wang' // 只查看特定用户
})

// 每条日志格式
// { id, time, user, category, action, detail, ip, signature }

审计日志 UI

<darra-audit-log
category="all"
limit="50"
show-filter="true"
show-export="true"
></darra-audit-log>

日志导出

// 导出为 CSV
Darra.exportAuditLogs({
startTime: Date.now() - 7 * 86400000,
format: 'csv'
})

审计日志文件位于 %AppData%/DarraPLC/audit/ 目录,按日期分文件,只增不删,不可修改


电子签名 (21 CFR Part 11)

适用场景

电子签名功能满足 FDA 21 CFR Part 11 合规要求,适用于医药、食品、生物制品等行业:

  • 配方变更需要电子签名确认
  • 关键参数修改需要电子签名
  • 批量记录需要电子签名
  • 审计追踪需要电子签名验证

启用电子签名

{
"ElectronicSignature": {
"Enabled": true,
"SignatureType": "username_password",
"RequireReason": true,
"RequireReview": true,
"SignatureTimeout": 30
}
}
参数默认值说明
Enabledfalse启用电子签名
SignatureTypeusername_password签名方式:username_password / mfa / biometric
RequireReasontrue是否强制填写签名原因
RequireReviewtrue是否需要第二人复核
SignatureTimeout30签名有效期(分钟),超时需重新签名

签名流程

操作触发签名请求


弹出签名对话框

┌───┴───┐
│ 用户名 │ (自动填充当前用户)
│ 密码 │ (需重新输入)
│ 原因 │ (必填,如"调整焊接参数")
│ 复核人 │ (可选,RequireReview=true 时显示)
└───┬───┘


验证用户名 + 密码


记录签名日志 (含签名值、时间、原因)


执行关联操作

签名 API

// 写入变量时要求电子签名
Darra.writeVariable('DB1.SetCurrent', 185.0, {
requireSignature: true,
reason: '工艺优化调整'
})

// 程式化签名
Darra.sign({
reason: '当前批次参数验证',
reviewer: 'li' // 复核人用户名(可选)
})

签名记录

每次电子签名生成一条不可篡改的签名记录,包含:

字段说明
签名值用户名 + 时间戳 + 操作内容的 HMAC 签名
签名人用户名 + 显示名
签名时间ISO 8601 格式,精确到毫秒
签名原因用户填写的签名原因
复核人第二人复核的用户名(如启用)
关联操作本次签名授权的具体操作
签名 Hash整条记录的 SHA-256,链式校验

安全事件处理

安全事件类型

事件级别触发条件自动响应
登录失败Warning单用户连续失败锁定账户 MaxLoginAttempts
暴力破解Critical多用户连续失败(总次数 > 20)临时封禁源 IP 30 分钟
越权访问Error访问无权限的页面/API记录审计日志 + 返回 403
会话异常WarningToken 在异地登录使旧 Token 失效
白名单写入拒绝Info尝试写入未在白名单的变量记录审计日志
外部认证失败ErrorLDAP/AD 服务器无响应降级到本地账户认证

安全事件监控

// 监听安全事件
Darra.on('securityEvent', (event) => {
// { type: 'login_fail', severity: 'warning', detail: { user: 'unknown', ip: '...' }, timestamp }
if (event.severity === 'critical') {
showSecurityAlert(event)
}
})

安全事件 API

// 获取最近的安全事件
const events = Darra.getSecurityEvents({
severity: 'error,critical',
startTime: Date.now() - 86400000,
limit: 50
})

// 清除已处理的安全事件
Darra.clearSecurityEvents({ before: Date.now() - 30 * 86400000 })

安全配置检查清单

项目建议是否强制
WebHMI 启用 RequireAuth强制
强密码策略长度 ≥ 8建议
会话超时480 分钟以内建议
登录失败锁定启用建议
屏幕锁定启用,超时 ≤ 10 分钟建议
写入白名单只包含必需的变量强制
审计日志启用建议
电子签名医药/食品行业启用行业合规
HTTPS 部署外网访问必须强制
密码定期更换90 天建议
双因素认证管理员启用建议

相关文档