武永建
(北京工业职业技术学院 图书馆,北京 100042)
从当前国际国内的新冠肺炎疫情发展情况来看,疫情防控将会是一项长期的、常态化的任务[1]。高校是一个人员集中,各种活动较多的场所,疫情防控任务更为严峻和突出[2]。根据卫生部门的要求,场所的人数控制是防控工作中的一个重要环节。
目前,高校广泛使用的校园一卡通通过共同的身份认证机制,实现了数据管理的集成与共享[3]。高校各楼宇的门禁系统以校园一卡通为基础数据,进行了同步与二次开发使用。楼宇门禁系统已经是校园各个场所的一个标配装置,但目前仅应用于人员的进出控制。在当前严峻的疫情防控形势下,可以充分利用门禁系统的后台数据,实时监测数据的变化,统计在场人员数量,以数据可视化形式在场所进出口大屏上展示[4],以引起进入人员的关注;同时设置警戒值,当人员数量达到警戒值后,以醒目信息发出警示,为疫情防控、部门协作提供辅助和决策支持,为学生的校园生活和自我防护提供服务指引。
笔者以北京工业职业技术学院图书馆为例,设计一个实时在馆人数显示预警平台,利用Socket.io实时通信技术,主动推送门禁进出动态数据,并以可视化数据直观的视角,协助管理人员限制图书馆人员流量过度集中,以达到疫情防控的目的。
无论是传统的刷卡、指纹门禁,还是识别技术更为先进的刷脸测温门禁,它们的工作原理大致为:门禁读取进入人员数据向服务器发出认证请求,服务器从数据库查询认证信息并返回给门禁通过与否的指令。具体流程如下:(1)门禁读取进入人员的数据,若是刷卡门禁,则读取卡片芯片存储的人员ID信息;若是指纹和人脸,则读取生物特征码,并向门禁服务器发送。(2)门禁服务器获取数据后查询门禁数据库。(3)从数据库人员信息表中读取权限标志,并返回给门禁,门禁根据权限标志给予进入人员通过与否的开门指令。(4)门禁服务器在返回给门禁指令的同时,会把人员的通行记录写入数据库的日志表中。
其中第4步是获取实时数据的关键环节,在该系统Web服务端实现中,通过获取门禁后台数据库访问权限,监视第4步中日志表数据变化,通过秒级轮询机制查询出最近门禁通过者信息,同时汇总进入人员数量,返回给前端,完成门禁实时数据的获取。
该系统采用B/S架构来满足大屏、PC和手机端的查询与展示,页面所需的数据需要Web服务器即时主动地推送到浏览器。
在B/S架构中,传统的浏览器通信方式是基于HTTP协议的请求/响应模式,在这种模式下,只能通过刷新浏览器来更新服务器端的数据。随着Web技术的不断发展,Ajax技术采用异步的方式能够更新页面部分区域,虽然不用刷新浏览器,但仍然需要客户端主动请求才能获取服务器应答的数据,而服务器端有数据变化后,无法通过推送方式主动告诉客户端数据的变化。
随着网络的发展和需求的变化,越来越多的应用场景需要以服务器端即时推送的通信方式把数据主动推送给浏览器。HTML5出现后,http补充了一个新的协议WebSocket,它实现了浏览器与服务器全双工(Full Duplex)通信,全双工通信允许数据在2个方向上同时(瞬时)传输,这种方式能更好地节省服务器资源和带宽并达到实时通信的目的。WebSocket协议虽然已获主流浏览器支持,但仍然可能有不兼容的情况。为此,Socket.io库将WebSocket,AJAX和其他的通信方式全部封装成了统一的通信接口,因而不用担心兼容问题,底层会自动选用最佳的通信方式,将服务端的数据主动推送给客户端。该平台采用Socket.io库推送门禁实时刷卡数据到浏览器,实现刷卡与刷卡者信息同步显示。
该平台基于图书馆门禁管理系统,在进出馆数据的基础上进行二次开发,通过充分挖掘这部分数据的实用价值,以实现图1所示的功能。
图1 平台功能
平台主要功能介绍如下:
(1)在馆人员数量实时显示。进出馆人员在门禁刷卡后,大屏界面上会实时更新在馆人员数量。当达到预警值时,背景会闪烁提示,提醒防疫值勤人员采取限流措施,限制人员过度集中。警戒值的设定与楼宇座位数相关,根据隔位入座的防控要求,一般为楼宇座位数的一半。
(2)进出馆人员信息实时显示。界面会显示最近出馆人员和进馆人员的信息,为充分保障个人隐私,学号、姓名中部分用‘*’号替代。
(3)在馆人员类型结构分析。以部门隶属关系为标准划分进出人员分组,掌握进馆人员的组成结构,作为防控分析的一个数据来源。
(4)进馆动态曲线图。采用时序数据可视化方案。随着时间的变化,动态曲线图显示以分钟为单位的在馆人员数量变动趋势,直观判断每天的入馆人数高峰,为防疫工作提供指引。
(5)手机端查询。以嵌入微信公众号菜单的方式,读者可用手机端查询图书馆目前人数与警戒值的差额,读者根据差额决定是否去图书馆。
由于多终端界面的实时查询和显示是该系统的一个显著需求,因此,该平台采用了B/S架构[5]。B/S架构在处理模式上大大简化了客户端,用户只需安装浏览器即可。另外随着Web相关技术的发展,特别是Chrome V8引擎的诞生[6],大大提高了JavaScript的执行效率,使得前端具备了更多的终端业务处理能力,B/S 架构具有了更广的应用范围。同时,因为客户端使用浏览器,在开发维护上更加便利,可以减少系统开发和维护的成本。
在该平台中,Web服务器程序定时查询数据库,返回的结果转为JSON格式,同时,服务器使用Socket.io与客户端建立实时通信通道,把上述JSON格式数据主动推送给建立连接的客户端。客户端得到数据后更新页面可视化组件。平台结构如图2所示。
图2 平台结构图
图书馆门禁采用上海盛卡恩公司的产品,后台采用sql server数据库,进出馆人员的每一次刷卡,门禁数据库就会写入1条记录到visit_status表,实时记录人员进出情况,如表1所示。另一张表icreader则保存了从校园一卡通同步过来的用户信息,如表2所示。
表1 visit_status表
表2 icreader表
汇总表1表2的查询结果,并把查询结果交给业务逻辑处理,然后把处理的数据传送给前端Web页面做可视化显示。
服务端程序采用轮询机制,每隔3 s向数据库发出查询,一旦数据表记录有写入,将查询出的最新数据封装成JSON格式,并以事件形式向每个客户端发出广播。客户端浏览器监听事件,获取广播的数据并更新到DOM视图。服务端轮询查询伪代码如下:
const POLLING_INTERVAL=3000
function pollingLoop(){
request.query('select * from test_user')
request.on('row', row => {
users.push(row);
})
request.on('done', result => {
if (connectionsArray.length) {
pollingTimer = setTimeout(pollingLoop, POLLING_INTERVAL);
updateSockets({
students: students
});
})
}
该平台采用Socket.io实现浏览器和服务器之间实时、双向和基于事件的通信,在服务器端的业务逻辑中,服务器等待客户端的连接,一旦有客户端浏览器接入,便建立双向的持久通信连接,并向其推送数据,直到客户端关闭浏览器,通信才会中止。服务端用数组维护接入的客户端,用客户端ID标识每一个接入的连接。
浏览器利用Socket.io客户端建立与服务端Socket.io的连接,并监听数据更新事件,数据到达后进行更新人员数量、动态曲线及进出馆人员信息的视图。服务器端代码如下:
var updateSockets = function(data) {
connectionsArray.forEach(function(tmpSocket) {
tmpSocket.emit('lib_data', data);
});
};
客户端代码如下:
var Socket = io.connect('http://ip:8000');
Socket.on('lib_data', function (data) {
//得到推送的数据data,更新页面视图
}
数据可视化能够有效提升数据的可见度与可访问性,使人们易于接受和理解,系统采用了Echarts可视化库增强入馆读者对人员流量感知。Apache Echarts是由百度出品的一个免费、强大的图表和可视化库,它基于ZRENDER并用纯粹的JavaScript编写而成,可为Web页面添加直观、互动和高度可自定义的图表。页面使用Echarts实现可视化图例[7],主要由实时馆人员数量仪表盘、在馆人员以二级学院分组的结构柱状图和基于时间坐标轴的动态曲线构成。
在多终端跨界页面显示需求下,需要采用不同的方案分别设计大屏、PC端和手机端的正常可视化显示。
3.5.1 数据可视化大屏和PC端的显示适配方案
大屏的数据可视化要实现全屏显示,首先要去掉浏览器的附加部分(地址栏、导航栏、tab栏等)的尺寸。其次,设计页面时,页面内容的尺寸不能超过视窗的大小,以防出现滚动条。第三,目前主流的液晶显示器分辨率为1 920×1 080,而大屏的分辨率远远大于台式机液晶显示器,一般为2 560×1 440,4 096×2 160或更高。数据可视化大屏和PC端可采用如下设计:设计稿采用1 920×1 080分辨率模式适配PC端,因高宽比率满足16:9,因此可采用动态获取缩放系数进行等比例放大,来满足1 920×1 080以上的分辨率,即大屏的显示适配。代码如下:
resize() {
const designwidth=1920 ,designheight=1080
let w = window.innerWidth / designwidth
let h = window.innerHeight / designheight
let scale = w < h ? w : h
let body = document.body
body.style.transform='scale('+scale+')'
body.style.transformOrigin = '0 0'
}
window.addEventLishener('resize',function(){
resize ()
}
resize ()
3.5.2 手机端查询适配方案
在小于1 920×1 080分辨率的情况下,利用CSS3的媒体查询和flex布局,可实现手机端的查询页面自适应适配方案。在页面显示的默认布局里,前半部分布局分成3块内容。手机端的媒体查询和自适应代码如下:
.wraper:{
display:flex;
}
@media screen and (min-width: 320px) and (max-width: 480px) {
#inlibcount,#inout,#deptanalysis{
width:100%;
}
}
高校中各个楼宇门禁的配置在很多情况下是由不同部门在不同的时间完成的,造成了门禁系统品牌和技术多样化、后台数据库多源异构的现状。在这种情况下,要即时获取多个门禁系统的实时数据,服务器可以对每一个门禁后台数据库启动1个线程,对其进行3 s一次的轮询。一旦有数据查询到,便使用1个唯一的消息标识绑定数据,由服务端Socket.io实例发送此消息到浏览器Socket.io客户端。消息标识采用“【楼宇名】_data”来命名,比如:lib_data标识图书馆门禁的数据,diningHall_data标识了餐厅门禁的数据。浏览器启动对应的Socket.io客户端,对服务器发出的多个数据消息进行监听,并在监听的回调函数里更新相应的页面DOM节点,由此完成针对多个楼宇门禁数据的实时获取和显示。多楼宇人数实时动态显示系统架构图如图3所示。
图3 多楼宇人数实时动态显示系统架构图
平台不仅可以在大屏上展示,也可以在校园网内的任何计算机和手机上查看,方便读者和管理人员远程掌握图书馆人员流量信息。
实时显示预警平台的显示页面由4部分构成,如图4所示。
图4 楼宇人数实时显示预警平台显示页面
图4显示如下内容:(1)在馆人数的实时动态变化由仪表盘图例展示,环状颜色随着在馆人员的数量变化而变化,在达到警戒值后,颜色呈红色显示,并不断闪烁,以提醒管理人员和进出人员注意。(2)显示页面的中间部分显示了最近入馆和最近出馆人员的简要信息,辅助门禁管控进出人员,掌握人员活动轨迹。(3)显示页面的柱状图部分展示了在馆人员的构成,主要统计“机电工程学院”“建筑与测绘工程学院”“电气与信息工程学院”“文法与管理学院”“基础教育学院”5个学院的进馆读者构成。(4)页面下半部分的动态曲线图展示了基于时间轴顺序的进馆人员数量变化,从而可以分析一天中哪个时段人流量比较集中,是场所人数控制高度关注的时间结点。
手机端查询以微信公众号嵌入链接的方式实现。手机界面提供了在馆人数实时动态变化仪表盘图例和入馆时序折线图,如图5所示。
图5上半部分提供当前时间的在馆人数和上限值,下半部分描述了在各个时间点的人员流量情况。
通过该平台可以将进出图书馆门禁的人员数量实时显示在大屏上,对进出馆人数动态数量进行醒目展示,并通过颜色变化提示来馆人员注意进馆人员过度集中,以达到在疫情防控中对人员数量进行控制的目的。同时,平台也提供了移动端的查询供读者参考。该平台尤其适用于图书馆、食堂等人员活动集中场所,在各个楼宇门禁具有配置且获得授权访问后台数据库的理想条件下,可实现多楼宇人流量的实时监控,助力疫情防控工作。