65.9K
CodeProject 正在变化。 阅读更多。
Home

Raspberry Pi 的 IoT Home Assistant API

starIconstarIconstarIconstarIcon
emptyStarIcon
starIcon

4.90/5 (8投票s)

2018年10月30日

CPOL

7分钟阅读

viewsIcon

15659

构建一个改善 Home Assistant 和 Docker 容器之间交互的胚胎 API。

引言

本项目测试了家庭助理(Home Assistant)与 Docker 容器之间的交互。本系列的前几篇文章包括:

  • IoT.Starter.Pi.Thing:使用树莓派、Linux、Docker 和 .NET Core 构建家庭智能的雏形。该项目基于树莓派 3B 型号,配备 Raspbian GNU/Linux 9.1 Stretch Lite 和一个由 Swagger Hub 几乎自动生成的 Web 服务。该雏形平台包含独立容器中的 API 和 UI,以加速物联网项目的启动阶段。
  • IoT.Home.Thing:家庭物联网(Home of Things)将 Raspberry# IO 添加到平台中。它是一个用于树莓派的 .NET/Mono IO 库,由 Raspberry# 社区发起。Ramon Balaguer 首先将其更新到 .NET Standard 1.6,然后升级到 .NET Core 2.1 并集成到 IoT.Starter.Pi 雏形中。

由于我们正在构建一个物联网入门的雏形,因此到目前为止,一直提供一个空的 MVC 网站作为用户界面(UI)的种子。现在,这个空的用户界面将被 Home Assistant 应用程序取代,从而在项目启动后立即获得更快、更高效的结果。

Home Assistant 是一个运行在 Python 3 上的开源家庭自动化平台。它用于跟踪和控制家中的所有设备,并具有许多实用工具来帮助我们进行自动化控制。您可以通过 Home Assistant 的博客查看社区的活跃程度,该平台不断进行更新和升级。我们希望 Home Assistant 能与 IoT.Starter.Pi 设备中可用的雏形 API 进行交互。

生成磁盘镜像

安装 Home Assistant 有多种方法,因为它支持多种不同的硬件平台。本项目重点介绍 Haspbian,这是一个包含在树莓派上运行 Home Assistant 所需一切的磁盘镜像。

Haspbian 镜像使用与生成树莓派基金会官方 Raspbian 镜像相同的脚本构建。用于创建 raspberrypi.org Raspbian 镜像的相同工具是从 home-assistant/pi-gen 存储库分叉而来。最终阶段被移除,并替换了一个新的 stage-3 以安装 Home Assistant。除了 git,所有依赖项都由构建脚本处理。

对于本项目,这个 pi-gen 工具再次从 home-assistant/pi-gen 分叉到 josemotta/pi-gen,并添加了一个新的 thing 分支,其中包含一个 stage-4,用于包含 Lirc 安装和 IoT.Starter.Pi 雏形的其他初始设置。请查看下面的 run.sh 脚本,其中显示了添加到磁盘镜像的一些有用依赖项。

#!/bin/bash -e

install -d "${ROOTFS_DIR}/var/run/lirc"
install -m 666 -d "${ROOTFS_DIR}/home/pi/config"
install -m 666 -d "${ROOTFS_DIR}/home/pi/backup"

rm -f "${ROOTFS_DIR}/etc/lirc/lircd.conf.d/devinput.lircd.conf"

install -m 644 files/i2c1-bcm2708.dtbo "${ROOTFS_DIR}/boot/overlays"

install -m 644 files/config.txt "${ROOTFS_DIR}/boot/config.txt"
install -m 644 files/lirc_options.conf "${ROOTFS_DIR}/etc/lirc/lirc_options.conf"
install -m 644 files/ir-remote.conf "${ROOTFS_DIR}/etc/modprobe.d/ir-remote.conf"
install -m 644 files/lirc24.conf "${ROOTFS_DIR}/etc/lirc/lircd.conf.d/lirc24.conf"
install -m 644 files/lirc44.conf "${ROOTFS_DIR}/etc/lirc/lircd.conf.d/lirc44.conf"
install -m 644 files/Samsung_BN59-00678A.conf 
               "${ROOTFS_DIR}/etc/lirc/lircd.conf.d/Samsung_BN59-00678A.conf"
install -m 644 files/AppConfig.json "${ROOTFS_DIR}/app"

install -m 755 files/setup.sh "${ROOTFS_DIR}/home/pi/setup.sh"

rm -f "${ROOTFS_DIR}/etc/default/keyboard"
install -m 644 files/keyboard "${ROOTFS_DIR}/etc/default/keyboard"

cat << EOF >> ${ROOTFS_DIR}/etc/samba/smb.conf
[config]
path = /home/pi/config
available = yes
valid users = pi
read only = no
browsable = yes
public = yes
writable = yes
[backup]
path = /home/pi/backup
available = yes
valid users = pi
read only = no
browsable = yes
public = yes
writable = yes
EOF

如您所见,stage-4 还安装和配置了 Samba 服务器,以公开几个文件夹

  • /home/pi/config:Home Assistant 配置文件夹
  • /home/pi/backup:用于备份/恢复雏形设置的文件夹

在我的开发 PC 上创建的虚拟 Debian 机器上运行 pi-gen 半小时后,生成了一个包含所有已安装依赖项的 SD 磁盘镜像。使用 Etcher 烧录镜像,即可获得雏形的核心,准备植入树莓派驱动器。该镜像已在 RPI 2B/3B 上成功测试。请暂时保留 SD 磁盘,因为我们首先要构建项目。

在开发机上构建

根据IoT.Starter.Pi.Thing的策略,构建在 RPI 之外进行,使用配备 Windows 10、Visual Studio、Docker 和 Hyper-V 的快速 x64 微型计算机。在开发机器上,我们应该根据 api.yml 文件使用 docker-compose 命令构建项目。

请参阅下面的文件,其中包括 apihassmosquittoportainer 服务。

version: "3"

services:
  api:
    image: josemottalopes/home-api
    build:
      context: .
      dockerfile: src/IO.Swagger/api.dockerfile
    ports:
    - "5000:5000"
    network_mode: bridge
    privileged: true
    restart: always
    devices:
      - /dev/mem:/dev/mem
      - /dev/i2c-1:/dev/i2c-1
      - /dev/gpiomem:/dev/gpiomem
    volumes:
      - /var/run/lirc:/var/run/lirc
    environment:
      - ASPNETCORE_ENVIRONMENT=Release

  hass:
    image: homeassistant/raspberrypi3-homeassistant:0.80.3
    ports:
      - "8123:8123"
    network_mode: bridge
    volumes:
      - /home/pi/config:/config
    restart: always
    devices:
      - /dev/i2c-1:/dev/i2c-1
      - /dev/gpiomem:/dev/gpiomem
    environment:
      - TZ=America/Sao_Paulo
    depends_on:
      - mosquitto
      - api

  mosquitto:
    build:
      context: ./Mosquitto
    restart: unless-stopped
    ports:
     - "1883:1883"
    network_mode: bridge 
    volumes:
     - ./Mosquitto/auth.conf:/etc/mosquitto/conf.d/auth.conf:ro
     - ./Mosquitto/users.passwd:/etc/mosquitto/users.passwd:ro

  portainer:
    image: portainer/portainer
    ports:
      - "9000:9000"
    command: -H unix:///var/run/docker.sock
    restart: always
    volumes:
      - /var/run/docker.sock:/var/run/docker.sock
      - portainer_data:/data

volumes:
  portainer_data:

以下是每个服务的简要描述:

  • api:这是由 Swagger Hub 生成的 API,它包含雏形消息。
  • hass:这是 Home Assistant 应用程序,用作雏形的 UI。
  • mosquitto:一个供 Home Assistant 逻辑使用的 MQQT 代理。
  • portainer:这是一个用于 Docker 的简单管理解决方案。

构建解决方案是一个漫长的过程,包括编译由 Swagger Hub 生成的 API 和 Raspberry# IO 库。当前解决方案还包括本系列之前使用的空 UI MVC 网站。下面是构建会话的快捷方式。

jo@CANOAS24 MINGW64 /c/_git/IoT.Home.Pi/home (master)
$ docker-compose -f api.yml build
Building api
Step 1/35 : FROM microsoft/dotnet:2.0.7-runtime-stretch-arm32v7 AS base
 ---> 87595eb7f1f4
Step 2/35 : ENV DOTNET_CLI_TELEMETRY_OPTOUT 1
 ---> Using cache
 ---> 9e6c62851cc6
Step 3/35 : ENV ASPNETCORE_URLS "http://*:5000"
 ---> Using cache
 ---> c290db537f12
Step 4/35 : WORKDIR /app
 ---> Using cache
 ---> 7dccd40b712f
Step 5/35 : RUN   apt-get update   && apt-get upgrade -y   && apt-get install -ylirc   
            --no-install-recommends &&   rm -rf /var/lib/apt/lists/*
 ---> Using cache

... big build including all projects from solution

  IO.Swagger -> /src/src/IO.Swagger/bin/Release/netcoreapp2.0/linux-arm/IO.Swagger.dll
  IO.Swagger -> /app/
Removing intermediate container e98edde9e6b1
 ---> 37f4b8ed2042
Step 32/35 : FROM base AS final
 ---> 055ee036885d
Step 33/35 : WORKDIR /app
 ---> Using cache
 ---> 79c8c71c098b
Step 34/35 : COPY --from=publish /app .
 ---> f0e36a46b8d2
Step 35/35 : ENTRYPOINT ["dotnet", "IO.Swagger.dll"]
 ---> Running in 9d100e734c07
Removing intermediate container 9d100e734c07
 ---> 46b9b656c5e2
Successfully built 46b9b656c5e2
Successfully tagged josemottalopes/home-api:latest
Building mosquitto
Step 1/3 : FROM resin/raspberry-pi-debian:stretch
 ---> ced6fc5da205
Step 2/3 : RUN   apt-get update   && apt-get upgrade -y   && apt-get install 
-ymosquitto mosquitto-clients   --no-install-recommends &&   rm -rf /var/lib/apt/lists/*
 ---> Using cache
 ---> 66afe7dadb46
Step 3/3 : CMD [ "/usr/sbin/mosquitto", "-c", "/etc/mosquitto/mosquitto.conf" ]
 ---> Using cache
 ---> d20ea9daf328
Successfully built d20ea9daf328
Successfully tagged home_mosquitto:latest
hass uses an image, skipping
portainer uses an image, skipping

最终构建步骤应该再次使用 docker-compose 命令,这次是将 API 镜像推送到 Docker Hub。请看下面的实际操作:

jo@CANOAS24 MINGW64 /c/_git/IoT.Home.Pi/home (master)
$ docker-compose -f api.yml push
Pushing api (josemottalopes/home-api:latest)...
The push refers to repository [docker.io/josemottalopes/home-api]
5b74c38596fb: Pushed
63edb82122c7: Pushed
08c704bc3c1a: Pushed
bf8666defb3a: Pushed
1f48f9c632fb: Pushed
3ae6b6a37d49: Pushed
0bbaa93801e6: Pushed
28d327b91985: Pushed
2917ff0f1d45: Pushed
420a4cbda8df: Layer already exists
53c3793bdb6b: Layer already exists
002111fc932d: Layer already exists
2e9c4696ffa4: Layer already exists
latest: digest: sha256:779b47a4c1f9757c8abf3f137df19261e4e335c3b18cff1d16b94ddd1a92efba 
                size: 3037

现在,我们可以前往 RPI 部署雏形。

部署到 RPI

将带有胚胎核心的 SD 磁盘插入树莓派驱动器插槽。该板已配备一个Anavi 红外 pHat,这是一个附加板,可将您的树莓派转换为智能遥控器。它还支持温度、湿度、气压和光线传感器模块。请查看下面的 RPI,它连接了三个传感器,左上方是提供强红外信号的双红外 LED。Anavi 红外 pHat 通过 RPI GPIO 连接器连接。树莓派还具有 5V 电源,并通过 RJ-45 网线连接到互联网路由器。

首次运行时,文件系统会初始化。启动后,我们应该首次登录树莓派并更改 pi 用户的初始密码。请注意,它保留了“raspberry”,与 raspberrypi.org Raspbian 镜像相同。由于 SSH 可用,可以使用无头 RPI,从另一台微型计算机打开 bash 终端。否则,只需插入 USB 键盘和 HDMI 连接器即可直接与雏形交互。

克隆仓库

让我们使用 ssh 从开发 PC 启动一个 bash 会话。请看下面 pi@copa,这是本次演示选择的主机名。

jo@CANOAS24 MINGW64 ~
$ ssh pi@copa
pi@copa's password:
Linux copa 4.14.70-v7+ #1144 SMP Tue Sep 18 17:34:46 BST 2018 armv7l

The programs included with the Debian GNU/Linux system are free software;
the exact distribution terms for each program are described in the
individual files in /usr/share/doc/*/copyright.

Debian GNU/Linux comes with ABSOLUTELY NO WARRANTY, to the extent
permitted by applicable law.
Last login: Mon Oct 29 13:17:49 2018 from 192.168.20.113 

让我们在树莓派本地克隆 Iot.Home.Pi 仓库。多亏了修改后的 pi-gen,在 pi 默认文件夹中应该已经有一个脚本可以完成此操作。

pi@copa:~ $ cat setup.sh
#!/bin/sh
set -e

# Home Setup
REPO="https://github.com/josemotta/IoT.Home.Pi.git"
HOME="/home/pi/IoT.Home.Pi"

git clone $REPO $HOME

然后,停留在默认的 /home/pi 文件夹中,您只需运行

./setup.sh 

请注意,这是在开发机器上构建项目时使用的同一个仓库。不同之处在于我们现在在 RPI 端。我们希望使用 docker-compose 命令两次,始终基于之前构建时使用的同一个 api.yml 文件。

  • 首先从 Docker Hub 拉取镜像,然后
  • 其次,编排相应的容器

文件夹 ~/IoT.Home.Pi/home 应该包含雏形项目的基本文件。

pi@copa:~ $ cd I*/home
pi@copa:~/IoT.Home.Pi/home $ ls -l
total 60
-rw-r--r--  1 pi pi 1017 Oct  6 20:10 api.yml
-rw-r--r--  1 pi pi  257 Oct  6 20:10 _clear.bat
drwxr-xr-x  3 pi pi 4096 Oct  6 20:10 Docker
-rw-r--r--  1 pi pi 1385 Oct  6 20:10 docker-compose.dcproj
-rw-r--r--  1 pi pi  458 Oct  6 20:10 docker-compose.yml
drwxr-xr-x  2 pi pi 4096 Oct  6 20:38 Hass
-rw-r--r--  1 pi pi 1490 Oct  6 20:10 home-api.yml
-rw-r--r--  1 pi pi  905 Oct  6 20:10 home-compose.yml
-rw-r--r--  1 pi pi 5870 Oct  6 20:10 Home.sln
drwxr-xr-x  4 pi pi 4096 Oct  6 20:10 Lirc
-rw-r--r--  1 pi pi  579 Oct  6 20:10 NuGet.Config
drwxr-xr-x  3 pi pi 4096 Oct  6 20:10 Proxy
drwxr-xr-x  2 pi pi 4096 Oct  6 20:10 Raspberry.IO
drwxr-xr-x 11 pi pi 4096 Oct  6 20:10 src

安装 Docker

Hass 文件夹中有一个 setup.sh 脚本,用于安装 Docker 和 docker-compose。正如之前解释的,RPI 的最新版本 docker-compose 是手动构建的,并通过安装脚本安装。此外,应该设置一个密码来保护公开的配置和备份文件夹。

#!/bin/sh
set -e

DOCKER_COMPOSE="$HOME/Docker/docker-compose"
KEY_USER="josemotta@bampli.com"
KEY_FILE="/home/pi/.ssh/id_rsa"
CONFIG_FOLDER=/home/pi/config/
BACKUP_FOLDER=/home/pi/backup/
DEFAULT_CONFIG=*_hassconfig_*
USERNAME=pi
PASSWORD=password

chmod 0777 $BACKUP_FOLDER
chmod 0777 $CONFIG_FOLDER
cp ${HOME}/Hass/${DEFAULT_CONFIG} ${BACKUP_FOLDER}

# Docker
curl -fsSL get.docker.com -o get-docker.sh
sh get-docker.sh
usermod -aG docker pi

# Docker-compose
cp $DOCKER_COMPOSE /usr/local/bin
chown root:root /usr/local/bin/docker-compose
chmod 0755 /usr/local/bin/docker-compose

# Senha inicial do "config"
echo -e "$PASSWORD\n$PASSWORD" | smbpasswd -a -s -c /etc/samba/smb.conf $USERNAME

# SSH
ssh-keygen -t rsa -b 4096 -C $KEY_USER -q -N "" -f $KEY_FILE

更改目录到 Hass 并运行 sudo ./setup.sh 以完成 RPI 设置。然后检查 Docker 是否正常运行。

pi@copa:~ $ docker version
Client:
 Version:           18.06.1-ce
 API version:       1.38
 Go version:        go1.10.3
 Git commit:        e68fc7a
 Built:             Tue Aug 21 17:30:52 2018
 OS/Arch:           linux/arm
 Experimental:      false

Server:
 Engine:
  Version:          18.06.1-ce
  API version:      1.38 (minimum version 1.12)
  Go version:       go1.10.3
  Git commit:       e68fc7a
  Built:            Tue Aug 21 17:26:37 2018
  OS/Arch:          linux/arm
  Experimental:     false

pi@copa:~ $ docker-compose version
docker-compose version 1.19.0-rc2, build dfcb02c
docker-py version: 2.7.0
CPython version: 2.7.13
OpenSSL version: OpenSSL 1.0.1t  3 May 2016

拉取镜像

docker-compose pull 命令用于从 Docker Hub 下载最新的 josemottalopes/home-api 镜像。

pi@copa:~/IoT.Home.Pi/home $ docker-compose -f api.yml pull
Pulling portainer (portainer/portainer:latest)...
latest: Pulling from portainer/portainer
Digest: sha256:07c0e19e28e18414dd02c313c36b293758acf197d5af45077e3dd69c630e25cc
Status: Image is up to date for portainer/portainer:latest
Pulling api (josemottalopes/home-api:latest)...
latest: Pulling from josemottalopes/home-api
5483105d0916: Already exists
4a08fa0bd267: Already exists
5db6c48919a3: Already exists
4ed51a05c924: Already exists
be01d4da0224: Pull complete
9902b97c6ff4: Pull complete
d45a0684105a: Pull complete
2fd83b49817b: Pull complete
9036c0edc62a: Pull complete
f66a27b68370: Pull complete
5e974242185a: Pull complete
ae3b66331312: Pull complete
4d4cbdc4d968: Pull complete
Digest: sha256:779b47a4c1f9757c8abf3f137df19261e4e335c3b18cff1d16b94ddd1a92efba
Status: Downloaded newer image for josemottalopes/home-api:latest
Pulling hass (homeassistant/raspberrypi3-homeassistant:0.78.3)...
0.78.3: Pulling from homeassistant/raspberrypi3-homeassistant
Digest: sha256:f06dc1d1bea815f50aa8244df31593e13d953d1b650427423375d9fc43443625
Status: Image is up to date for homeassistant/raspberrypi3-homeassistant:0.78.3 

全部运行

再次使用另一个 docker-compose 命令,现在使用 docker-compose up -d 来正确编排容器

pi@copa:~/IoT.Home.Pi/home $ docker-compose -f api.yml up -d
Creating network "home_default" with the default driver
Pulling portainer (portainer/portainer:latest)...
latest: Pulling from portainer/portainer
d1e017099d17: Pull complete
a9e4458c8fdc: Pull complete
Digest: sha256:07c0e19e28e18414dd02c313c36b293758acf197d5af45077e3dd69c630e25cc
Status: Downloaded newer image for portainer/portainer:latest
Creating home_portainer_1 ... done
Creating home_api_1       ... done
Creating home_hass_1      ... done

pi@copa:~/IoT.Home.Pi/home $ docker ps
CONTAINER ID        IMAGE                                             COMMAND                  CREATED             STATUS              PORTS                    NAMES
fdd60b1edf87        portainer/portainer                               "/portainer -H unix:�"   48 seconds ago      Up 34 seconds       0.0.0.0:9000->9000/tcp   home_portainer_1
c1163bb370db        homeassistant/raspberrypi3-homeassistant:0.78.3   "/bin/entry.sh pytho�"   48 seconds ago      Up 36 seconds       0.0.0.0:8123->8123/tcp   home_hass_1
71cf17d6af66        josemottalopes/home-api                           "dotnet IO.Swagger.d�"   48 seconds ago      Up 36 seconds       0.0.0.0:5000->5000/tcp   home_api_1
pi@copa:~/IoT.Home.Pi/home $

容器正在运行,我们可以检查端口 5000、8123 和 9000,以查看所有服务的相应 UI。

查看胚胎结果

Home Assistant 仪表板显示可用状态,包括可用传感器。

Portainer 管理器屏幕显示有关容器和运行镜像的所有详细信息。

还有由 Swagger Hub 生成的胚胎 API,显示使用 Raspberry# IO 库收集的传感器数据。

远程 API 可以使用 curl 发布红外命令,例如:

jo@CANOAS24 MINGW64 /c/_git/IoT.Home.Pi/home (master)
$ curl -X GET "http://192.168.20.105:5000/motta/home/1.0.3/remotes" -H "accept: text/plain"
Samsung_BN59-00678A
LED_24_KEY
LED_44_KEY

jo@CANOAS24 MINGW64 /c/_git/IoT.Home.Pi/home (master)
$ curl -X GET "http://192.168.20.105:5000/motta/home/1.0.3/remotes/LED_24_KEY" 
       -H "accept: text/plain"
0000000000000001 BRIGHT_DOWN
0000000000000002 BRIGHT_UP
0000000000000003 OFF
0000000000000004 ON
0000000000000005 RED
0000000000000006 GREEN
0000000000000007 BLUE
0000000000000008 WHITE
0000000000000009 ORANGE
000000000000000a PEA_GREEN
000000000000000b DARK_BLUE
000000000000000c 7_JUMP
000000000000000d DARK_YELLOW
000000000000000e CYAN
000000000000000f BROWN
0000000000000010 ALL_FADE
0000000000000011 YELLOW
0000000000000012 LIGHT_BLUE
0000000000000013 PINK
0000000000000014 7_FADE
0000000000000015 STRAW_YELLOW
0000000000000016 SKY_BLUE
0000000000000017 PURPLE
0000000000000018 3_JUMP 

Swagger UI 也可以用于发布红外命令,如下图所示:

结论

IoT.Home.Pi 胚胎已准备好进行定制,可以使用 Swagger Hub 的自动代码生成器来帮助进行 API 设计。Home Assistant 应正确配置以显示信息并控制可用设备。Portainer 管理器允许检查所有容器及其相关信息。还可以使用 Portainer 和 docker-compose 方法停止和运行容器。

祝您在物联网项目中玩得开心,工作顺利!

喜欢吗?请给我一颗星⭐️!

历史

© . All rights reserved.