4. 身份源接入工程
医院信息系统的身份数据从来不是集中生长的。HIS 里躺着职工工号与科室归属,HRP 掌握着人事编制与岗位变动,OA 承载着行政组织与审批角色,而 LDAP 或 AD 往往承担着统一认证的目录服务职责。这些系统各自建设、各自维护,字段命名、编码规则、组织层级甚至人员状态的定义都不一致。身份源接入工程要解决的,就是把这些异构数据源变成统一身份平台可以稳定消费的“权威数据流”。
先分清权威源与消费方
接入的第一步不是写代码,而是做数据主权划分。同一个属性可能出现在多个系统里,必须明确谁是权威源。例如“职工姓名”在 HRP 中是人事档案的法定记录,在 HIS 中可能只是建账号时的录入值;“科室”在 HRP 中对应成本核算单元,在 OA 中对应行政组织,在 HIS 中对应临床科室。如果不做权威源定义,同步时就会出现“后写覆盖先写”的随机结果。
一个可落地的做法是建立属性—权威源映射表。下面是一份示例,字段和取值属于教学假设,实际项目需按医院真实系统确认:
| 统一属性 | 权威源 | 示例字段 | 同步方向 |
|---|---|---|---|
| 职工唯一标识 | HRP | employee_no | HRP → 平台 |
| 姓名 | HRP | real_name | HRP → 平台 |
| 在职状态 | HRP | emp_status | HRP → 平台 |
| 登录账号 | AD/LDAP | sAMAccountName | AD → 平台 |
| 临床科室 | HIS | dept_code | HIS → 平台 |
| 行政组织 | OA | org_id | OA → 平台 |
这张表决定了后续所有同步任务的优先级和冲突处理策略。当 HRP 与 HIS 对同一属性都有值时,以权威源为准;非权威源只做补充,不覆盖。
异构协议与连接方式
不同身份源的接入协议差异很大,工程上要按源类型选择连接器:
- HIS:多数为 Oracle 或 SQL Server 数据库,通过 JDBC 只读账号拉取视图,避免直接查生产大表。建议由 HIS 厂商提供专用同步视图,字段稳定、权限可控。
- HRP:常见为数据库或 REST API。若有人事异动接口,优先走增量接口;否则按 last_update_time 做增量查询。
- OA:通常提供 REST/WebService,组织与人员接口分离,需要先同步组织树再同步人员归属。
- LDAP/AD:使用 LDAP 协议,通过 Base DN、Filter、Attribute 三要素定位用户。AD 还需注意分页查询(Paged Results)和 referral 处理。
以 AD 为例,一个典型的查询配置如下:
Base DN: OU=Hospital,DC=example,DC=com
Filter: (&(objectClass=user)(!(objectClass=computer))(employeeID=*))
Attributes: sAMAccountName, displayName, employeeID, department, userAccountControl
Page Size: 500
其中 userAccountControl 的位标志可以判断账号是否禁用,例如 514 表示禁用账号,512 表示正常账号。同步时不能只看“是否存在”,还要看“是否可用”。
同步链路与状态流转
身份同步不是一次性导入,而是一条持续运行的数据链路。每个源的数据经过抽取、字段映射、清洗校验、合并去重、写入平台,最终驱动账号生命周期。下图展示了多源接入到统一身份平台的核心链路与状态流转关系:
增量同步与水位线设计
全量同步只适合首次初始化。日常运行必须走增量,否则每天拉取数万条人员记录既浪费资源,也容易在业务高峰期造成源库压力。增量同步的核心是水位线(watermark):记录上一次成功同步的最大时间戳或最大自增 ID,下一次从该位置继续。
以 HRP 为例,假设人事异动表有 last_update_time 字段,同步任务每次执行时:
-- 读取上次水位线
SELECT watermark_value FROM sync_watermark WHERE source='HRP' AND table_name='employee';
-- 增量拉取
SELECT employee_no, real_name, dept_code, emp_status, last_update_time
FROM hrp_employee
WHERE last_update_time > :last_watermark
ORDER BY last_update_time ASC;
-- 同步成功后更新水位线
UPDATE sync_watermark SET watermark_value = :max_update_time
WHERE source='HRP' AND table_name='employee';
这里有一个容易踩的坑:如果源系统的时间戳精度只到秒,同一秒内多条变更可能被漏掉。稳妥做法是水位线回退一个安全窗口,例如每次从上次水位线减 5 秒开始拉取,再在平台侧按业务主键做幂等写入。幂等写入意味着同一条记录重复到达时,结果与只到达一次相同,通常通过“主键 + 版本号”或“主键 + 更新时间”比较实现。
字段映射与清洗规则
异构源接入最繁琐的部分是字段映射。HIS 的科室编码可能是 4 位数字,HRP 的科室编码可能是“DEPT_”前缀加 3 位数字,OA 的组织 ID 又是另一套 UUID。平台需要维护一张映射表,把各源编码统一到平台内部的组织编码。
清洗规则至少覆盖以下几类:
- 空值处理:HRP 中手机号为空时,不能直接写入平台必填字段,应进入待补全队列。
- 格式归一:身份证号统一去空格、转大写;日期统一为 yyyy-MM-dd HH:mm:ss。
- 枚举转换:HRP 的 emp_status 为 1/2/3,平台需要映射为 active/leave/retired。
- 去重合并:同一自然人在 HIS 和 HRP 中都有记录时,以工号为主键合并,避免生成两个账号。
冲突处理与人工兜底
多源同步不可能永远一致。当 HRP 显示某职工已离职,但 HIS 中该账号仍在活跃使用,平台不能简单禁用账号,因为可能影响临床业务。合理的策略是:先标记冲突,生成待处理工单,通知人事与信息科确认,确认后再执行停用。冲突记录应包含冲突属性、各源取值、发现时间、处理人和处理结果。
同步结果的可观测性
接入工程做完不等于稳定运行。每次同步任务都应输出可观测指标:拉取条数、新增条数、更新条数、跳过条数、失败条数、耗时、水位线位置。当失败条数超过阈值或连续多次同步无新增时,应触发告警。运维人员通过同步日志可以快速定位是源库连接问题、字段映射问题,还是平台写入冲突。
身份源接入工程的本质,是把医院里分散、异构、各自为政的人员数据,通过权威源定义、连接器适配、增量水位线、字段清洗和冲突兜底,变成统一身份平台可以持续信任的数据基础。只有这条链路稳定,后续的认证、授权、审计和租户治理才有可靠的前提。