部署指南

目标: 了解将安全工件部署到生产系统中时的最佳实践。

教程级别: 高级

时间: 20 分钟

背景

典型的部署场景通常涉及将容器化应用程序或软件包运送到远程系统。 部署启用安全性的应用程序时应特别注意,要求用户考虑打包文件的敏感性。

遵守 DDS Security standard, sros2 软件包提供了一组实用程序,用于以高度模块化和灵活的方式管理 ROS 2 环境下的安全性。

关于如何组织不同证书、密钥和目录的基本核心指南仍然是避免危及系统安全性的关键因素。

这包括保护意识和选择部署在远程生产系统上的最少必要文件集的标准,以最大限度地减少安全风险。

先决条件

一般准则

ROS 2 利用 DDS 安全扩展来确保同一安全区内消息交换的安全性。 安全区内的不同签名文件和证书由以下对象的私钥和证书生成: Certificate Authority (CA) trusted entity. 事实上,每个区域可以选择两个不同的 CA 来获得身份和权限。 这些 CA 工件存储在“private/”和“public/”子目录中 Keystore 具有以下文件夹结构:

keystore
├── enclaves
│   └── ...
│       └── ...
├── private
│   └── ...
└── public
    └── ...

在生产系统的典型部署中创建和使用某个证书颁发机构的良好做法是:

  1. 在仅供内部使用的组织系统内创建它。

  2. 生成/修改所需的区域,同时牢记:

    • 并非所有生成的 enclave 都应部署到所有目标设备。

    • 合理的方法是每个应用程序都有一个 enclave,以便分离关注点。

  3. 在设置期间将 public/ 和相应的 enclaves/ 一起发送到不同的远程生产设备。

  4. 保留并保护组织中的 private/ 密钥和/或认证请求。

需要注意的是,如果 private/ 文件丢失,将无法再更改访问权限、添加或修改安全配置文件。

此外,还可以考虑采取进一步的做法:

  • 授予对 enclaves/ 目录内容的只读权限。

  • 如果给出了符合 PKCS#11 的 URI 来生成 enclave 的私钥,则 Hardware Security Module (HSM) 可用于存储它们。

下表总结了前面将 Keystore 目录与推荐位置关联的语句:

Directory / Location

Organization

Target Device

Material Sensitivity

public

Low

private

High

enclaves

Medium

构建部署场景

为了说明一个简单的部署场景,将在“ros:<DISTRO>”提供的镜像之上构建一个新的 docker 镜像。

从镜像开始,将创建三个容器,目的是:

  • 初始化本地主机共享卷中的密钥库。

  • 模拟两个以安全方式相互交互的已部署远程设备。

在此示例中,本地主机充当组织的系统。

让我们从创建一个工作区文件夹开始:

mkdir ~/security_gd_tutorial
cd ~/security_gd_tutorial

生成 Docker 映像

为了构建新的 Docker 映像,需要一个 Dockerfile。 可以使用以下命令检索本教程建议的 Dockerfile:

# Download the Dockerfile
wget https://raw.githubusercontent.com/ros2/ros2_documentation/rolling/source/Tutorials/Advanced/Security/resources/deployment_gd/Dockerfile

现在,使用以下命令构建 docker 镜像:

# Build the base image
docker build -t ros2_security/deployment_tutorial --build-arg ROS_DISTRO=rolling .

了解 Compose 文件

Compose 配置文件使用映像将容器创建为服务。 在本教程中,配置中定义了三个服务:

  • keystore-creator:与之前的教程类似,它在内部初始化一个新的密钥库树目录。 这将创建 enclaves/ public/private/,在 ROS 2 Security enclaves 中有更详细的说明。 keystore 目录配置为跨容器的共享卷。

  • listenertalker:在本教程中充当远程设备参与者。 所需的 Security 环境变量以及必要的密钥库文件均来自共享卷。

可以使用以下命令下载 Compose 配置 yaml 文件:

# Download the compose file
wget https://raw.githubusercontent.com/ros2/ros2_documentation/rolling/source/Tutorials/Advanced/Security/resources/deployment_gd/compose.deployment.yaml

运行示例

在同一个工作目录“~/security_gd_tutorial”中,运行:

# Start the example
docker compose -f compose.deployment.yaml up

这应该导致以下输出:

  • tutorial-listener-1: Found security directory: /keystore/enclaves/talker_listener/listener

  • tutorial-talker-1: Found security directory: /keystore/enclaves/talker_listener/talker

  • tutorial-listener-1: Publishing: 'Hello World: <number>'

  • tutorial-talker-1: I heard: [Hello World: <number>]

检查容器

在运行模拟本教程的两个远程设备的容器时,通过打开两个不同的终端并输入以下内容来连接到每个远程设备:

# Terminal 1
docker exec -it tutorial-listener-1 bash
cd keystore
tree

# Terminal 2
docker exec -it tutorial-talker-1 bash
cd keystore
tree

应该获得与下面类似的输出:

# Terminal 1
keystore
 ├── enclaves
    ├── governance.p7s
    ├── governance.xml
    └── talker_listener
        └── listener
            ├── cert.pem
            ├── governance.p7s
            ├── identity_ca.cert.pem
            ├── key.pem
            ├── permissions_ca.cert.pem
            ├── permissions.p7s
            └── permissions.xml
 └── public
     ├── ca.cert.pem
     ├── identity_ca.cert.pem
     └── permissions_ca.cert.pem

# Terminal 2
keystore
 ├── enclaves
    ├── governance.p7s
    ├── governance.xml
    └── talker_listener
        └── talker
            ├── cert.pem
            ├── governance.p7s
            ├── identity_ca.cert.pem
            ├── key.pem
            ├── permissions_ca.cert.pem
            ├── permissions.p7s
            └── permissions.xml
 └── public
     ├── ca.cert.pem
     ├── identity_ca.cert.pem
     └── permissions_ca.cert.pem

请注意:

  • private/ 文件夹不会被移动,而是留在本地主机(组织)中。

  • 每个部署的设备都包含其应用程序所需的最小空间。

Note

为了简单起见,此区域内的身份和权限使用相同的 CA。