使用 Raspberry Pi 和开源工具收集传感器数据

更多地了解您家中正在发生的事情不仅有用;而且还很有趣!
102 位读者喜欢这篇文章。
Working from home at a laptop

Opensource.com

我一生中的大部分时间都住在百年以上的砖房里。它们看起来不错,很舒适,而且通常不太贵。然而,在我所在的气候中,冬季湿度很高,霉菌是一个反复出现的问题。一个显示相对湿度的桌面温度计对于测量湿度很有用,但它不能提供持续监测。

Raspberry Pi 应运而生:它体积小、价格低廉,并且有许多传感器选项,包括温度和相对湿度。它可以全天候收集数据、进行一些警报,并转发数据以进行分析。

最近,我参与了 miniNodes 的一项实验,旨在收集和处理全 Arm 计算机网络上的环境数据。我的网络节点之一是一台 Raspberry Pi,它收集了我办公桌上方的环境数据。项目结束后,我被允许保留硬件并使用它。这成为了我的寒假项目。仅仅为了更多地了解 PythonElasticsearch 而学习它们是很枯燥的。拥有一个利用这些技术的实际项目不仅有用,而且使学习变得有趣。

最初,我计划仅使用这两种技术。不幸的是,我的老式 Arm “服务器”,一台面向开发人员的 OverDrive 1000 机器,以及我的 Xeon 服务器,声音都太大了,不适合在我办公桌上方持续使用。我只在需要它们时才打开它们,这意味着当服务器离线时,某种缓冲是必要的。对于一个 Python 初学者来说,为 Elasticsearch 实现缓冲看起来有点困难。幸运的是,我知道一个可以缓冲数据并将其发送到 Elasticsearch 的工具:syslog-ng

关于许可的说明

Elasticsearch 的维护者 Elastic 最近将其项目的许可证从 Apache License(一个由开源促进组织批准的极其宽松的许可证)更改为更严格的许可证“以保护我们的产品和品牌免受滥用”。上下文中的“滥用”一词指的是 公司使用 Elasticsearch 和 Kibana 并直接向客户提供服务,而没有与 Elastic 或 Elastic 社区合作(对宽松许可证的常见批评)的趋势。目前尚不清楚这会如何影响用户,但这对于开源社区来说是一个重要的讨论,尤其是在云服务变得越来越普遍的情况下。

为了保持您的项目开源,请使用 Apache License 下的 Elasticsearch 7.10 版本。

配置数据收集

对于数据收集,我使用了一台 Raspberry Pi Model 3B+,它运行最新的 Raspberry Pi OS 版本,并连接了一组来自 SparkFun 的传感器,这些传感器连接到一个 Qwiic pHat 附加板(该板已停产,但有更新的板提供相同的功能)。由于使用固定位置监控 GPS 没有多大意义,而且冬季也检测不到闪电,因此我只连接了环境传感器。您可以使用 GitHub 上提供的 Python 脚本 从传感器收集数据。

以用户身份在本地安装 Python 模块

pip3 install sparkfun-qwiic-bme280

有三个示例脚本可用于检查数据收集。您可以使用浏览器或 Git 下载它们

git clone https://github.com/sparkfun/Qwiic_BME280_Py/

当您启动脚本时,它将以美观、人类可读的格式打印数据

pi@raspberrypi:~/Documents/Qwiic_BME280_Py/examples $ python3 qwiic_bme280_ex1.py

SparkFun BME280 Sensor  Example 1

Humidity:	58.396
Pressure:	128911.984
Altitude:	-6818.388
Temperature:	70.43

Humidity:	58.390
Pressure:	128815.051
Altitude:	-6796.598
Temperature:	70.41

^C
Ending Example 1

我来自欧洲,因此默认温度数据对我来说意义不大。幸运的是,您可以轻松地重写代码以使用公制单位:只需将 temperature_fahrenheit 替换为 temperature_celsius 即可。压力和海拔高度显示了一些疯狂的值,即使我更改为公制单位也是如此,但我没有调试它们。湿度和温度值与我预期的值(基于我的桌面温度计)非常接近。

一旦我验证了相关传感器按预期工作,我就开始开发自己的代码。它非常简单。首先,我确保它每秒向终端打印值,然后我添加了 syslog 支持

#!/usr/bin/python3

import qwiic_bme280
import time
import sys
import syslog

# initialize sensor
sensor = qwiic_bme280.QwiicBme280()
if sensor.connected == False:
  print("Sensor not connected. Exiting")
  sys.exit(1)
sensor.begin()

# collect and log time, humidity and temperature
while True:
  t = time.localtime()
  current_time = time.strftime("%H:%M:%S", t)
  current_humidity = sensor.humidity
  current_temperature = sensor.temperature_celsius
  print("time={} humidity={} temperature={}".format(current_time,current_humidity,current_temperature))
  message = "humidity=" + str(current_humidity) + " temperature=" + str(current_temperature)
  syslog.syslog(message)
  time.sleep(1)

当我使用 screen 实用程序启动 Python 脚本时,我也将数据打印到终端。使用 tail 命令检查收集的数据是否到达 syslog-ng

pi@raspberrypi:~ $ tail -3 /var/log/messages
Jan  5 12:11:24 raspberrypi sensor2syslog_v2.py[6213]: humidity=58.294921875 temperature=21.4
Jan  5 12:11:25 raspberrypi sensor2syslog_v2.py[6213]: humidity=58.294921875 temperature=21.4
Jan  5 12:11:26 raspberrypi sensor2syslog_v2.py[6213]: humidity=58.294921875 temperature=21.39

配置 Elasticsearch

我的 Pi 3B+ 中的 1GB RAM 太低了,无法运行 Elasticsearch 和 Kibana,因此我将它们托管在第二台机器上。在 Linux 上安装 Elasticsearch 和 Kibana 在每个平台上都不同,因此我不会介绍这一点。我将介绍的是映射。默认情况下,syslog-ng 将所有数据作为文本发送。如果您想在 Kibana 中准备漂亮的图表,则需要将温度和湿度值作为浮点数。

您需要在从 syslog-ng 发送数据之前设置映射。syslog-ng 配置期望 Sensors 索引使用此映射

{
  "mappings": {
    "_doc": {
      "properties": {
        "@timestamp": {
          "type": "date"
        },
        "sensors": {
          "properties": {
            "humidity": {
              "type": "float"
            },
            "temperature": {
              "type": "float"
            }
          }
        }
      }
    }
  }
}

Elasticsearch 现在已准备好从 syslog-ng 收集数据。

安装和配置 syslog-ng

Raspberry Pi OS 中包含 syslog-ng 的 3.19 版本,但它尚不具备 Elasticsearch 支持。因此,我从一个非官方存储库安装了最新版本的 syslog-ng。首先,我添加了存储库密钥

wget -qO - https://download.opensuse.org/repositories/home:/laszlo_budai:/syslog-ng/Raspbian_10/Release.key | sudo apt-key add -

然后,我将以下行添加到 /etc/apt/sources.list.d/sng.list

deb https://download.opensuse.org/repositories/home:/laszlo_budai:/syslog-ng/Raspbian_10/ ./

最后,我更新了存储库并安装了必要的 syslog-ng 软件包(这也从系统中删除了 rsyslog)

apt-get update
apt-get install syslog-ng-mod-json syslog-ng-mod-http

还有许多其他 syslog-ng 子软件包,但只需要这两个子软件包即可将传感器日志转发到 Elasticsearch。

Syslog-ng 的主配置文件是 /etc/syslog-ng/syslog-ng.conf,您无需修改它。您可以通过在 /etc/syslog-ng/conf.d 目录下创建扩展名为 .conf 的新文本文件来扩展配置。

我创建了一个名为 sens2elastic.conf 的文件,内容如下

filter f_sensors {program("sensor2syslog_v2.py")};
parser p_kv {kv-parser(prefix("sensors."));};
destination d_sensors {
  file("/var/log/sensors" template("$(format-json @timestamp=${ISODATE} --key sensors.*)\n\n"));
  elasticsearch-http(
      index("sensors")
      type("")
      url("http://192.168.1.129:9200/_bulk")
      template("$(format-json @timestamp=${ISODATE} --key sensors.*)")
      disk-buffer(
        disk-buf-size(1G)
        reliable(no)
        dir("/tmp/disk-buffer")
      )
  );
};
log {
  source(s_src);
  filter(f_sensors);
  parser(p_kv);
  destination(d_sensors);
};

如果您是 syslog-ng 的新手,请阅读我关于 syslog-ng 构建块 的文章,以了解 syslog-ng 的配置。上面的配置片段显示了一些可能的构建块,除了源之外,因为您需要使用 syslog-ng.conf (s_src) 中定义的本地日志源。

第一行是一个过滤器:它匹配程序名称。我的程序名称是 sensor2syslog_v2.py。确保此值与您的 Python 脚本的名称相同。

第二行是一个键值解析器。默认情况下,syslog-ng 将传入日志消息的消息部分视为纯文本。使用此解析器,您可以从日志消息中的数据在 syslog-ng 中创建名称-值对,您可以在稍后将日志发送到 Elasticsearch 时使用这些名称-值对。

下一个块稍大一些。它是一个包含两个不同目标驱动程序的目标。第一个驱动程序以 JSON 格式将日志保存到本地文件。我使用它进行调试。第二个驱动程序是 Elasticsearch 目标。确保索引名称和 URL 与您的环境匹配。使用这个大型磁盘缓冲区,您可以确保即使您的 Elasticsearch 服务器离线数天也不会丢失任何数据。

最后一个块有点不同。它是日志语句,即连接上述构建块的配置部分。源的名称来自主配置。

保存配置并创建 /tmp/disk-buffer/ 目录。重新加载 syslog-ng 以使配置生效

systemctl restart syslog-ng

测试系统

下一步是测试系统。Elasticsearch 已经运行并准备好接收数据。Syslog-ng 已配置为将数据转发到 Elasticsearch。因此,启动脚本以确保实际收集数据。

对于快速测试,您可以在终端窗口中启动它。对于连续数据收集,我建议从 screen 实用程序启动它,以便即使您断开与机器的连接,它也能保持运行。当然,这并非万无一失,因为它不会在重新启动时“自动”启动。如果您想 24/7 全天候收集数据,请为其创建一个 init 脚本或 systemd 服务文件。

检查日志是否到达 /var/log/sensors 文件。如果它不为空,则过滤器按预期工作。接下来,打开 Kibana。我无法在此处给出确切的说明,因为菜单结构似乎随每个版本而变化。从 Sensors 索引为 Kibana 创建索引模式,然后切换到 Kibana 的 Discover 模式,并选择新定义的索引。您应该已经在屏幕上看到传入的温度和湿度数据。

您现在可以可视化数据了。我使用了 Kibana 的新 Lens 模式来可视化温度和湿度值。虽然它不是很灵活,但它肯定比 Kibana 中的其他可视化工具更容易操作。此图显示了我收集的数据,包括当我打开窗户用新鲜冷空气通风房间时值的变化。

我学到了什么?

我的最初目标是在复习 Python 和 Elasticsearch 技能的同时,监控我家的相对湿度。即使停留在基本水平,我现在也感觉更自如地使用 Python 和 Elasticsearch。

最棒的是:我不仅练习了这些工具,还从图表中了解了相对湿度。以前,我经常打开窗户通风一两分钟。Kibana 图表显示,当我关闭窗户后,湿度很快又恢复到原来的水平。当我打开窗户通风五到十分钟后,湿度会保持较低水平几个小时。

下一步是什么?

更喜欢冒险的人可以使用 Raspberry Pi 和传感器不仅来监控,还可以控制他们的家。我从头开始配置所有内容,但也有现成的工具可用,例如 Home Assistant。您还可以在 syslog-ng 中配置警报,以执行诸如 向您的 Slack 频道发送警报 之类的操作,如果温度降至设定水平以下。Raspberry Pi 有许多传感器可用,因此在软件和硬件方面都有无数的可能性。

接下来阅读什么
标签
Peter Czanik
Peter 是一位工程师,在 Balabit(One Identity 业务部门)担任开源布道师,该公司开发了 syslog-ng。他协助发行版维护 syslog-ng 软件包,跟踪错误,帮助用户,并在会议(SCALE、All Things Open、FOSDEM、LOADays 等)上定期谈论 sudo 和 syslog-ng。

1 条评论

英雄所见略同 :) 我也发表了一篇使用相同传感器的文章在 opensource.com 上
https://open-source.net.cn/article/21/3/sensor-data-raspberry-pi

如果您担心 elasticsearch 许可证,您应该考虑切换到 prometheus 和 grafana,因为它们是开源产品。它们也可以在 arm 架构上运行。

Creative Commons 许可协议本作品根据 Creative Commons 署名-相同方式共享 4.0 国际许可协议获得许可。
© . All rights reserved.