嵌套Ansible角色中server变量作用域丢失问题求助
Ansible角色变量传递问题:
server变量在create-service角色中丢失 背景
原有openldap_vpn角色用于运行wireguard-go Docker容器,现需改造为部署可执行DNS查询并启动podman的systemd服务,容器内包含负责隧道转发的依赖服务。角色调用链路为:openldap_vpn → podman_wireguard_forwarder → podman_user_service → create-service。create-service角色解析模板时依赖server变量,但该变量传递至create-service时丢失——不过在podman_user_service中通过debug模块验证时,server变量仍可正常访问。
相关配置代码
1. openldap_vpn角色vars目录下的server字典
server: public_key: MFrZG5hi29Yp0U/p2RauSUUH8EAiE2wBcqX3p8jkG28= inside_ip: whatever host: whatever port: whatever
2. openldap_vpn引入podman_wireguard_forwarder的配置
--- - include_role: name=podman_wireguard_forwarder vars: name: openldap_vpn # needs private key listen_port: "{{ server.port }}" peers: - allowed_ips: - "{{ server.inside_ip }}/32" endpoint: ENDPOINT_IP public_key: "{{ server.public_key }}" forward_port: 3389 forward_dst: host: "{{ server.inside_ip }}" port: 3389 config_prepare_command: "ip=\"$(getent hosts '{{ server.host }}' | awk '{ print $1 }')\" ; sed -E \"s/ENDPOINT_IP/$ip/\""
3. podman_wireguard_forwarder的关键任务
- name: install wireguard config template become: yes become_user: "{{ user }}" template: src: wireguard_config dest: "{{ wg_config }}.template" - include_role: name=podman_user_service vars: service_name: "{{ service_name_vpn }}" params: |- --network "{{ podman_network }}" \ --cap-add=NET_ADMIN \ -v /dev/net/tun:/dev/net/tun \ -v "{{ wg_config }}:/etc/wireguard/wg0.conf" image: docker.io/masipcat/wireguard-go:latest start_pre: "/bin/sh -c '{{ config_prepare_command }}' < '{{ wg_config}}.template' > '{{ wg_config }}'"
4. podman_user_service的关键任务
- debug: msg: "still works: {{ server }}" - name: "update podman image {{ image }}" become: yes become_user: "{{ user }}" shell: podman image pull "{{ image }}" when: not image | regex_search('^localhost/') - include_role: name=create-service
5. create-service中执行失败的任务
- name: "copy {{ service_name }} service file" become: yes become_user: "{{ user if scope == 'user' else omit }}" template: src: service dest: "\ {{ '/home/' + user + '/.config/systemd/user' if scope == 'user' else '/etc/systemd/system' }}\ /{{ service_name }}.service"
报错信息
ansible.errors.AnsibleUndefinedVariable: [{'allowed_ips': ['{{ server.inside_ip }}/32'], 'endpoint': 'ENDPOINT_IP', 'public_key': '{{ server.public_key }}'}]: 'server' is undefined. 'server' is undefined.
解决方法
- 显式传递变量:在
podman_user_service引入create-service时,手动将server变量传递过去,因为Ansible默认不会自动将父角色的变量传递给嵌套调用的子角色。修改podman_user_service中的角色引入代码:
- include_role: name=create-service vars: server: "{{ server }}"
- 提前渲染模板依赖值:检查
create-service使用的service模板文件,若模板中直接引用了server变量的字段,可在调用create-service前,将这些字段提前渲染为独立变量并传递,避免模板依赖上层角色的变量。
内容的提问来源于stack exchange,提问作者Banyoghurt
相关产品推荐
相关产品推荐

