目录
4 | 变量文件 group_vars/all.yml(整体加密)
5.1 roles/minio/tasks/main.yml
5.2 install.yml —— 上传二进制 + 创建用户
5.3 configure.yml —— 创建目录 + 生成 endpoint 列表 + unit 文件
5.6 templates/minio.service.j2
6 | 主 Playbook deploy_minio.yml
版本与环境
OS:openEuler 24.03 (LTS)
Ansible:≥ 2.11(
dnf install -y ansible
)MinIO:
RELEASE.2025-06-13T11-33-47Z
主控节点:
10.130.135.145
(也运行 Ansible)存储节点:
10.130.135.{164,149,200,199}
数据目录:
/app/minio_data/disk1…4
端口:9000(API)/9001(Console)
0 | 为什么要写这篇教程?
在 openEuler-24.03 上用 Ansible 部署 MinIO 分布式,踩过不少坑:
报错/现象 | 根因 |
---|---|
VARIABLE IS NOT DEFINED! |
Vault 文件未被加载 / 变量自引用 |
loop.parent attribute error |
Jinja2 嵌套循环解析不稳定 |
requested handler 'restart minio' was not found |
忘了在 handlers 里声明 |
SELinux 绑定缺失 | openEuler 默认开启 SELinux,需安装 python3-libselinux |
curl 下载慢 | 改为一次上传二进制 → copy 分发 |
下面给出一次能跑通的最终方案,并总结每个坑的解决思路。
1 | 准备工作
1.1 控制节点手工下载 MinIO
mkdir -p /opt/minio-bin
cd /opt/minio-bin
curl -LO https://dl.min.io/server/minio/release/linux-amd64/archive/minio.RELEASE.2025-06-13T11-33-47Z
mv minio.RELEASE.* minio
chmod +x minio
这样只有控制机访问公网,其余节点通过 Ansible 的
copy
分发即可。
1.2 SSH 互信(可跳过,本教程已有互信)
ssh-keygen -t rsa -f ~/.ssh/id_rsa -N ''
for h in 164 149 200 199; do ssh-copy-id root@10.130.135.$h; done
1.3 安装 Ansible & SELinux 依赖
dnf install -y ansible python3-libselinux
2 | 项目目录
minio-ansible/
├── hosts.ini
├── deploy_minio.yml
├── group_vars/
│ └── all.yml # 已加密
└── roles/
└── minio/
├── tasks/
│ ├── main.yml
│ ├── install.yml
│ ├── configure.yml
│ └── start.yml
├── handlers/
│ └── main.yml
└── templates/
└── minio.service.j2
3 | Inventory hosts.ini
[minio]
10.130.135.164
10.130.135.149
10.130.135.200
10.130.135.199
4 | 变量文件 group_vars/all.yml
(整体加密)
为啥放 all.yml 而不是 vault.yml?
group_vars/all.yml
是 Ansible 的 自动加载路径,不会漏读。整个文件加密,省去在 playbook 里
vars_files
的声明和加载顺序问题。
5 | 角色文件
5.1 roles/minio/tasks/main.yml
- import_tasks: install.yml
- import_tasks: configure.yml
- import_tasks: start.yml
5.2 install.yml
—— 上传二进制 + 创建用户
- name: Create group & user
become: true
group: { name: "{{ minio_group }}" }
- user:
name: "{{ minio_user }}"
group: "{{ minio_group }}"
shell: /sbin/nologin
create_home: no
become: true
- name: Copy MinIO binary from control node
copy:
src: "{{ minio_local_bin }}"
dest: "{{ minio_bin_path }}"
owner: root
group: root
mode: '0755'
become: true
5.3 configure.yml
—— 创建目录 + 生成 endpoint 列表 + unit 文件
- name: Create data dirs
file:
path: "{{ item }}"
state: directory
owner: "{{ minio_user }}"
group: "{{ minio_group }}"
mode: '0755'
loop: "{{ minio_data_dirs }}"
become: true
# 单行 set_fact,避开 loop.parent 的坑
- name: Build endpoint list
set_fact:
minio_endpoints: "{{ minio_cluster_nodes
| product(minio_data_dirs)
| map('join','')
| map('regex_replace','^(.*)$','http://\\1')
| list }}"
- name: Deploy systemd unit
template:
src: minio.service.j2
dest: /etc/systemd/system/minio.service
notify: restart minio
become: true
5.4 start.yml
- systemd:
daemon_reload: true
become: true
- systemd:
name: minio
state: started
enabled: true
become: true
5.5 handlers/main.yml
- name: restart minio
become: true
systemd:
name: minio
state: restarted
daemon_reload: true
5.6 templates/minio.service.j2
[Unit]
Description=MinIO Distributed Object Storage
After=network.target
[Service]
User={{ minio_user }}
Group={{ minio_group }}
Environment="MINIO_ROOT_USER={{ minio_root_user }}"
Environment="MINIO_ROOT_PASSWORD={{ minio_root_password }}"
ExecStart={{ minio_bin_path }} server {{ minio_endpoints | join(' ') }} \
--address ":{{ minio_port }}" --console-address ":{{ minio_console_port }}"
Restart=always
LimitNOFILE=65536
[Install]
WantedBy=multi-user.target
6 | 主 Playbook deploy_minio.yml
---
- hosts: minio
become: true
roles:
- minio
7 | 执行部署
# 首次或每次升级
ansible-playbook -i hosts.ini deploy_minio.yml --ask-vault-pass
如果一切正常,你会看到所有节点
ok=
绿色,failed=0
。
8 | 验证集群状态
# 查看 systemd
ansible -i hosts.ini minio -b -a "systemctl status minio --no-pager"
# 查看端口
ansible -i hosts.ini minio -a "ss -ltnp | grep :9000" -b
ansible -i hosts.ini minio -a "ss -ltnp | grep :9001" -b
# 浏览器访问 http://10.130.135.164:9001 用 root 账号登录
9 | 常见踩坑与解决
报错 | 解决 |
---|---|
VARIABLE IS NOT DEFINED |
确保敏感变量放在 group_vars/all.yml 并加密;或在 playbook 中显式 vars_files 。 |
loop.parent attribute error |
不要在模板用 loop.parent ;改为先 set_fact 生成列表。 |
requested handler 'restart minio' was not found |
在 roles/minio/handlers/main.yml 声明同名 handler。 |
SELinux 报缺 libselinux-python |
openEuler 24.03 默认装 python3-libselinux ,若无则 dnf install -y python3-libselinux 。 |
下载慢 | 手工下载到控制机,copy 分发。 |
10 | 总结
openEuler 24.03 自带
dnf
/ systemd,与 RHEL8 类似;Ansible 默认只加载
group_vars/all.yml
和<group>.yml
,Vault 文件最好直接放这里;Jinja2 里避免
loop.parent
,用set_fact
先生成结果再模板化;上传二进制 + copy 分发是离线环境、内网环境最稳妥方案。
按本文步骤,你可以在 5 分钟内把一套 4 节点 × 4 盘 的 MinIO 分布式集群跑在 openEuler 24.03 上,并且 playbook 可重复执行、幂等升级。Happy Object Storage on openEuler!
完整可用文件下载: https://download.csdn.net/download/gs80140/91262220
与教程不同的是, 下载的文件使用了vault加密服务, 可以参考下载文件说明使用