diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index b3ef8e3..6c64e21 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -40,10 +40,29 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - distro: - - rockylinux9 - - ubuntu2404 - - debian12 + include: + - distro: rockylinux9 + scenario: default + - distro: ubuntu2404 + scenario: default + - distro: ubuntu2204 + scenario: default + - distro: debian12 + scenario: default + - distro: debian11 + scenario: default + - distro: ubuntu2404 + scenario: deb822 + - distro: debian12 + scenario: deb822 + - distro: ubuntu2204 + scenario: deb822 + - distro: debian11 + scenario: deb822 + - distro: ubuntu2004 + scenario: deb822 + - distro: debian13 + scenario: deb822 steps: - name: Check out the codebase. @@ -60,7 +79,7 @@ jobs: run: pip3 install ansible molecule molecule-plugins[docker] docker - name: Run Molecule tests. - run: molecule test + run: molecule test -s ${{ matrix.scenario }} env: PY_COLORS: '1' ANSIBLE_FORCE_COLOR: '1' diff --git a/README.md b/README.md index aa2a11f..dd9c7cc 100644 --- a/README.md +++ b/README.md @@ -2,11 +2,11 @@ [![CI](https://github.com/geerlingguy/ansible-role-filebeat/actions/workflows/ci.yml/badge.svg)](https://github.com/geerlingguy/ansible-role-filebeat/actions/workflows/ci.yml) -An Ansible Role that installs [Filebeat](https://www.elastic.co/products/beats/filebeat) on RedHat/CentOS or Debian/Ubuntu. +An Ansible Role that installs [Filebeat](https://www.elastic.co/products/beats/filebeat) on RedHat/CentOS or Debian/Ubuntu. Supports both traditional APT repository format and the DEB822 format for Debian 13+ and Ubuntu 24+. ## Requirements -None. +- Ansible 2.15+ (required for DEB822 repository format support on modern Debian/Ubuntu systems) ## Role Variables diff --git a/defaults/main.yml b/defaults/main.yml index d3ec0fc..9deb633 100644 --- a/defaults/main.yml +++ b/defaults/main.yml @@ -3,6 +3,11 @@ filebeat_version: 7.x filebeat_package: filebeat filebeat_package_state: present +# Repository configuration is automatic based on OS version: +# - Debian 12+ and Ubuntu 22+ use DEB822 format (modern systems) +# - Older systems use traditional apt_repository format +# Old repository sources are automatically cleaned up on modern systems + filebeat_create_config: true filebeat_template: "filebeat.yml.j2" diff --git a/meta/main.yml b/meta/main.yml index 5f4ca5f..522b61e 100644 --- a/meta/main.yml +++ b/meta/main.yml @@ -7,17 +7,24 @@ galaxy_info: description: Filebeat for Linux. company: "Midwestern Mac, LLC" license: "license (BSD, MIT)" - min_ansible_version: 2.10 + min_ansible_version: "2.15" platforms: - name: Debian versions: - jessie - stretch + - buster + - bullseye + - bookworm + - trixie - name: Ubuntu versions: - trusty - xenial - bionic + - focal + - jammy + - noble galaxy_tags: - web - system diff --git a/molecule/deb822/converge.yml b/molecule/deb822/converge.yml new file mode 100644 index 0000000..407bc8a --- /dev/null +++ b/molecule/deb822/converge.yml @@ -0,0 +1,107 @@ +--- +- name: Converge + hosts: all + become: true + vars: + filebeat_version: 8.x + filebeat_create_config: false # Skip config creation for repository testing + + pre_tasks: + - name: Update apt cache. + apt: update_cache=yes cache_valid_time=600 + when: ansible_os_family == 'Debian' + + roles: + - role: geerlingguy.filebeat + + post_tasks: + - name: Verify DEB822 repository exists for systems using DEB822 format + stat: + path: /etc/apt/sources.list.d/elasticsearch.sources + register: deb822_repo + when: + - ansible_os_family == 'Debian' + - > + (ansible_distribution == "Debian" and ansible_distribution_major_version | int >= 12) or + (ansible_distribution == "Ubuntu" and ansible_distribution_major_version | int >= 22) + + - name: Assert DEB822 repository exists when expected + assert: + that: + - deb822_repo.stat.exists + msg: "DEB822 repository file should exist at /etc/apt/sources.list.d/elasticsearch.sources" + when: + - ansible_os_family == 'Debian' + - > + (ansible_distribution == "Debian" and ansible_distribution_major_version | int >= 12) or + (ansible_distribution == "Ubuntu" and ansible_distribution_major_version | int >= 22) + + - name: Verify traditional repository does not exist when using DEB822 + shell: grep -r "artifacts.elastic.co" /etc/apt/sources.list.d/*.list || true + register: traditional_repo_check + changed_when: false + when: + - ansible_os_family == 'Debian' + - > + (ansible_distribution == "Debian" and ansible_distribution_major_version | int >= 12) or + (ansible_distribution == "Ubuntu" and ansible_distribution_major_version | int >= 22) + + - name: Assert old traditional repositories are cleaned up + assert: + that: + - traditional_repo_check.stdout == "" + msg: "Traditional repository entries should be cleaned up when using DEB822 format" + when: + - ansible_os_family == 'Debian' + - > + (ansible_distribution == "Debian" and ansible_distribution_major_version | int >= 12) or + (ansible_distribution == "Ubuntu" and ansible_distribution_major_version | int >= 22) + + - name: Verify filebeat package is installable + package: + name: filebeat + state: present + when: ansible_os_family == 'Debian' + + # Tests for older systems (should use traditional format) + - name: Verify DEB822 repository does NOT exist for older systems + stat: + path: /etc/apt/sources.list.d/elasticsearch.sources + register: deb822_repo_old + when: + - ansible_os_family == 'Debian' + - > + (ansible_distribution == "Debian" and ansible_distribution_major_version | int < 12) or + (ansible_distribution == "Ubuntu" and ansible_distribution_major_version | int < 22) + + - name: Assert DEB822 repository does NOT exist on older systems + assert: + that: + - not deb822_repo_old.stat.exists + msg: "DEB822 repository file should NOT exist on older systems (< Debian 12 or < Ubuntu 22)" + when: + - ansible_os_family == 'Debian' + - > + (ansible_distribution == "Debian" and ansible_distribution_major_version | int < 12) or + (ansible_distribution == "Ubuntu" and ansible_distribution_major_version | int < 22) + + - name: Verify traditional repository exists for older systems + shell: grep -r "artifacts.elastic.co" /etc/apt/sources.list.d/*.list || true + register: traditional_repo_old + changed_when: false + when: + - ansible_os_family == 'Debian' + - > + (ansible_distribution == "Debian" and ansible_distribution_major_version | int < 12) or + (ansible_distribution == "Ubuntu" and ansible_distribution_major_version | int < 22) + + - name: Assert traditional repository exists on older systems + assert: + that: + - traditional_repo_old.stdout != "" + msg: "Traditional repository should exist on older systems (< Debian 12 or < Ubuntu 22)" + when: + - ansible_os_family == 'Debian' + - > + (ansible_distribution == "Debian" and ansible_distribution_major_version | int < 12) or + (ansible_distribution == "Ubuntu" and ansible_distribution_major_version | int < 22) diff --git a/molecule/deb822/molecule.yml b/molecule/deb822/molecule.yml new file mode 100644 index 0000000..b4966c1 --- /dev/null +++ b/molecule/deb822/molecule.yml @@ -0,0 +1,33 @@ +--- +role_name_check: 1 +dependency: + name: galaxy + options: + ignore-errors: true +driver: + name: docker +platforms: + - name: ubuntu2404-deb822 + image: "geerlingguy/docker-ubuntu2404-ansible:latest" + command: ${MOLECULE_DOCKER_COMMAND:-""} + volumes: + - /sys/fs/cgroup:/sys/fs/cgroup:rw + cgroupns_mode: host + privileged: true + pre_build_image: true + - name: debian12-deb822 + image: "geerlingguy/docker-debian12-ansible:latest" + command: ${MOLECULE_DOCKER_COMMAND:-""} + volumes: + - /sys/fs/cgroup:/sys/fs/cgroup:rw + cgroupns_mode: host + privileged: true + pre_build_image: true +provisioner: + name: ansible + playbooks: + converge: ${MOLECULE_PLAYBOOK:-converge.yml} + inventory: + host_vars: + ubuntu2404-deb822: {} + debian12-deb822: {} diff --git a/molecule/default/converge.yml b/molecule/default/converge.yml index 7ff5f94..8e752ab 100644 --- a/molecule/default/converge.yml +++ b/molecule/default/converge.yml @@ -1,7 +1,7 @@ --- - name: Converge hosts: all - #become: true + # become: true pre_tasks: - name: Update apt cache. @@ -28,6 +28,6 @@ roles: - role: geerlingguy.java - - role: geerlingguy.elasticsearch - - role: geerlingguy.logstash + # - role: geerlingguy.elasticsearch + # - role: geerlingguy.logstash - role: geerlingguy.filebeat diff --git a/tasks/config.yml b/tasks/config.yml index d320493..c2938aa 100644 --- a/tasks/config.yml +++ b/tasks/config.yml @@ -34,4 +34,4 @@ - filebeat_ssl_key_file | default(false) - filebeat_ssl_certificate_file | default(false) -#- name: Ensure filebeat can read system's private key +# - name: Ensure filebeat can read system's private key diff --git a/tasks/setup-Debian.yml b/tasks/setup-Debian.yml index 7772c31..92f5e85 100644 --- a/tasks/setup-Debian.yml +++ b/tasks/setup-Debian.yml @@ -6,14 +6,85 @@ - gnupg2 state: present -- name: Add Elasticsearch apt key. +- name: Remove old Elasticsearch repository from sources.list.d when using DEB822 format. + apt_repository: + repo: 'deb https://artifacts.elastic.co/packages/{{ filebeat_version }}/apt stable main' + state: absent + when: > + (ansible_distribution == "Debian" and ansible_distribution_major_version | int >= 12) or + (ansible_distribution == "Ubuntu" and ansible_distribution_major_version | int >= 22) + +- name: Find all sources of elasticsearch packages. + find: + paths: "/etc/apt/sources.list.d/" + patterns: "artifacts_elastic_co_packages_*_apt.list" + register: elasticsearch_sources + when: > + (ansible_distribution == "Debian" and ansible_distribution_major_version | int >= 12) or + (ansible_distribution == "Ubuntu" and ansible_distribution_major_version | int >= 22) + changed_when: False + +- name: Remove old traditional repository files when using DEB822 format. + file: + path: "{{ item }}" + state: absent + with_items: "{{ elasticsearch_sources.files | map(attribute='path') | list }}" + when: > + (ansible_distribution == "Debian" and ansible_distribution_major_version | int >= 12) or + (ansible_distribution == "Ubuntu" and ansible_distribution_major_version | int >= 22) + +- name: Ensure python3-debian is present for DEB822 repository management. + apt: + name: python3-debian + state: present + update_cache: true + when: > + (ansible_distribution == "Debian" and ansible_distribution_major_version | int >= 12) or + (ansible_distribution == "Ubuntu" and ansible_distribution_major_version | int >= 22) + +- name: Add Elasticsearch apt key (for traditional repository format). apt_key: url: https://artifacts.elastic.co/GPG-KEY-elasticsearch id: 46095ACC8548582C1A2699A9D27D666CD88E42B4 state: present + when: > + (ansible_distribution == "Debian" and ansible_distribution_major_version | int < 12) or + (ansible_distribution == "Ubuntu" and ansible_distribution_major_version | int < 22) -- name: Add Filebeat repository. +- name: Add Filebeat repository (traditional format). apt_repository: repo: 'deb https://artifacts.elastic.co/packages/{{ filebeat_version }}/apt stable main' state: present update_cache: true + when: > + (ansible_distribution == "Debian" and ansible_distribution_major_version | int < 12) or + (ansible_distribution == "Ubuntu" and ansible_distribution_major_version | int < 22) + +- name: Add Filebeat repository (DEB822 format for Debian 12+ and Ubuntu 22+). + deb822_repository: + name: elasticsearch + types: [deb] + uris: https://artifacts.elastic.co/packages/{{ filebeat_version }}/apt + suites: [stable] + components: [main] + signed_by: https://artifacts.elastic.co/GPG-KEY-elasticsearch + state: present + when: > + (ansible_distribution == "Debian" and ansible_distribution_major_version | int >= 12) or + (ansible_distribution == "Ubuntu" and ansible_distribution_major_version | int >= 22) + +- name: Update apt cache after adding DEB822 repository. + apt: + update_cache: true + when: > + (ansible_distribution == "Debian" and ansible_distribution_major_version | int >= 12) or + (ansible_distribution == "Ubuntu" and ansible_distribution_major_version | int >= 22) + +- name: Remove old Elasticsearch APT key when using DEB822 format (Debian 12). + # Note: apt_key is deprecated in Debian 13+, so we only use it for Debian 12 + apt_key: + id: 46095ACC8548582C1A2699A9D27D666CD88E42B4 + state: absent + when: > + (ansible_distribution == "Debian" and ansible_distribution_major_version | int == 12) or + (ansible_distribution == "Ubuntu" and ansible_distribution_major_version | int == 22)