You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: CHANGELOG.md
+16Lines changed: 16 additions & 0 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -15,12 +15,21 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
15
15
16
16
### Breaking Changes
17
17
18
+
***role:apache_httpd, role:apache_tomcat, role:mastodon, role:postgresql_server**: Rename tags to the project-wide naming scheme. `apache_httpd:config` becomes `apache_httpd:configure`, and `apache_tomcat:users`, `mastodon:users`, `postgresql_server:users` and `postgresql_server:databases` lose their trailing `s` (`...:user`, `...:database`). Adjust any `--tags` / `--skip-tags` invocations and automation that reference the old tag names.
18
19
***role:minio_client, role:objectstore_backup**: Both roles and their playbooks (`playbooks/minio_client.yml`, `playbooks/objectstore_backup.yml`) have been removed, along with the corresponding role blocks in `playbooks/setup_nextcloud.yml` and the `setup_nextcloud__skip_minio_client` / `setup_nextcloud__skip_objectstore_backup` variables. MinIO Server has been archived as no-longer-maintained since February 2026, and we are moving away from using object storage for critical data. Users relying on these roles must replace the MinIO-based object-store backup with their own solution (e.g. `rclone`); the `mc` binary, its config under `/etc/mc/`, the `objectstore-backup` systemd timer/service, and `/usr/local/bin/mc-mirror.sh` are no longer managed by lfops and will remain on existing hosts until removed manually ([#241](https://github.com/Linuxfabrik/lfops/issues/241)).
19
20
***role:infomaniak_vm**: Always create a managed port for every entry in `infomaniak_vm__networks`, even when no `fixed_ip` is set. Previously only networks with a `fixed_ip` got a managed port; networks without one relied on OpenStack's auto-created port. To avoid creating unused (but billed) managed ports on VMs provisioned under the old behavior, make sure to manually rename the existing port in OpenStack to match the `port_name`. Note that this port will not survive VM deletion / detachment, since it was automatically created and therefore is owned by OpenStack, not the user.
20
21
21
22
### Added
22
23
23
24
***testing**: Add a Molecule-based test framework that runs the playbooks (and through them the roles) against throwaway libvirt/KVM VMs or Podman containers. Scenarios live under `extensions/molecule`; see the Testing section in `CONTRIBUTING.md`.
25
+
***role:icinga2_master, role:icingadb, role:icingaweb2, role:icingaweb2_module_reporting, role:icingaweb2_module_x509**: Add explicit Ubuntu variable files, making Ubuntu support visible alongside Debian. The Icinga repository, GPG key and package names were verified on Debian 13 and Ubuntu 24.04.
26
+
***role:nextcloud**: Add `meta/argument_specs.yml` declaring the user-facing variables, so role-entry validation catches type mismatches and missing mandatory variables.
27
+
***role:clamav**: Add `meta/argument_specs.yml` declaring the user-facing variables, so role-entry validation catches type mismatches and unknown variables.
28
+
***role:core_dumps**: New role that disables core dumps (which can leak sensitive process memory to disk) following the CIS Benchmark recommendations. Runs as part of `setup_basic`.
29
+
***role:login**: Sets a password-aging policy and a stricter default umask in `/etc/login.defs` (configurable). Applies to newly created accounts and password changes, not retroactively to existing accounts.
30
+
***role:kernel_modules**: New role that hardens a host by blocking rarely used or risky kernel modules (FireWire, legacy filesystems, uncommon network protocols) following the CIS Benchmark recommendations. Runs as part of `setup_basic`. The defaults stay clear of modules that would break common workloads (containers, snap, USB storage); those can be blocked explicitly where wanted.
31
+
***role:sshd**: Add Ubuntu 22.04 / 24.04 / 26.04 support and run on Fedora. On Debian and Ubuntu the role now manages the correct service unit (`ssh.service`) and disables OpenSSH socket activation (`ssh.socket`) so the daemon is managed consistently across distributions. Red Hat-family releases without a version-specific template (in particular Fedora) now fall back to a generic `RedHat``sshd_config` template instead of failing.
32
+
***role:hostname**: Maintains an `/etc/hosts` entry mapping the FQDN (and short name) to the host's primary IPv4 address for proper local name resolution. The IP is configurable via `hostname__etc_hosts_ip`, and the whole behaviour can be disabled with `hostname__manage_etc_hosts: false`.
24
33
***role:tmux**: Installs tmux and deploys a system-wide `/etc/tmux.conf` with sensible defaults, such as a larger scrollback buffer and mouse support. Selections are copied to the local clipboard over SSH via OSC 52 (where the terminal emulator supports it), and `prefix + P` dumps a pane's whole scrollback buffer to a file.
25
34
***role:graylog_server**: Make more HTTP, Elasticsearch, processing/output buffer and message journal settings configurable via `graylog_server__http_external_uri`, `graylog_server__http_enable_cors`, `graylog_server__elasticsearch_max_total_connections`, `graylog_server__elasticsearch_max_total_connections_per_route`, `graylog_server__output_batch_size`, `graylog_server__processbuffer_processors`, `graylog_server__outputbuffer_processors`, `graylog_server__ring_size`, `graylog_server__inputbuffer_ring_size`, `graylog_server__message_journal_max_age` and `graylog_server__message_journal_max_size`.
26
35
***role:mariadb_server**: Make `aria_pagecache_buffer_size`, `key_buffer_size` and `sort_buffer_size` configurable via the corresponding `mariadb_server__cnf_*` variables.
@@ -61,6 +70,10 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
61
70
62
71
### Changed
63
72
73
+
***role:icinga2_master, role:icingadb**: Validate the Icinga 2 configuration before restarting the service. A faulty config now fails the playbook run loudly instead of bouncing the daemon into a broken state and leaving Icinga 2 down.
74
+
***role:nextcloud**: Automatic app updates are now enabled by default (`nextcloud__timer_app_update_enabled`). The scheduled app update only switches Nextcloud into maintenance mode when an app update is actually pending, so an instance that is already up to date keeps serving requests without interruption. After updating, the recommended database migrations are applied automatically. A failed run no longer leaves the instance stuck in maintenance mode.
75
+
***role:clamav**: Now runs on Debian and Ubuntu in addition to Red Hat-family systems, and works on RHEL 10. The role seeds the signature database on first install so the scanner starts reliably, and runs an EICAR self-test (also available on its own via the `clamav:test` tag) that confirms detection actually works.
76
+
***role:sshd**: Ship hardened SSH defaults: X11 forwarding, agent forwarding and TCP keepalives are now off, `MaxAuthTries` is `3`, `ClientAliveCountMax` is `2`, and the log level is `VERBOSE`. All are overridable via the new `sshd__allow_agent_forwarding`, `sshd__allow_tcp_forwarding`, `sshd__client_alive_count_max`, `sshd__max_auth_tries`, `sshd__max_sessions`, `sshd__tcp_keep_alive` and `sshd__x11_forwarding` variables. Note: a client offering more than three keys from its SSH agent can be rejected by `MaxAuthTries 3`; use an explicit identity on the client or raise `sshd__max_auth_tries`.
64
77
***role:acme_sh**: Issue ECDSA P-256 certificates by default instead of RSA-4096, for faster TLS handshakes at equivalent security. Certificates previously issued as RSA are reissued as ECDSA on the next run, and the superseded RSA certificate is dropped from renewal. Set `acme_sh__key_length` to an RSA value such as `4096` to keep RSA.
65
78
***playbooks**: Enable the CRB repository on Rocky 10 too, not just Rocky 9. Previously Rocky 10 hosts silently skipped this step, which could leave dependencies such as `python3-virtualenv` uninstallable.
66
79
***role:grafana**: Apply the systemd/chkconfig workaround on RHEL 10 as well, not just RHEL 9.
@@ -135,6 +148,9 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
135
148
136
149
### Fixed
137
150
151
+
***role:repo_influxdb**: prevent the `influxdata-archive-keyring` package from being installed on both Enterprise Linux and Debian, as it would drop a second repo file pointing at upstream that is not managed by LFOps.
152
+
***role:php**: php-fpm workers now run with a defined `PATH`. Previously the worker environment was cleared, leaving `getenv("PATH")` empty, which broke PHP code that shells out to system binaries and tripped Nextcloud's "PHP getenv" setup warning.
153
+
***role:redis**: The Redis configuration file is no longer world-readable. It is now deployed as `root:redis` with mode `0640`, so its contents (e.g. a configured password) can no longer be read by other local users.
138
154
***role:acme_sh**: No longer reinstalls every certificate and reloads the web server on every run. Certificates are only reinstalled when they were just (re)issued or when the installed file is missing, so repeated runs are idempotent.
139
155
***role:keycloak**: Role now prints a clear instruction when a re-run can no longer obtain a token because the bootstrap admin was manually switched over to a permanent account (temporary `-temp` user deleted) and the bootstrap marker went missing.
140
156
***roles**: Controller-side downloads and git clones (those delegated to localhost) are no longer skipped when the first targeted host happens not to need them. Running a role against multiple hosts previously risked leaving later hosts without the downloaded artifact. Such steps now also run safely when the playbook targets many hosts in parallel.
Copy file name to clipboardExpand all lines: CONTRIBUTING.md
+35-1Lines changed: 35 additions & 1 deletion
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -174,7 +174,7 @@ Commit scopes:
174
174
fix(roles/graylog_server): prevent warn on receiveBufferSize (fix #341)
175
175
```
176
176
177
-
* For the first commit, use the message `Add roles/<role-name>` or `Add playbooks/<playbook-name>`.
177
+
* For the first commit, use the message `feat(roles/<role-name>): add role` or `feat(playbooks/<playbook-name>): add playbook`.
178
178
179
179
180
180
### Deliverables
@@ -190,6 +190,15 @@ When creating a new role, make sure to deliver:
190
190
* Update `CHANGELOG.md`.
191
191
192
192
193
+
### OS Coverage
194
+
195
+
When creating a new role or changing an existing one, pull through the **full operating-system matrix** declared in [COMPATIBILITY.md](COMPATIBILITY.md) (currently Debian 12 and 13, RHEL 8, 9 and 10, and Ubuntu 22.04, 24.04 and 26.04). COMPATIBILITY.md is the authoritative list; support what it lists, and add a column there before supporting a new release.
196
+
197
+
* Abstract OS differences (package names, configuration paths, service / unit names, users, ...) into per-OS vars files; see "OS-specific Variables" below for the mechanism and the explicit-`vars/Ubuntu.yml` rule. Reference roles: `sshd`, `clamav`.
198
+
* Validate empirically on each family before claiming support. Spin up a container per OS (podman, e.g. `rockylinux/rockylinux:10`, `debian:13`, `ubuntu:24.04`) and confirm the role runs end to end. A full systemd run (service enable / start / reload) needs a systemd-enabled container.
199
+
* Only mark a cell `x` in COMPATIBILITY.md once it is proven to run; use `(x)` for "expected to work but not verified".
200
+
201
+
193
202
### Changelog
194
203
195
204
LFOps overrides the project-agnostic "Changelog" rule above (alphabetical sorting): entries are sorted newest first, because operators running playbooks need to see what changed most recently.
* The tags should be set in the role itself. Do not set them in the playbook.
398
407
* Blocks/tasks that install base packages do not require tags such as `apache:pkgs`, `apache:setup` or `apache:install`. There is no real world scenario where it makes sense to only run the installation via Ansible, some configuration is always required.
399
408
* For each task, consider to which areas it belongs. A task will usually have multiple tags.
409
+
* Reuse a section name from the controlled vocabulary below whenever one fits, so that `--tags` / `--skip-tags` behave the same way across roles. Only invent a role-specific section name (e.g. `apache_httpd:vhosts`, `mariadb_server:galera_new_cluster`) when a task covers an area that none of the standard names describe.
410
+
411
+
Controlled vocabulary of standard `role_name:section` tags (alphabetical):
412
+
413
+
* `role_name:certs`: Deploys and renews the role's TLS certificates and private keys.
414
+
* `role_name:configure`: Renders and deploys the role's configuration files and applies settings. The most common section; everything that is neither install, state, nor one of the more specific sections below belongs here.
415
+
* `role_name:containers`: Manages the role's containers and their systemd container units.
416
+
* `role_name:cron`: Deploys the role's scheduled jobs (cron entries or systemd timers).
417
+
* `role_name:database`: Creates, updates and deletes the databases managed by the role.
418
+
* `role_name:dump`: Sets up scheduled dumps / backups of the role's data.
419
+
* `role_name:enroll`: Registers (enrolls) the node with a remote service or controller.
* `role_name:logrotate`: Deploys the role's logrotate configuration.
422
+
* `role_name:modules`: Installs, enables and removes the role's pluggable modules (e.g. PHP, SELinux, Apache modules).
423
+
* `role_name:networks`: Manages the role's networks (cloud VM, libvirt or container networks).
424
+
* `role_name:plugins`: Installs and removes the role's optional application plugins / add-ons (distinct from OS-level `:modules`; e.g. Grafana or CMS plugins).
425
+
* `role_name:remove`: Uninstalls the managed software and removes its artifacts.
426
+
* `role_name:state`: Manages the runtime state of the role's services, timers and sockets (start / stop / enable / disable).
427
+
* `role_name:update`: Updates the managed application to a newer version.
428
+
* `role_name:upgrade`: Runs the post-update migration / upgrade steps after the package itself was updated.
429
+
* `role_name:user`: Creates, updates and deletes the application or service user accounts managed by the role.
430
+
431
+
The Ansible built-in tags `always` and `never` are reserved for their built-in meaning: tag the platform-variable loading and `assert` validation tasks with `always` so the variables and checks are present even when the role runs with a specific `--tags` selection.
400
432
401
433
402
434
#### Variables
@@ -631,6 +663,8 @@ Variables with the same name are overridden by the files in `vars/` in order fro
631
663
* `distribution_major_version` (e.g. `CentOS7`) is more specific than distribution
632
664
* `distribution_version` (e.g. `CentOS7.9`) is the most specific
633
665
666
+
When a role has a `vars/Debian.yml`, always create an explicit `vars/Ubuntu.yml` too, even if it is currently an identical copy. Ubuntu (a `distribution`) is loaded on top of its `Debian` os_family, so a full copy is redundant today, but it keeps Ubuntu visible at a glance and gives later Ubuntu-specific drift a dedicated home instead of silently inheriting Debian values.
667
+
634
668
To load the variables include the `platform-variables.yml` in the `tasks/main.yml` like this:
0 commit comments