用户案例

借助 Canvas 和 Elasticsearch 监测机场安全运营

Crimson Macaw 最近与曼彻斯特机场集团 (MAG) 携手开展了一个十分有趣的项目。我们需要为斯坦斯特德机场创建并实施一个机场安全运营实时仪表板。

此仪表板能够让控制室和安全部员工更好地了解乘客流动情况和安全表现,从而可以基于实时数据快速制定决策。需要从多个自有系统和外部数据源采集数据,然后在多个大屏幕上实现可视化。

数据采集挑战

决定采用 Elasticsearch 作为数据存储层后,我们需要确定采集哪些数据,以及如何采集。信息来自多个来源:自有数据库系统,经常被放入 AWS S3 桶的文件,以及来自外部 API 数据源的文件。National Rail 数据便是个很好的例子,我们需要使用 STOMP(流文本定向消息协议)接口将其加载到 Elasticsearch 中。

这本身便为我们造成了一些不得不克服的早期挑战:

  • 从数据库轮循数据的频率必须高于 1 次/分钟
  • 来自 STOMP 的输入数据已经过 gzip 压缩

轮循数据库的频率高于每分钟 1 次

我们使用了一个针对既有 logstash-input-jdbc 插件的简单补丁包,第一个问题迎刃而解。在使用补丁包之前,计划只能以 cron 格式来表达。该插件使用一个名为 rufus-scheduler 的作业规划工具,此工具支持以 cron 或者秒数来提供计划表达式。唯一改动是通过一行代码来使用 repeat 方法(而非 cron):

if @schedule @scheduler = Rufus::Scheduler.new(:max_work_threads => 1) @scheduler.cron @schedule do @scheduler.repeat @schedule do execute_query(queue) end

如要使用这些代码,可从 GitHub 下载我们的补丁包

处理经 gzip 压缩的消息

为了处理来自 STOMP 接口的压缩消息,我们必须使用 Logstash 将其解压缩以对数据进行筛选。尽管已经有 codec 能够读取来自 gzip 压缩消息的数据行,但是在我们的用例中,gzip 压缩消息为多行 XML。为了克服这一难题,我们自创了一个插件——logstash-codec-gzip,并将此插件发布在 GitHub 上。

使用 Canvas 对数据进行可视化

开始时,我们使用 Kibana 对在 Elastic Cloud 上托管的 Elasticsearch 中的数据进行可视化,但是效果不甚理想。我们觉得需要在更细的粒度层面进行控制。通过一个偶然的机会,我们知道了 Canvas,那时曼彻斯特机场集团的 BI 主管和我正参加于 2018 年 5 月在伦敦举行的 AWS 峰会。我们与 Elastic 展台的员工交谈,他们提到了 Canvas,并且说他们觉得 Canvas 是实现我们理想结果的更佳选择,还说明了原因。

“我们在 Kibana 中尝试对数据进行可视化时遇到了难题,因为其并不能给予我们所需的更精细层次的控制。”
“你知道 Canvas 吗?”
“不知道,那是什么?”
“它是我们新推的可视化工具;目前仍处在技术预览阶段,但是我们感觉它能帮你达到目标。”

安装 Canvas 和第一印象

Canvas 是 Kibana 中的一个插件,按照添加任何 Kibana 插件的正常流程便可安装。由于 Canvas 在技术预览阶段并未在 Elastic Cloud 上推出,所以我们在曼彻斯特机场集团 AWS 环境中托管 Kibana;完全脚本化,使用的是 Terraform。

Canvas 以简单的表达式语言来控制每个元素的可视化方式,这一点很棒。这让我想起了 Shell 编程,在 Shell 编程中,一条命令的输出会输入到下一条命令中,通过在括号内声明表达式便可以实现子表达式。

我第一次尝试使用 Canvas 仪表板对列车到达时间进行可视化(在下方查看当前版本)

在熟悉了几天 Canvas 之后,我们便能够对斯坦斯特德机场的列车到达时间进行可视化了。此仪表板的文本部分是使用 Markdown 元素创建的,页脚中的图标和图片则是使用 Image Repeat 创建的。

一切看起来都很好,我们能够控制各个元素,但是还有一些不尽完美之处。对于我们的用例,我们需要在更大程度上进行控制以实现下列操作:

  • 根据时区来设置时间戳格式,虽然数据是以 UTC 时间存储的,但是需要根据夏令时时间进行调整
  • 根据已知限值更改文本和/或图片的颜色

扩展 Canvas

为 Canvas 编写插件与为 Kibana 编写插件十分相似。它们都是用 NodeJS 编写的,并且所使用的注册表能够允许你添加更多函数,甚至添加可在 Canvas UI 中选择的新元素。我们开发了 3 个插件来实现所需的控制层级。

根据时区来设置时间戳格式

这是我们编写的第一个插件,是对内置 formatdate 进行的十分简单的扩展:

import moment from 'moment';
import 'moment-timezone/builds/moment-timezone-with-data';
export const formatdatetz = () => ({
  name: 'formatdatetz',
  type: 'string',
  help:'Output a ms since epoch number as a formatted string according to a given timezone',
  context: {
    types: ['number'],
  },
  args: {
    _: {
      types: ['string'],
      help:'MomentJS Format with which to bucket (See https://momentjs.com/docs/#/displaying/)',
      required: true
    },
    timezone: {
      types: ['string'],
      help:'The timezone',
      required: true,
      default:'UTC'
    }
  },
  fn: (context, args) => {
    if (!args._) return moment.utc(new Date(context)).tz(args.timezone).toISOString();
    return moment.utc(new Date(context)).tz(args.timezone).format(args._);
  },
});

formatdatetz 插件已在 GitHub 上发布,你可在 Canvas 的基础上安装此插件。安装过程就这么简单:

./bin/kibana-plugin install https://github.com/crimsonmacaw/nodejs-canvas-plugin-formatdatetz/releases/download/v1.0.2/canvas-plugin-formatdatetz-1.0.2.zip

控制文本和图片的颜色

我们无法使用 Markdown 控制文本和图片的样式(尽管你可以在 Canvas 中提供层叠样式表,但 Markdown 语法并不支持对 HTML 类别属性进行设置以表明要应用哪个样式表)。

对我们而言,最简单的方法是开发一个插件,此插件可以允许对 HTML 进行直接编码,并且编码方式与 Markdown 元素的编码方式类似,允许针对数据绑定使用手柄表达式。鉴于 SVG 图片可以直接嵌入到 HTML 中,我们可以直接应用相同层级的控制以根据从 Elasticsearch 检索的数据动态更改图片。

创建可视化

一旦拥有了所需插件,我们便能够控制以创建一些简单的内容,例如各行采用不同颜色的表格。

基于用户线框图,首个通过的安全中心仪表板设计方案(此仪表板的当前版本在下面显示,其与最初版本看起来大相径庭)

可视化现在已经聚合到了一起,数据也能填充到各个相关的占位符中,但是外观和感觉仍感觉不太对劲儿,我们收到的请求也反映了这一点。

“可以做得更漂亮些吗?”

现在便需要从互联网汲取灵感了,通过在各大平台(例如 PinterestDribbble)搜索“现代风格仪表板”,我们得到了一些很有意思的仪表板设计方法,并选择了不同的方向。

仍是安全中心仪表板,不过换成了黑色主题,使用了仪表盘和颜色渐变(仍在改进,之后会有更多变化)

向屏幕中添加了多项元素,大部分都是使用我们创建的 HTML 插件完成的,此插件同时混有简单 HTML 和一些动态生成的复杂 SVG 图片。

我们刚开始收到了积极反馈,但如果不向用户解释的话,未参与设计过程的用户并不能理解所有指标。

“哇塞!看起来好多啦,但底部的条柱是什么意思呢?“

通过回顾机场安全运营的最初要求,即能够快速制定决策,我们发现尽管你能生成特别炫酷的内容,但这不一定在任何时候都是对信息进行可视化的最佳方法。用户应该能够立即理解展现在他们面前的内容,而无需其他人对仪表板加以解释。

迭代式方法

在能够熟练使用 Canvas 表达语言后,我们举行了多场讨论会,邀请了多位利益相关方到场,并现场对仪表板进行了编辑。有一点很清楚,我们已经从在人们看到工具之前或者根据他们现有的报告来构建线框图,转换至富有创意的方式,即如何以最佳方式在仪表板上展示信息。利益相关方将最新版的仪表板展示给最终用户并收集反馈,然后再基于所收到的反馈进行更改。

最终仪表板

下方仪表板便是协作和创意思维的结晶。

“Crimson Macaw 使用 Elasticsearch 和 Canvas 为我们创建的仪表板能够让斯坦斯特德机场以现代方式展示我们的数据,而之前这些数据都位于各自的系统内。这为我们很多内部流程带来了多项效率优势,这在之前根本是不可能的。” – Stuart Hutson,曼彻斯特机场集团 BI 和分析部门主管

备注:出于演示目的,所有仪表板中的数据均为随机数据。为了实现这一点,我们甚至针对 Canvas 开发了一个 randomise(随机化)插件呢!

安全中心

此仪表板显示了机场安检的当前状态,从进出安检的人员,到合规率,再到有关各条通道的信息,十分全面。为安全通道所选的形状能够反映机场安检内的实际布局,所以运营员工能够立即将仪表板与实际通道联系到一起。

安全性 Pod

此仪表板显示了趋势信息,展示了进入机场安检区域的人数,这是基于不同区域预计会出现的乘客人数和等待时间而绘制的。

航班出发

这与正常的 FIDS(航班信息显示屏)十分相似,但还显示了其他详细信息,即未来航班的预估乘客数量与已通过机场安检乘客的数量的百分比。

列车到达

有大量乘客搭乘列车抵达斯坦斯特德机场,如果他们的行程有误,这会对抵达机场安检的乘客数量造成巨大影响。每辆列车上都会有数百名旅客,在问题得到解决后,可能会有多趟列车在很短时间内相继抵达。

仪表板不仅显示常见的列车信息表,而且还在时间轴上显示列车抵达时间。你可以看到,这与我们刚开始试验使用 Canvas 时的首个迭代版本相比,已经发生了翻天覆地的变化。

结论

Canvas 是一个很强大的工具,能够让用户创建十分炫酷的实时信息可视化。尽管 Canvas 目前仍为公测版,并且可能需要增加某些额外功能,但是用户能够通过插件扩展其核心功能,这一点的确有点像 Elastic 开发软件的方式。

很多 BI 工具会限制你仅使用图形和表格,且仅提供少数几个仪表盘和其他标准可视化。通过 Canvas 创建仪表板十分简单,这可允许数据工程师和数据可视化专员自由地创建可视化,不受任何约束,唯一的限制就是想象力。


Robert BruceCrimson Macaw 的创始合伙人之一,同时也是工程部总监。Crimson Macaw 是一家位于英国曼彻斯特的云/数据 IT 咨询公司。Robert 在数据工程和网络领域拥有 20 多年的丰富经验,目前致力于研究云技术领域。