Files

104 lines
8.4 KiB
YAML

---
# tasks/preview_diff_report.yml — Compute and display configuration diff report
#
# Included by the configure role when commit=false (default).
# Uses the netbird_diff and netbird_format_diff filter plugins for comparison.
- name: Display preview header
ansible.builtin.debug:
msg:
- "══════════════════════════════════════════════════════════════"
- " NETBIRD CONFIGURATION PREVIEW — {{ config_dir | basename | upper }}"
- " Config: {{ config_dir }}/"
- " API: {{ netbird_api_url }}"
- " Mode: READ-ONLY (no changes will be made)"
- "══════════════════════════════════════════════════════════════"
# =========================================================================
# Build lookup maps
# =========================================================================
- name: Index current resources by name
ansible.builtin.set_fact:
current_groups_map: "{{ dict(api_groups.data | map(attribute='name') | zip(api_groups.data)) }}"
current_posture_checks_map: "{{ dict(api_posture_checks.data | map(attribute='name') | zip(api_posture_checks.data)) }}"
current_setup_keys_map: "{{ dict(api_setup_keys.data | map(attribute='name') | zip(api_setup_keys.data)) }}"
current_dns_map: "{{ dict(api_dns_nameservers.data | map(attribute='name') | zip(api_dns_nameservers.data)) }}"
current_dns_zones_map: "{{ dict(api_dns_zones.data | map(attribute='name') | zip(api_dns_zones.data)) }}"
current_networks_map: "{{ dict(api_networks.data | map(attribute='name') | zip(api_networks.data)) }}"
current_policies_map: "{{ dict(api_policies.data | map(attribute='name') | zip(api_policies.data)) }}"
- name: Build reverse lookup maps
ansible.builtin.set_fact:
peer_id_name: "{{ dict(api_peers.data | default([]) | map(attribute='id') | zip(api_peers.data | default([]) | map(attribute='name'))) }}"
group_id_name: "{{ dict(api_groups.data | default([]) | map(attribute='id') | zip(api_groups.data | default([]) | map(attribute='name'))) }}"
# =========================================================================
# Enrich network data with routers
# =========================================================================
- name: Build enriched current networks (with routers)
ansible.builtin.set_fact:
current_networks_enriched: >-
{% set result = {} -%}
{% for net in api_networks.data | default([]) -%}
{% set routers = (preview_network_routers.results[loop.index0].json | default([])) if preview_network_routers is defined and preview_network_routers.results is defined else [] -%}
{% set _ = result.update({net.name: net | combine({'routers': routers})}) -%}
{% endfor -%}
{{ result | to_json | from_json }}
# =========================================================================
# Build protected groups list (JWT + All)
# =========================================================================
- name: Build protected group names
ansible.builtin.set_fact:
_protected_groups: "{{ api_groups.data | selectattr('issued', 'defined') | selectattr('issued', 'equalto', 'jwt') | map(attribute='name') | list + ['All'] }}"
# =========================================================================
# Compute diffs using filter plugin
# =========================================================================
- name: Compute all resource diffs
ansible.builtin.set_fact:
diff_groups_data: "{{ netbird_groups | default([]) | community.ansible_netbird.netbird_diff(current_groups_map, 'simple', protected=_protected_groups) }}"
diff_pc_data: "{{ netbird_posture_checks | default([]) | community.ansible_netbird.netbird_diff(current_posture_checks_map) }}"
diff_sk_data: "{{ netbird_setup_keys | default([]) | community.ansible_netbird.netbird_diff(current_setup_keys_map) }}"
diff_dns_data: "{{ netbird_dns_nameserver_groups | default([]) | community.ansible_netbird.netbird_diff(current_dns_map, 'dns', group_ids=group_ids) }}"
diff_dz_data: "{{ netbird_dns_zones | default([]) | community.ansible_netbird.netbird_diff(current_dns_zones_map) }}"
diff_net_data: "{{ netbird_networks | default([]) | community.ansible_netbird.netbird_diff(current_networks_enriched, 'network', peer_ids=peer_ids, peer_id_name=peer_id_name) }}"
diff_pol_data: "{{ netbird_policies | default([]) | community.ansible_netbird.netbird_diff(current_policies_map, 'policy', group_id_name=group_id_name) }}"
# =========================================================================
# Format and display
# =========================================================================
- name: Build account diff
ansible.builtin.set_fact:
diff_account:
- "── Account Settings ──────────────────────────────────────────"
- "{{ ' ~ EXISTS: account settings (will be re-applied)' if netbird_settings | default({}) | length > 0 else ' (not configured — skipped)' }}"
- name: Display diff report
ansible.builtin.debug:
msg: >-
{{ diff_account + ['']
+ diff_pc_data | community.ansible_netbird.netbird_format_diff('Posture Checks') + ['']
+ diff_groups_data | community.ansible_netbird.netbird_format_diff('Groups') + ['']
+ diff_sk_data | community.ansible_netbird.netbird_format_diff('Setup Keys') + ['']
+ diff_dns_data | community.ansible_netbird.netbird_format_diff('DNS Nameserver Groups') + ['']
+ diff_dz_data | community.ansible_netbird.netbird_format_diff('DNS Zones') + ['']
+ diff_net_data | community.ansible_netbird.netbird_format_diff('Networks') + ['']
+ diff_pol_data | community.ansible_netbird.netbird_format_diff('Policies') }}
# =========================================================================
# Summary
# =========================================================================
- name: Display summary
ansible.builtin.debug:
msg:
- "══════════════════════════════════════════════════════════════"
- " SUMMARY — {{ config_dir | basename | upper }}{{ ' (STRICT)' if strict | default(false) | bool else '' }}"
- "──────────────────────────────────────────────────────────────"
- " + Add: {{ (diff_groups_data.new | length) + (diff_pc_data.new | length) + (diff_sk_data.new | length) + (diff_dns_data.new | length) + (diff_dz_data.new | length) + (diff_net_data.new | length) + (diff_pol_data.new | length) }} resource(s)"
- " ~ Changed: {{ (diff_groups_data.changed | length) + (diff_pc_data.changed | length) + (diff_sk_data.changed | length) + (diff_dns_data.changed | length) + (diff_dz_data.changed | length) + (diff_net_data.changed | length) + (diff_pol_data.changed | length) }} resource(s)"
- " = Unchanged: {{ (diff_groups_data.unchanged | length) + (diff_pc_data.unchanged | length) + (diff_sk_data.unchanged | length) + (diff_dns_data.unchanged | length) + (diff_dz_data.unchanged | length) + (diff_net_data.unchanged | length) + (diff_pol_data.unchanged | length) }} resource(s)"
- " - Remove: {{ (diff_groups_data.remove | length) + (diff_pc_data.remove | length) + (diff_sk_data.remove | length) + (diff_dns_data.remove | length) + (diff_dz_data.remove | length) + (diff_net_data.remove | length) + (diff_pol_data.remove | length) }} resource(s)"
- "{% set total_orphan = (diff_groups_data.orphaned | length) + (diff_pc_data.orphaned | length) + (diff_sk_data.orphaned | length) + (diff_dns_data.orphaned | length) + (diff_dz_data.orphaned | length) + (diff_net_data.orphaned | length) + (diff_pol_data.orphaned | length) %}{% if total_orphan > 0 %} - Orphan: {{ total_orphan }} resource(s) (not in config{{ ', will be removed with strict=true' if not strict | default(false) | bool else ', WILL BE REMOVED' }}){% endif %}"
- "══════════════════════════════════════════════════════════════"