linux运维中实现密码修改后自动通知,关键在于统一改密入口而非监听系统变更;推荐方案依次为:接管passwd命令的wrapper脚本、pam模块异步日志通知、自研web平台统一控制。

Linux 运维中实现“密码修改后自动通知用户绑定邮箱或企业微信”,关键不在于监听密码变更动作本身(系统无原生钩子),而在于在用户改密流程中主动嵌入通知逻辑。真实可行的路径是:统一收口密码修改入口 + 脚本化通知 + 与用户身份信息联动。以下是可落地的三类方案,按推荐度排序:
方案一:接管 passwd 命令,用 wrapper 脚本触发通知
这是最直接、可控性最强的方式,适用于集中管理、权限可控的环境(如跳板机、堡垒机或内部运维平台)。
- 重命名原
passwd:sudo mv /usr/bin/passwd /usr/bin/passwd.real - 新建 wrapper 脚本
/usr/bin/passwd(需 root 权限):#!/bin/bash # 获取当前操作用户(非 root 时为被修改者;root 执行时取 -u 参数) if [ "$EUID" -ne 0 ]; then TARGET_USER="$USER" else TARGET_USER=$(getopt -o u: --long user: -n 'passwd' -- "$@" 2>/dev/null | awk '/--user/ {print $2}') [ -z "$TARGET_USER" ] && TARGET_USER=$(whoami) fi <h1>执行真实 passwd</h1><p>/usr/bin/passwd.real "$@"</p><div class="aritcle_card flexRow artxards"> <div class="artcardd flexRow"> <a class="aritcle_card_img" rel="nofollow" href="/xiazai/skill3433" title="Linux Journey"><img src="https://img.php.cn/upload/skill/000/000/081/178955841494725.jpg" alt="Linux Journey" onerror="this.onerror='';this.src='/static/lhimages/moren/morentu.png'" ></a> <div class="aritcle_card_info flexColumn"> <a rel="nofollow" href="/xiazai/skill3433" title="Linux Journey" class="overflowclass">Linux Journey</a> <p class="overflowclass">当用户想学习Linux基础、命令行、文件系统等时,在LabEx查找并推荐免费的Linux Journey课程。</p> </div> <a rel="nofollow" href="/xiazai/skill3433" title="Linux Journey" class="aritcle_card_btn flexRow flexcenter"><b></b><span>下载</span> </a> </div> </div><h1>密码修改成功后,尝试获取该用户绑定的邮箱或企业微信 userid</h1><p>EMAIL=$(getent passwd "$TARGET_USER" 2>/dev/null | cut -d: -f5 | awk -F',' '{print $1}' | grep '@') USERID=$(awk -F':' -v u="$TARGET_USER" '$1==u {print $4}' /etc/userinfo.conf 2>/dev/null) # 需提前维护映射表</p><h1>发送通知(示例:邮件 + 企业微信)</h1><p>if [ -n "$EMAIL" ]; then echo "您的密码已于 $(date) 修改成功。" | mail -s "【系统通知】密码已更新" "$EMAIL" fi if [ -n "$USERID" ]; then</p><h1>调用企业微信 API(需提前获取 access_token 和 agentid)</h1><p>curl -s -X POST "<a href="https://www.php.cn/link/d5476e73177cf85134a8e5e73fe88cd3">https://www.php.cn/link/d5476e73177cf85134a8e5e73fe88cd3</a>" \ -H 'Content-Type: application/json' \ -d "{\"touser\":\"$USERID\",\"msgtype\":\"text\",\"agentid\":1000002,\"text\":{\"content\":\"✅ 密码修改成功\n时间:$(date)\n请妥善保管新密码。\"}}" fi </p> - 赋予执行权限:
sudo chmod +x /usr/bin/passwd - 注意:
getent passwd的 GECOS 字段(第5字段)常存邮箱;若未规范填写,需另建映射文件(如/etc/userinfo.conf)维护username:email:weixin_userid关系
方案二:结合 PAM 模块,在密码更新后写日志并异步通知
适合无法替换系统命令的生产环境,利用 PAM 的 pam_exec.so 在认证模块链末尾执行脚本,记录事件并交由后台服务处理。
- 编辑
/etc/pam.d/common-password(Debian/Ubuntu)或/etc/pam.d/system-auth(RHEL/CentOS),末尾添加:password [success=ok default=ignore] pam_exec.so /usr/local/bin/pam_notify.sh
-
/usr/local/bin/pam_notify.sh内容(仅响应密码变更,不响应登录):#!/bin/bash # 仅当密码实际被修改时触发(PAM_TYPE=password) [ "$PAM_TYPE" = "password" ] || exit 0 # 避免重复触发(例如多模块调用) [ -n "$PAM_USER" ] || exit 1 <h1>记录到专用日志,供轮询脚本消费</h1><p>logger -t pwd-change "User $PAM_USER changed password at $(date)" echo "$(date '+%Y-%m-%d %H:%M:%S') $PAM_USER" >> /var/log/pwd_change.log </p>
- 再配一个每分钟运行的 cron 脚本,读取
/var/log/pwd_change.log新增行,查用户信息并推送——避免阻塞认证流程
方案三:通过自研 Web 管理平台统一入口控制
面向终端用户自助改密场景(如内网门户),完全绕过命令行限制,是最安全、扩展性最好的方式。
- 用户在 Web 页面提交新密码,后端调用
chpasswd或usermod修改密码 - 修改成功后,从数据库或 LDAP 中查该用户的
mail属性或wechat_userid字段 - 同步调用邮件 SMTP 或企业微信机器人 API 发送结构化通知(含时间、IP、设备 UA 等上下文)
- 优势:可加二次验证、审计留痕、支持多通道降级(邮件失败自动切微信)、兼容移动端
不依赖系统级 hook,也不建议监听 /etc/shadow 变更(时间粒度粗、无法区分谁改的、易漏报)。核心是把“通知”作为密码修改流程的一个确定性环节,而不是事后补救。只要用户改密走的是你控制的路径,就能稳稳发出去。










