2 - name: Set next release
6 msg: "{{lookup('vars', ansible_distribution+'_releases', default=[])}}"
8 msg: "{{ansible_distribution_release}}"
10 release_index: "{{lookup('ansible.utils.index_of', data=lookup('vars', ansible_distribution+'_releases', default=[]), test='eq', value=ansible_distribution_release)}}"
11 # If there is not a next release available (as defined below in Debian_releasess
12 # or Ubuntu_releases), the execution of the playbook will fail at this step.
14 next_release: "{{lookup('vars', ansible_distribution+'_releases')[release_index|int + 1]}}"
16 msg: "{{next_release}}"
18 # 'stable' releases ordered from oldest to newest
28 - name: Run any outstanding upgrades
38 - name: Pre-upgrade backups
41 - name: Check if /etc is a git repo
44 cmd: test -d /etc/.git
46 - name: Tag etc configuration
47 when: etckeeper.rc == 0
54 - "pre-{{next_release}}"
58 - name: Backup package state
61 cmd: "tar czf /var/backups/pre-{{next_release}}-backup.tgz /etc /var/lib/dpkg /var/lib/apt/extended_states"
62 # Mitogen doesn't seem to work with the 'archive' module, since tarfile is
63 # "present in the Mitogent importer blacklist", so a shell command is used
67 cmd: "dpkg --get-selections '*' > /var/backups/dpkg-selections-pre-{{next_release}}.txt"
72 - "/var/backups/pre-{{next_release}}-backup.tgz"
73 - "/var/backups/dpkg-selections-pre-{{next_release}}.txt"
74 - name: Debian major version upgrade
76 when: ansible_distribution == 'Debian'
78 apt_noninteractive_environment:
79 DEBIAN_FRONTEND: noninteractive
80 APT_LISTCHANGES_FRONTEND: mail
83 # @TODO: Should 3rd party sources be removed?
84 # @TODO: Ensure kernel package is installed
85 # @TODO: Should a 2nd sshd be started on a non-standard port in case of failure?
91 cmd: 'apt-mark showhold'
92 - name: remove all holds
94 cmd: "apt-mark unhold '*'"
95 - name: Replace release in apt sources.list
97 regexp: "{{ansible_distribution_release}}"
98 replace: "{{next_release}}"
99 path: /etc/apt/sources.list
100 - name: Replace release in apt sources.list.d
102 cmd: "sed -i 's/{{ansible_distribution_release}}/{{next_release}}/' /etc/apt/sources.list.d/*"
107 # @TODO: Check required disk space and available disk space
108 - name: Download packages
110 cmd: 'apt-get -y -d upgrade'
112 environment: "{{apt_noninteractive_environment}}"
113 - name: Minimal upgrade run
115 cmd: 'apt upgrade -y --without-new-pkgs'
117 environment: "{{apt_noninteractive_environment}}"
118 - name: Full upgrade run
120 cmd: 'apt full-upgrade -y'
122 environment: "{{apt_noninteractive_environment}}"
123 # @TODO: reconfigure grub if installed
124 # `dpkg-reconfigure grub-pc` on many systems, but not all
125 # @TODO: Our instances often have an OS version identifier,
126 # it would be handy to do a replace in /etc/hostname
129 command: /usr/sbin/reboot
133 register: last_result
134 - name: wait for the server to reboot
135 local_action: wait_for host={{ inventory_hostname }}
140 when: last_result.changed
142 - name: Purge configuration of removed packages
144 cmd: "apt -y purge '~c'"
146 environment: "{{apt_noninteractive_environment}}"
147 - name: Purge obsolete packages
149 cmd: "apt -y purge '~o'"
151 environment: "{{apt_noninteractive_environment}}"
152 - name: Ubuntu major version upgrade
154 when: ansible_distribution == 'Ubuntu'
156 - name: Do release upgrade
158 cmd: 'do-release-upgrade -m server --frontend=DistUpgradeViewNonInteractive'
159 - name: Post-upgrade tasks
162 - name: Mark rsyslog as auto
163 when: next_release == 'bookworm'
165 cmd: 'apt-mark auto rsyslog'
166 - name: Autoremove any packages
170 - name: Clean apt cache