Merge ~chad.smith/ubuntu/+source/update-notifier:update-notifier-esm-support-hirsute into ubuntu/+source/update-notifier:ubuntu/hirsute-proposed
- Git
- lp:~chad.smith/ubuntu/+source/update-notifier
- update-notifier-esm-support-hirsute
- Merge into ubuntu/hirsute-proposed
Status: | Approved |
---|---|
Approved by: | Bryce Harrington |
Approved revision: | 73a133fef94e01ab004c04d1f284a930b1163177 |
Proposed branch: | ~chad.smith/ubuntu/+source/update-notifier:update-notifier-esm-support-hirsute |
Merge into: | ubuntu/+source/update-notifier:ubuntu/hirsute-proposed |
Diff against target: |
885 lines (+521/-143) 4 files modified
data/apt_check.py (+186/-83) debian/changelog (+17/-0) debian/control (+2/-0) tests/test_motd.py (+316/-60) |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
Bryce Harrington (community) | Approve | ||
Lucas Albuquerque Medeiros de Moura | Pending | ||
Brian Murray | Pending | ||
Review via email: mp+401662@code.launchpad.net |
Commit message
Description of the change
Currently, the apt-check script is configured to only handle package count for ESM Infra. We are now updating the logic to also handle ESM Apps packages as well.
Furthermore, we are also updating the messaging that is created in apt-check. We are advertising ESM Apps if the service is disabled and only messaging about ESM Infra if the distro is already on ESM mode.
Finally, this PR also fixes LP #1883315, since we now check to see if the system has esm-infra or esm-apps before performing a package count for package with esm origins
Brian Murray (brian-murray) wrote : | # |
I uploaded update-notifier to the hirsute queue after I merged Lucas's changes to the devel branch.
https:/
In the event that some code docs were added I should reject the old hirsute upload and we should get a new one so the code is consistent across releases.
Chad Smith (chad.smith) wrote : | # |
Thank you so much Bryce and Brian for the quick reviews here. So does that
mean we should add another upload to devel then?
If so, I'll sort with Lucas Monday morning about what we need to do there
to ensure consistency
Thanks again guys,
Chad
On Fri, Apr 23, 2021 at 3:20 PM Brian Murray <email address hidden> wrote:
> I uploaded update-notifier to the hirsute queue after I merged Lucas's
> changes to the devel branch.
>
>
> https:/
>
> In the event that some code docs were added I should reject the old
> hirsute upload and we should get a new one so the code is consistent across
> releases.
> --
>
> https:/
> You are the owner of
> ~chad.smith/
>
- 4119eec... by Lucas Albuquerque Medeiros de Moura
-
Separate security updates from esm updates
Currently, we display packaging count for both ESM
and security updates. However, if the package upgrade
comes from ESM, we still count it as a security update.
This can provide confusing messages to users, since
we don't say in that message that security updates contain
both source of packages. To better handle that, we are
now only treating as security updates only security upgrades
that are not related to ESM packages. To further make that
distinction, we are updating the message to show
standard security updates instead of just security updates - 1b2c05a... by Chad Smith
-
changelog: version 3.192.40.1 for first hirsute SRU
- 73a133f... by Chad Smith
-
apt_check: use applied instead of installed. correct singular msg
Bryce Harrington (bryce) wrote : | # |
Make sure to include the code docs that lamoura added for the other MPs, so those changes are preserved going forward:
Bryce Harrington (bryce) wrote : | # |
Since the xenial sru is under a deadline to get uploaded, and since the code docs aren't a necessary part of the fix, I went ahead and uploaded this branch as is, but do please incorporate them in your branch so they'll be there for the next update.
triage-
Updated tag 'upload/3.192.40.1' (was d633f7f)
triage-
Enumerating objects: 39, done.
Counting objects: 100% (39/39), done.
Delta compression using up to 12 threads
Compressing objects: 100% (19/19), done.
Writing objects: 100% (31/31), 8.71 KiB | 1.45 MiB/s, done.
Total 31 (delta 24), reused 16 (delta 12), pack-reused 0
To ssh://git.
* [new tag] upload/3.192.40.1 -> upload/3.192.40.1
triage-
D: Setting host argument.
Checking signature on .changes
gpg: /home/bryce/
Checking signature on .dsc
gpg: /home/bryce/
Uploading to ubuntu (via ftp to upload.ubuntu.com):
Uploading update-
Uploading update-
Uploading update-
Uploading update-
Successfully uploaded packages.
Unmerged commits
- 73a133f... by Chad Smith
-
apt_check: use applied instead of installed. correct singular msg
- 1b2c05a... by Chad Smith
-
changelog: version 3.192.40.1 for first hirsute SRU
- 4119eec... by Lucas Albuquerque Medeiros de Moura
-
Separate security updates from esm updates
Currently, we display packaging count for both ESM
and security updates. However, if the package upgrade
comes from ESM, we still count it as a security update.
This can provide confusing messages to users, since
we don't say in that message that security updates contain
both source of packages. To better handle that, we are
now only treating as security updates only security upgrades
that are not related to ESM packages. To further make that
distinction, we are updating the message to show
standard security updates instead of just security updates - 3dddd13... by Chad Smith
-
Add changelog for release 3.192.41
- 7311d1c... by Lucas Albuquerque Medeiros de Moura
-
Update apt-check script for ESM Apps handling
Currently, the apt-check script is configured to only handle
package count for ESM Infra. We are now updating the logic
to also handle ESM Apps packages as well.Furthermore, we are also updating the messaging that is created in
apt-check. We are advertising ESM Apps if the service is disabled
and only messaging about ESM Infra if the distro is already on ESM mode
Preview Diff
1 | diff --git a/data/apt_check.py b/data/apt_check.py |
2 | index 2c18ef6..60d2ecd 100755 |
3 | --- a/data/apt_check.py |
4 | +++ b/data/apt_check.py |
5 | @@ -10,13 +10,16 @@ import sys |
6 | from optparse import OptionParser |
7 | import gettext |
8 | import subprocess |
9 | +import distro_info |
10 | |
11 | SYNAPTIC_PINFILE = "/var/lib/synaptic/preferences" |
12 | DISTRO = subprocess.check_output( |
13 | ["lsb_release", "-c", "-s"], |
14 | universal_newlines=True).strip() |
15 | |
16 | -ESM_ORIGINS = ("UbuntuESM", "UbuntuESMApps") |
17 | +ESM_INFRA_ORIGIN = "UbuntuESM" |
18 | +ESM_APPS_ORIGIN = "UbuntuESMApps" |
19 | +ESM_ORIGINS = (ESM_INFRA_ORIGIN, ESM_APPS_ORIGIN) |
20 | |
21 | |
22 | def _(msg): |
23 | @@ -47,8 +50,8 @@ def saveDistUpgrade(cache, depcache): |
24 | def isSecurityUpgrade(ver): |
25 | " check if the given version is a security update (or masks one) " |
26 | security_pockets = [("Ubuntu", "%s-security" % DISTRO), |
27 | - ("UbuntuESM", "%s-infra-security" % DISTRO), |
28 | - ("UbuntuESMApps", "%s-apps-security" % DISTRO), |
29 | + (ESM_INFRA_ORIGIN, "%s-infra-security" % DISTRO), |
30 | + (ESM_APPS_ORIGIN, "%s-apps-security" % DISTRO), |
31 | ("gNewSense", "%s-security" % DISTRO), |
32 | ("Debian", "%s-updates" % DISTRO)] |
33 | for (file, index) in ver.file_list: |
34 | @@ -58,14 +61,22 @@ def isSecurityUpgrade(ver): |
35 | return False |
36 | |
37 | |
38 | -def isESMUpgrade(ver): |
39 | +def _isESMUpgrade(ver, esm_origin): |
40 | " check if the given version is a security update (or masks one) " |
41 | for (file, index) in ver.file_list: |
42 | - if file.origin in ESM_ORIGINS and file.archive.startswith(DISTRO): |
43 | + if file.origin == esm_origin and file.archive.startswith(DISTRO): |
44 | return True |
45 | return False |
46 | |
47 | |
48 | +def isESMAppsUpgrade(ver): |
49 | + return _isESMUpgrade(ver, esm_origin=ESM_APPS_ORIGIN) |
50 | + |
51 | + |
52 | +def isESMInfraUpgrade(ver): |
53 | + return _isESMUpgrade(ver, esm_origin=ESM_INFRA_ORIGIN) |
54 | + |
55 | + |
56 | def write_package_names(outstream, cache, depcache): |
57 | " write out package names that change to outstream " |
58 | pkgs = [pkg for pkg in cache.packages if depcache.marked_install(pkg) |
59 | @@ -73,11 +84,86 @@ def write_package_names(outstream, cache, depcache): |
60 | outstream.write("\n".join([p.name for p in pkgs])) |
61 | |
62 | |
63 | +def is_esm_distro(): |
64 | + ubuntu_distro = distro_info.UbuntuDistroInfo() |
65 | + |
66 | + is_esm_supported = bool( |
67 | + DISTRO in ubuntu_distro.supported_esm() |
68 | + ) |
69 | + |
70 | + is_not_currently_supported = bool( |
71 | + DISTRO in ubuntu_distro.unsupported() |
72 | + ) |
73 | + |
74 | + return is_esm_supported and is_not_currently_supported |
75 | + |
76 | + |
77 | +def is_lts_distro(): |
78 | + return distro_info.UbuntuDistroInfo().is_lts(DISTRO) |
79 | + |
80 | + |
81 | +def _output_esm_package_count(outstream, service_type, esm_pkg_count): |
82 | + if esm_pkg_count > 0: |
83 | + outstream.write("\n") |
84 | + outstream.write(gettext.dngettext("update-notifier", |
85 | + "%d of these updates " |
86 | + "is an UA %s: ESM " |
87 | + "security update.", |
88 | + "%d of these updates " |
89 | + "are UA %s: ESM " |
90 | + "security updates.", |
91 | + esm_pkg_count) % |
92 | + (esm_pkg_count, service_type)) |
93 | + |
94 | + |
95 | +def _output_esm_package_alert( |
96 | + outstream, service_type, disabled_pkg_count |
97 | +): |
98 | + outstream.write("\n") |
99 | + if disabled_pkg_count > 0: |
100 | + outstream.write("\n") |
101 | + outstream.write(gettext.dngettext("update-notifier", |
102 | + "%i additional security " |
103 | + "update can be applied " |
104 | + "with UA %s: ESM\nLearn " |
105 | + "more about enabling UA " |
106 | + "%s: ESM service at " |
107 | + "https://ubuntu.com/esm", |
108 | + "%i additional security " |
109 | + "updates can be applied " |
110 | + "with UA %s: ESM\nLearn " |
111 | + "more about enabling UA " |
112 | + "%s: ESM service at " |
113 | + "https://ubuntu.com/esm", |
114 | + disabled_pkg_count) % |
115 | + (disabled_pkg_count, service_type, service_type)) |
116 | + else: |
117 | + outstream.write("\n") |
118 | + outstream.write(gettext.dgettext("update-notifier", |
119 | + "Enable UA %s: ESM to " |
120 | + "receive additional future " |
121 | + "security updates.") % |
122 | + service_type) |
123 | + |
124 | + outstream.write("\n") |
125 | + outstream.write( |
126 | + gettext.dgettext("update-notifier", |
127 | + "See https://ubuntu.com/security/esm " |
128 | + "or run: sudo ua status") |
129 | + ) |
130 | + |
131 | + |
132 | def write_human_readable_summary(outstream, upgrades, security_updates, |
133 | - esm_updates, have_esm, disabled_esm_updates): |
134 | + esm_infra_updates, esm_apps_updates, |
135 | + have_esm_infra, have_esm_apps, |
136 | + disabled_esm_infra_updates, |
137 | + disabled_esm_apps_updates): |
138 | + |
139 | + esm_distro = is_esm_distro() |
140 | + lts_distro = is_lts_distro() |
141 | " write out human summary summary to outstream " |
142 | - if have_esm is not None: |
143 | - if have_esm: |
144 | + if have_esm_infra is not None and esm_distro: |
145 | + if have_esm_infra: |
146 | outstream.write(gettext.dgettext("update-notifier", |
147 | "UA Infra: Extended " |
148 | "Security Maintenance (ESM) is " |
149 | @@ -87,64 +173,51 @@ def write_human_readable_summary(outstream, upgrades, security_updates, |
150 | "UA Infra: Extended " |
151 | "Security Maintenance (ESM) is " |
152 | "not enabled.")) |
153 | - outstream.write("\n\n") |
154 | - |
155 | - outstream.write(gettext.dngettext("update-notifier", |
156 | - "%i update can be installed " |
157 | - "immediately.", |
158 | - "%i updates can be installed " |
159 | - "immediately.", |
160 | - upgrades) % upgrades) |
161 | - outstream.write("\n") |
162 | - if esm_updates > 0: |
163 | + if upgrades > 0: |
164 | + outstream.write("\n\n") |
165 | + if upgrades > 0: |
166 | + outstream.write( |
167 | + gettext.dngettext("update-notifier", |
168 | + "%i update can be applied immediately.", |
169 | + "%i updates can be applied immediately.", |
170 | + upgrades) % upgrades |
171 | + ) |
172 | + |
173 | + _output_esm_package_count( |
174 | + outstream, service_type="Infra", esm_pkg_count=esm_infra_updates) |
175 | + _output_esm_package_count( |
176 | + outstream, service_type="Apps", esm_pkg_count=esm_apps_updates) |
177 | + |
178 | + if security_updates > 0: |
179 | + outstream.write("\n") |
180 | outstream.write(gettext.dngettext("update-notifier", |
181 | - "%i of these updates is fixed " |
182 | - "through UA Infra: ESM.", |
183 | + "%i of these updates is a " |
184 | + "standard security update.", |
185 | "%i of these updates are " |
186 | - "fixed through UA " |
187 | - "Infra: ESM.", |
188 | - esm_updates) % |
189 | - esm_updates) |
190 | - outstream.write("\n") |
191 | - outstream.write(gettext.dngettext("update-notifier", |
192 | - "%i of these updates is a " |
193 | - "security update.", |
194 | - "%i of these updates are " |
195 | - "security updates.", |
196 | - security_updates) % |
197 | - security_updates) |
198 | - if upgrades > 0 or security_updates > 0 or esm_updates > 0: |
199 | + "standard security updates.", |
200 | + security_updates) % |
201 | + security_updates) |
202 | + |
203 | + if any([upgrades, security_updates, esm_infra_updates, esm_apps_updates]): |
204 | outstream.write("\n") |
205 | outstream.write(gettext.dgettext("update-notifier", |
206 | "To see these additional updates " |
207 | "run: apt list --upgradable")) |
208 | - if have_esm is not None and not have_esm: |
209 | - outstream.write("\n") |
210 | - if disabled_esm_updates > 0: |
211 | - outstream.write("\n") |
212 | - outstream.write(gettext.dngettext("update-notifier", |
213 | - "Enable UA Infra: ESM " |
214 | - "to receive %i additional " |
215 | - "security update.", |
216 | - "Enable UA Infra: ESM " |
217 | - "to receive %i additional " |
218 | - "security updates.", |
219 | - disabled_esm_updates) % |
220 | - disabled_esm_updates) |
221 | - else: |
222 | - outstream.write("\n") |
223 | - outstream.write(gettext.dgettext("update-notifier", |
224 | - "Enable UA Infra: ESM to " |
225 | - "receive additional future " |
226 | - "security updates.")) |
227 | - outstream.write("\n") |
228 | - outstream.write(gettext.dgettext("update-notifier", |
229 | - "See https://ubuntu.com/security/esm " |
230 | - "or run: sudo ua status")) |
231 | + |
232 | + if have_esm_apps is not None and not have_esm_apps and lts_distro: |
233 | + _output_esm_package_alert( |
234 | + outstream, service_type="Apps", |
235 | + disabled_pkg_count=disabled_esm_apps_updates) |
236 | + |
237 | + if have_esm_infra is not None and not have_esm_infra and esm_distro: |
238 | + _output_esm_package_alert( |
239 | + outstream, service_type="Infra", |
240 | + disabled_pkg_count=disabled_esm_infra_updates) |
241 | + |
242 | outstream.write("\n") |
243 | |
244 | |
245 | -def has_disabled_esm_security_update(depcache, pkg): |
246 | +def has_disabled_esm_security_update(depcache, pkg, esm_origin): |
247 | " check if we have a disabled ESM security update " |
248 | inst_ver = pkg.current_ver |
249 | if not inst_ver: |
250 | @@ -155,12 +228,39 @@ def has_disabled_esm_security_update(depcache, pkg): |
251 | break |
252 | |
253 | for (file, index) in ver.file_list: |
254 | - if (file.origin in ESM_ORIGINS and file.archive.startswith(DISTRO) |
255 | + if (file.origin == esm_origin and file.archive.startswith(DISTRO) |
256 | and depcache.policy.get_priority(file) == -32768): |
257 | return True |
258 | return False |
259 | |
260 | |
261 | +def has_disabled_esm_apps_security_update(depcache, pkg): |
262 | + return has_disabled_esm_security_update(depcache, pkg, ESM_APPS_ORIGIN) |
263 | + |
264 | + |
265 | +def has_disabled_esm_infra_security_update(depcache, pkg): |
266 | + return has_disabled_esm_security_update(depcache, pkg, ESM_INFRA_ORIGIN) |
267 | + |
268 | + |
269 | +def has_esm_service(cache, depcache, esm_origin): |
270 | + have_esm = None |
271 | + for file in cache.file_list: |
272 | + origin = file.origin |
273 | + if origin == esm_origin and file.archive.startswith(DISTRO): |
274 | + # In case of multiple ESM repos, one enabled is sufficient. |
275 | + if depcache.policy.get_priority(file) == -32768: |
276 | + # We found a disabled ESM repository, but we'll only count |
277 | + # ESM as disabled here if we have not found any other ESM |
278 | + # repo, so one ESM repo being enabled means ESM is enabled. |
279 | + if have_esm is None: |
280 | + have_esm = False |
281 | + else: |
282 | + have_esm = True |
283 | + break |
284 | + |
285 | + return have_esm |
286 | + |
287 | + |
288 | def init(): |
289 | " init the system, be nice " |
290 | # FIXME: do a ionice here too? |
291 | @@ -203,31 +303,26 @@ def run(options=None): |
292 | |
293 | # Check if we have ESM enabled or disabled; and if it exists in the |
294 | # first place. |
295 | - have_esm = None # None == does not exist |
296 | - for file in cache.file_list: |
297 | - if file.origin in ESM_ORIGINS and file.archive.startswith(DISTRO): |
298 | - # In case of multiple ESM repos, one enabled is sufficient. |
299 | - if depcache.policy.get_priority(file) == -32768: |
300 | - # We found a disabled ESM repository, but we'll only count |
301 | - # ESM as disabled here if we have not found any other ESM |
302 | - # repo, so one ESM repo being enabled means ESM is enabled. |
303 | - if have_esm is None: |
304 | - have_esm = False |
305 | - else: |
306 | - have_esm = True |
307 | - break |
308 | + have_esm_infra = has_esm_service( |
309 | + cache, depcache, esm_origin=ESM_INFRA_ORIGIN) |
310 | + have_esm_apps = has_esm_service( |
311 | + cache, depcache, esm_origin=ESM_APPS_ORIGIN) |
312 | |
313 | # analyze the ugprade |
314 | upgrades = 0 |
315 | security_updates = 0 |
316 | - esm_updates = 0 |
317 | - disabled_esm_updates = 0 |
318 | + esm_apps_updates = 0 |
319 | + esm_infra_updates = 0 |
320 | + disabled_esm_apps_updates = 0 |
321 | + disabled_esm_infra_updates = 0 |
322 | |
323 | # we need another cache that has more pkg details |
324 | with apt.Cache() as aptcache: |
325 | for pkg in cache.packages: |
326 | - if has_disabled_esm_security_update(depcache, pkg): |
327 | - disabled_esm_updates += 1 |
328 | + if has_disabled_esm_apps_security_update(depcache, pkg): |
329 | + disabled_esm_apps_updates += 1 |
330 | + if has_disabled_esm_infra_security_update(depcache, pkg): |
331 | + disabled_esm_infra_updates += 1 |
332 | |
333 | # skip packages that are not marked upgraded/installed |
334 | if not (depcache.marked_install(pkg) |
335 | @@ -241,10 +336,14 @@ def run(options=None): |
336 | continue |
337 | # check for security upgrades |
338 | if isSecurityUpgrade(cand_ver): |
339 | - if isESMUpgrade(cand_ver): |
340 | - esm_updates += 1 |
341 | + if have_esm_apps and isESMAppsUpgrade(cand_ver): |
342 | + esm_apps_updates += 1 |
343 | + elif have_esm_infra and isESMInfraUpgrade(cand_ver): |
344 | + esm_infra_updates += 1 |
345 | + else: |
346 | + security_updates += 1 |
347 | + |
348 | upgrades += 1 |
349 | - security_updates += 1 |
350 | continue |
351 | |
352 | # check to see if the update is a phased one |
353 | @@ -268,9 +367,11 @@ def run(options=None): |
354 | and apt_pkg.version_compare(ver.ver_str, |
355 | inst_ver.ver_str) <= 0): |
356 | continue |
357 | - if isESMUpgrade(ver): |
358 | - esm_updates += 1 |
359 | - if isSecurityUpgrade(ver): |
360 | + if have_esm_apps and isESMAppsUpgrade(cand_ver): |
361 | + esm_apps_updates += 1 |
362 | + elif have_esm_infra and isESMInfraUpgrade(cand_ver): |
363 | + esm_infra_updates += 1 |
364 | + elif isSecurityUpgrade(ver): |
365 | security_updates += 1 |
366 | break |
367 | |
368 | @@ -279,8 +380,10 @@ def run(options=None): |
369 | write_package_names(sys.stderr, cache, depcache) |
370 | elif options and options.readable_output: |
371 | write_human_readable_summary(sys.stdout, upgrades, security_updates, |
372 | - esm_updates, have_esm, |
373 | - disabled_esm_updates) |
374 | + esm_infra_updates, esm_apps_updates, |
375 | + have_esm_infra, have_esm_apps, |
376 | + disabled_esm_infra_updates, |
377 | + disabled_esm_apps_updates) |
378 | else: |
379 | # print the number of regular upgrades and the number of |
380 | # security upgrades |
381 | diff --git a/debian/changelog b/debian/changelog |
382 | index d603649..8473bfe 100644 |
383 | --- a/debian/changelog |
384 | +++ b/debian/changelog |
385 | @@ -1,3 +1,20 @@ |
386 | +update-notifier (3.192.40.1) hirsute; urgency=medium |
387 | + |
388 | + [ Lucas Moura ] |
389 | + |
390 | + * data/apt_check.py: |
391 | + - Add support to handle packages from ESM Apps in addition to ESM Infra |
392 | + and only display alerts if the distro is ESM. (LP: #1924766) |
393 | + - Do not display a count of ESM packages if the system does not have ESM |
394 | + enabled. (LP: #1883315) |
395 | + - Make distinction between standard security updates and ESM updates |
396 | + when performing package counts. (LP: #1926208) |
397 | + - use 'applied' instead of 'installed', redact 0 of these updates are |
398 | + security updates, and correct singular messages |
399 | + * debian/control: Add a dependency on python3-distro-info. |
400 | + |
401 | + -- Chad Smith <chad.smith@canonical.com> Thu, 22 Apr 2021 17:47:19 -0600 |
402 | + |
403 | update-notifier (3.192.40) hirsute; urgency=medium |
404 | |
405 | * Skip notify for an update if the command we need to run doesn't exist |
406 | diff --git a/debian/control b/debian/control |
407 | index 79975d0..c6c9012 100644 |
408 | --- a/debian/control |
409 | +++ b/debian/control |
410 | @@ -18,6 +18,7 @@ Build-Depends: debhelper (>= 11~), |
411 | python3-apt, |
412 | python3-debconf, |
413 | python3-debian, |
414 | + python3-distro-info, |
415 | python3-mock |
416 | Standards-Version: 4.5.0 |
417 | Vcs-Git: https://git.launchpad.net/update-notifier -b master |
418 | @@ -51,6 +52,7 @@ Depends: ${shlibs:Depends}, |
419 | python3:any, |
420 | python3-apt, python3-dbus, python3-debian, |
421 | python3-debconf | debconf (<< 1.5.64~), |
422 | + python3-distro-info, |
423 | patch, update-manager-core (>= 1:17.04.2) |
424 | Recommends: libpam-modules (>= 1.0.1-9ubuntu3) |
425 | Suggests: policykit-1 |
426 | diff --git a/tests/test_motd.py b/tests/test_motd.py |
427 | index ec1a09f..3efe2e8 100755 |
428 | --- a/tests/test_motd.py |
429 | +++ b/tests/test_motd.py |
430 | @@ -6,6 +6,8 @@ import io |
431 | import unittest |
432 | import textwrap |
433 | |
434 | +from unittest import mock |
435 | + |
436 | |
437 | def get_message(*args, **kwds): |
438 | with io.StringIO() as stream: |
439 | @@ -16,132 +18,386 @@ def get_message(*args, **kwds): |
440 | class TestMotd(unittest.TestCase): |
441 | """ Validate /etc/motd text """ |
442 | |
443 | - def test_esm_disabled_upto_date_esm_avail(self): |
444 | + @mock.patch("apt_check.is_lts_distro", return_value=True) |
445 | + @mock.patch("apt_check.is_esm_distro", return_value=True) |
446 | + def test_esm_infra_disabled_upto_date_esm_avail( |
447 | + self, _m_esm_distro, _m_is_lts |
448 | + ): |
449 | self.assertEqual( |
450 | get_message(upgrades=0, security_updates=0, |
451 | - esm_updates=0, have_esm=False, |
452 | - disabled_esm_updates=23), |
453 | + esm_infra_updates=0, esm_apps_updates=0, |
454 | + have_esm_infra=False, have_esm_apps=False, |
455 | + disabled_esm_infra_updates=1, |
456 | + disabled_esm_apps_updates=0), |
457 | textwrap.dedent( |
458 | - """ |
459 | + """\ |
460 | UA Infra: Extended Security Maintenance (ESM) is not enabled. |
461 | |
462 | - 0 updates can be installed immediately. |
463 | - 0 of these updates are security updates. |
464 | - |
465 | - Enable UA Infra: ESM to receive 23 additional security updates. |
466 | + Enable UA Apps: ESM to receive additional future security updates. |
467 | See https://ubuntu.com/security/esm or run: sudo ua status |
468 | - """).lstrip()) |
469 | |
470 | - def test_esm_disabled_security_esm_avail(self): |
471 | + 1 additional security update can be applied with UA Infra: ESM |
472 | + Learn more about enabling UA Infra: ESM service at https://ubuntu.com/esm |
473 | + """)) |
474 | + |
475 | + @mock.patch("apt_check.is_lts_distro", return_value=True) |
476 | + @mock.patch("apt_check.is_esm_distro", return_value=True) |
477 | + def test_esm_infra_disabled_security_esm_avail( |
478 | + self, _m_esm_distro, _m_is_lts |
479 | + ): |
480 | self.assertEqual( |
481 | - get_message(upgrades=15, security_updates=7, |
482 | - esm_updates=0, have_esm=False, |
483 | - disabled_esm_updates=23), |
484 | + get_message(upgrades=15, security_updates=1, |
485 | + esm_infra_updates=0, esm_apps_updates=0, |
486 | + have_esm_infra=False, have_esm_apps=False, |
487 | + disabled_esm_infra_updates=23, |
488 | + disabled_esm_apps_updates=0), |
489 | textwrap.dedent( |
490 | - """ |
491 | + """\ |
492 | UA Infra: Extended Security Maintenance (ESM) is not enabled. |
493 | |
494 | - 15 updates can be installed immediately. |
495 | - 7 of these updates are security updates. |
496 | + 15 updates can be applied immediately. |
497 | + 1 of these updates is a standard security update. |
498 | To see these additional updates run: apt list --upgradable |
499 | |
500 | - Enable UA Infra: ESM to receive 23 additional security updates. |
501 | + Enable UA Apps: ESM to receive additional future security updates. |
502 | See https://ubuntu.com/security/esm or run: sudo ua status |
503 | - """).lstrip()) |
504 | |
505 | - def test_esm_disabled_security_no_esm_avail(self): |
506 | + 23 additional security updates can be applied with UA Infra: ESM |
507 | + Learn more about enabling UA Infra: ESM service at https://ubuntu.com/esm |
508 | + """)) |
509 | + |
510 | + @mock.patch("apt_check.is_lts_distro", return_value=True) |
511 | + @mock.patch("apt_check.is_esm_distro", return_value=True) |
512 | + def test_esm_infra_disabled_security_no_esm_avail( |
513 | + self, _m_esm_distro, _m_is_lts |
514 | + ): |
515 | self.assertEqual( |
516 | get_message(upgrades=15, security_updates=7, |
517 | - esm_updates=0, have_esm=False, |
518 | - disabled_esm_updates=0), |
519 | + esm_infra_updates=0, esm_apps_updates=0, |
520 | + have_esm_infra=False, have_esm_apps=False, |
521 | + disabled_esm_infra_updates=0, |
522 | + disabled_esm_apps_updates=0), |
523 | textwrap.dedent( |
524 | - """ |
525 | + """\ |
526 | UA Infra: Extended Security Maintenance (ESM) is not enabled. |
527 | |
528 | - 15 updates can be installed immediately. |
529 | - 7 of these updates are security updates. |
530 | + 15 updates can be applied immediately. |
531 | + 7 of these updates are standard security updates. |
532 | To see these additional updates run: apt list --upgradable |
533 | |
534 | + Enable UA Apps: ESM to receive additional future security updates. |
535 | + See https://ubuntu.com/security/esm or run: sudo ua status |
536 | + |
537 | Enable UA Infra: ESM to receive additional future security updates. |
538 | See https://ubuntu.com/security/esm or run: sudo ua status |
539 | - """).lstrip()) |
540 | + """)) |
541 | |
542 | - def test_esm_disabled_nosecurity(self): |
543 | + @mock.patch("apt_check.is_lts_distro", return_value=True) |
544 | + @mock.patch("apt_check.is_esm_distro", return_value=True) |
545 | + def test_esm_infra_disabled_nosecurity( |
546 | + self, _m_esm_distro, _m_is_lts |
547 | + ): |
548 | self.assertEqual( |
549 | get_message(upgrades=15, security_updates=0, |
550 | - esm_updates=0, have_esm=False, |
551 | - disabled_esm_updates=0), |
552 | + esm_infra_updates=0, esm_apps_updates=0, |
553 | + have_esm_infra=False, have_esm_apps=False, |
554 | + disabled_esm_infra_updates=0, |
555 | + disabled_esm_apps_updates=0), |
556 | textwrap.dedent( |
557 | - """ |
558 | + """\ |
559 | UA Infra: Extended Security Maintenance (ESM) is not enabled. |
560 | |
561 | - 15 updates can be installed immediately. |
562 | - 0 of these updates are security updates. |
563 | + 15 updates can be applied immediately. |
564 | To see these additional updates run: apt list --upgradable |
565 | |
566 | + Enable UA Apps: ESM to receive additional future security updates. |
567 | + See https://ubuntu.com/security/esm or run: sudo ua status |
568 | + |
569 | Enable UA Infra: ESM to receive additional future security updates. |
570 | See https://ubuntu.com/security/esm or run: sudo ua status |
571 | - """).lstrip()) |
572 | + """)) |
573 | |
574 | - def test_esm_disabled_noupdates(self): |
575 | + @mock.patch("apt_check.is_lts_distro", return_value=True) |
576 | + @mock.patch("apt_check.is_esm_distro", return_value=True) |
577 | + def test_esm_infra_disabled_noupdates( |
578 | + self, _m_esm_distro, _m_is_lts |
579 | + ): |
580 | self.assertEqual( |
581 | get_message(upgrades=0, security_updates=0, |
582 | - esm_updates=0, have_esm=False, |
583 | - disabled_esm_updates=0), |
584 | + esm_infra_updates=0, esm_apps_updates=0, |
585 | + have_esm_infra=False, have_esm_apps=False, |
586 | + disabled_esm_infra_updates=0, |
587 | + disabled_esm_apps_updates=0), |
588 | textwrap.dedent( |
589 | - """ |
590 | + """\ |
591 | UA Infra: Extended Security Maintenance (ESM) is not enabled. |
592 | |
593 | - 0 updates can be installed immediately. |
594 | - 0 of these updates are security updates. |
595 | + Enable UA Apps: ESM to receive additional future security updates. |
596 | + See https://ubuntu.com/security/esm or run: sudo ua status |
597 | |
598 | Enable UA Infra: ESM to receive additional future security updates. |
599 | See https://ubuntu.com/security/esm or run: sudo ua status |
600 | - """).lstrip()) |
601 | + """)) |
602 | |
603 | - def test_esm_enabled_nosecurity(self): |
604 | + @mock.patch("apt_check.is_lts_distro", return_value=True) |
605 | + @mock.patch("apt_check.is_esm_distro", return_value=True) |
606 | + def test_esm_infra_enabled_nosecurity( |
607 | + self, _m_esm_distro, _m_is_lts |
608 | + ): |
609 | self.assertEqual( |
610 | get_message(upgrades=35, security_updates=0, |
611 | - esm_updates=13, have_esm=True, |
612 | - disabled_esm_updates=0), |
613 | + esm_infra_updates=13, esm_apps_updates=0, |
614 | + have_esm_infra=True, have_esm_apps=False, |
615 | + disabled_esm_infra_updates=0, |
616 | + disabled_esm_apps_updates=0), |
617 | textwrap.dedent( |
618 | - """ |
619 | + """\ |
620 | UA Infra: Extended Security Maintenance (ESM) is enabled. |
621 | |
622 | - 35 updates can be installed immediately. |
623 | - 13 of these updates are fixed through UA Infra: ESM. |
624 | - 0 of these updates are security updates. |
625 | + 35 updates can be applied immediately. |
626 | + 13 of these updates are UA Infra: ESM security updates. |
627 | To see these additional updates run: apt list --upgradable |
628 | - """).lstrip()) |
629 | |
630 | - def test_esm_enabled_somesecurity(self): |
631 | + Enable UA Apps: ESM to receive additional future security updates. |
632 | + See https://ubuntu.com/security/esm or run: sudo ua status |
633 | + """)) |
634 | + |
635 | + @mock.patch("apt_check.is_lts_distro", return_value=True) |
636 | + @mock.patch("apt_check.is_esm_distro", return_value=True) |
637 | + def test_esm_infra_enabled_somesecurity( |
638 | + self, _m_esm_distro, _m_is_lts |
639 | + ): |
640 | self.assertEqual( |
641 | get_message(upgrades=47, security_updates=7, |
642 | - esm_updates=13, have_esm=True, |
643 | - disabled_esm_updates=0), |
644 | + esm_infra_updates=13, esm_apps_updates=0, |
645 | + have_esm_infra=True, have_esm_apps=False, |
646 | + disabled_esm_infra_updates=0, |
647 | + disabled_esm_apps_updates=0), |
648 | textwrap.dedent( |
649 | - """ |
650 | + """\ |
651 | UA Infra: Extended Security Maintenance (ESM) is enabled. |
652 | |
653 | - 47 updates can be installed immediately. |
654 | - 13 of these updates are fixed through UA Infra: ESM. |
655 | - 7 of these updates are security updates. |
656 | + 47 updates can be applied immediately. |
657 | + 13 of these updates are UA Infra: ESM security updates. |
658 | + 7 of these updates are standard security updates. |
659 | To see these additional updates run: apt list --upgradable |
660 | - """).lstrip()) |
661 | |
662 | - def test_esm_enabled_noupdates(self): |
663 | + Enable UA Apps: ESM to receive additional future security updates. |
664 | + See https://ubuntu.com/security/esm or run: sudo ua status |
665 | + """)) |
666 | + |
667 | + @mock.patch("apt_check.is_lts_distro", return_value=True) |
668 | + @mock.patch("apt_check.is_esm_distro", return_value=True) |
669 | + def test_esm_infra_enabled_noupdates( |
670 | + self, _m_esm_distro, _m_is_lts |
671 | + ): |
672 | self.assertEqual( |
673 | get_message(upgrades=0, security_updates=0, |
674 | - esm_updates=0, have_esm=True, |
675 | - disabled_esm_updates=0), |
676 | + esm_infra_updates=0, esm_apps_updates=0, |
677 | + have_esm_infra=True, have_esm_apps=False, |
678 | + disabled_esm_infra_updates=0, |
679 | + disabled_esm_apps_updates=10), |
680 | + textwrap.dedent( |
681 | + """\ |
682 | + UA Infra: Extended Security Maintenance (ESM) is enabled. |
683 | + |
684 | + 10 additional security updates can be applied with UA Apps: ESM |
685 | + Learn more about enabling UA Apps: ESM service at https://ubuntu.com/esm |
686 | + """)) |
687 | + |
688 | + @mock.patch("apt_check.is_lts_distro", return_value=True) |
689 | + @mock.patch("apt_check.is_esm_distro", return_value=True) |
690 | + def test_esm_infra_and_esm_apps_enabled( |
691 | + self, _m_esm_distro, _m_is_lts |
692 | + ): |
693 | + self.assertEqual( |
694 | + get_message(upgrades=30, security_updates=0, |
695 | + esm_infra_updates=15, esm_apps_updates=15, |
696 | + have_esm_infra=True, have_esm_apps=True, |
697 | + disabled_esm_infra_updates=0, |
698 | + disabled_esm_apps_updates=0), |
699 | textwrap.dedent( |
700 | """ |
701 | UA Infra: Extended Security Maintenance (ESM) is enabled. |
702 | |
703 | - 0 updates can be installed immediately. |
704 | - 0 of these updates are security updates. |
705 | + 30 updates can be applied immediately. |
706 | + 15 of these updates are UA Infra: ESM security updates. |
707 | + 15 of these updates are UA Apps: ESM security updates. |
708 | + To see these additional updates run: apt list --upgradable |
709 | + """).lstrip()) |
710 | + |
711 | + @mock.patch("apt_check.is_lts_distro", return_value=True) |
712 | + @mock.patch("apt_check.is_esm_distro", return_value=True) |
713 | + def test_esm_infra_disable_and_esm_apps_enabled( |
714 | + self, _m_esm_distro, _m_is_lts |
715 | + ): |
716 | + self.assertEqual( |
717 | + get_message(upgrades=30, security_updates=12, |
718 | + esm_infra_updates=0, esm_apps_updates=15, |
719 | + have_esm_infra=False, have_esm_apps=True, |
720 | + disabled_esm_infra_updates=0, |
721 | + disabled_esm_apps_updates=0), |
722 | + textwrap.dedent( |
723 | + """ |
724 | + UA Infra: Extended Security Maintenance (ESM) is not enabled. |
725 | + |
726 | + 30 updates can be applied immediately. |
727 | + 15 of these updates are UA Apps: ESM security updates. |
728 | + 12 of these updates are standard security updates. |
729 | + To see these additional updates run: apt list --upgradable |
730 | + |
731 | + Enable UA Infra: ESM to receive additional future security updates. |
732 | + See https://ubuntu.com/security/esm or run: sudo ua status |
733 | + """).lstrip()) |
734 | + |
735 | + @mock.patch("apt_check.is_lts_distro", return_value=True) |
736 | + @mock.patch("apt_check.is_esm_distro", return_value=True) |
737 | + def test_esm_infra_disabled_wih_pkgs_and_esm_apps_enabled( |
738 | + self, _m_esm_distro, _m_is_lts |
739 | + ): |
740 | + self.assertEqual( |
741 | + get_message(upgrades=30, security_updates=15, |
742 | + esm_infra_updates=0, esm_apps_updates=1, |
743 | + have_esm_infra=False, have_esm_apps=True, |
744 | + disabled_esm_infra_updates=40, |
745 | + disabled_esm_apps_updates=0), |
746 | + textwrap.dedent( |
747 | + """ |
748 | + UA Infra: Extended Security Maintenance (ESM) is not enabled. |
749 | + |
750 | + 30 updates can be applied immediately. |
751 | + 1 of these updates is an UA Apps: ESM security update. |
752 | + 15 of these updates are standard security updates. |
753 | + To see these additional updates run: apt list --upgradable |
754 | + |
755 | + 40 additional security updates can be applied with UA Infra: ESM |
756 | + Learn more about enabling UA Infra: ESM service at https://ubuntu.com/esm |
757 | """).lstrip()) |
758 | |
759 | + @mock.patch("apt_check.is_lts_distro", return_value=True) |
760 | + @mock.patch("apt_check.is_esm_distro", return_value=True) |
761 | + def test_esm_infra_disabled_and_esm_apps_disabled_with_pkgs( |
762 | + self, _m_esm_distro, _m_is_lts |
763 | + ): |
764 | + self.assertEqual( |
765 | + get_message(upgrades=30, security_updates=18, |
766 | + esm_infra_updates=0, esm_apps_updates=0, |
767 | + have_esm_infra=False, have_esm_apps=False, |
768 | + disabled_esm_infra_updates=0, |
769 | + disabled_esm_apps_updates=40), |
770 | + textwrap.dedent( |
771 | + """\ |
772 | + UA Infra: Extended Security Maintenance (ESM) is not enabled. |
773 | + |
774 | + 30 updates can be applied immediately. |
775 | + 18 of these updates are standard security updates. |
776 | + To see these additional updates run: apt list --upgradable |
777 | + |
778 | + 40 additional security updates can be applied with UA Apps: ESM |
779 | + Learn more about enabling UA Apps: ESM service at https://ubuntu.com/esm |
780 | + |
781 | + Enable UA Infra: ESM to receive additional future security updates. |
782 | + See https://ubuntu.com/security/esm or run: sudo ua status |
783 | + """)) |
784 | + |
785 | + @mock.patch("apt_check.is_lts_distro", return_value=True) |
786 | + @mock.patch("apt_check.is_esm_distro", return_value=True) |
787 | + def test_no_esm_infra_and_apps_index_in_esm_distro( |
788 | + self, _m_esm_distro, _m_is_lts |
789 | + ): |
790 | + self.assertEqual( |
791 | + get_message(upgrades=30, security_updates=18, |
792 | + esm_infra_updates=0, esm_apps_updates=0, |
793 | + have_esm_infra=None, have_esm_apps=None, |
794 | + disabled_esm_infra_updates=0, |
795 | + disabled_esm_apps_updates=0), |
796 | + textwrap.dedent( |
797 | + """\ |
798 | + 30 updates can be applied immediately. |
799 | + 18 of these updates are standard security updates. |
800 | + To see these additional updates run: apt list --upgradable |
801 | + """)) |
802 | + |
803 | + @mock.patch("apt_check.is_lts_distro", return_value=False) |
804 | + @mock.patch("apt_check.is_esm_distro", return_value=False) |
805 | + def test_no_esm_infra_and_apps_index_in_non_lts_distro( |
806 | + self, _m_esm_distro, _m_is_lts |
807 | + ): |
808 | + self.assertEqual( |
809 | + get_message(upgrades=30, security_updates=18, |
810 | + esm_infra_updates=0, esm_apps_updates=0, |
811 | + have_esm_infra=None, have_esm_apps=None, |
812 | + disabled_esm_infra_updates=0, |
813 | + disabled_esm_apps_updates=0), |
814 | + textwrap.dedent( |
815 | + """\ |
816 | + 30 updates can be applied immediately. |
817 | + 18 of these updates are standard security updates. |
818 | + To see these additional updates run: apt list --upgradable |
819 | + """)) |
820 | + |
821 | + @mock.patch("apt_check.is_lts_distro", return_value=False) |
822 | + @mock.patch("apt_check.is_esm_distro", return_value=False) |
823 | + def test_esm_infra_disabled_and_esm_apps_disabled_with_no_esm_distro( |
824 | + self, _m_esm_distro, _m_is_lts, |
825 | + ): |
826 | + self.assertEqual( |
827 | + get_message(upgrades=30, security_updates=18, |
828 | + esm_infra_updates=0, esm_apps_updates=0, |
829 | + have_esm_infra=False, have_esm_apps=False, |
830 | + disabled_esm_infra_updates=0, |
831 | + disabled_esm_apps_updates=40), |
832 | + textwrap.dedent( |
833 | + """\ |
834 | + 30 updates can be applied immediately. |
835 | + 18 of these updates are standard security updates. |
836 | + To see these additional updates run: apt list --upgradable |
837 | + """)) |
838 | + |
839 | + @mock.patch("apt_check.is_lts_distro", return_value=False) |
840 | + @mock.patch("subprocess.Popen") |
841 | + def test_message_for_distro_that_will_not_go_into_esm_mode( |
842 | + self, m_popen, _m_is_lts |
843 | + ): |
844 | + comm_mock = mock.MagicMock() |
845 | + comm_mock.communicate.return_value = ( |
846 | + "(unknown)".encode("utf-8"), "") |
847 | + m_popen.return_value = comm_mock |
848 | + |
849 | + self.assertEqual( |
850 | + get_message(upgrades=30, security_updates=18, |
851 | + esm_infra_updates=0, esm_apps_updates=0, |
852 | + have_esm_infra=False, have_esm_apps=False, |
853 | + disabled_esm_infra_updates=0, |
854 | + disabled_esm_apps_updates=40), |
855 | + textwrap.dedent( |
856 | + """\ |
857 | + 30 updates can be applied immediately. |
858 | + 18 of these updates are standard security updates. |
859 | + To see these additional updates run: apt list --upgradable |
860 | + """)) |
861 | + |
862 | + @mock.patch("apt_check.is_lts_distro", return_value=True) |
863 | + @mock.patch("apt_check.is_esm_distro", return_value=False) |
864 | + def test_message_for_lts_distro_not_in_esm_mode_yet( |
865 | + self, _m_is_esm, _m_is_lts |
866 | + ): |
867 | + self.assertEqual( |
868 | + get_message(upgrades=30, security_updates=18, |
869 | + esm_infra_updates=0, esm_apps_updates=0, |
870 | + have_esm_infra=False, have_esm_apps=False, |
871 | + disabled_esm_infra_updates=10, |
872 | + disabled_esm_apps_updates=40), |
873 | + textwrap.dedent( |
874 | + """\ |
875 | + 30 updates can be applied immediately. |
876 | + 18 of these updates are standard security updates. |
877 | + To see these additional updates run: apt list --upgradable |
878 | + |
879 | + 40 additional security updates can be applied with UA Apps: ESM |
880 | + Learn more about enabling UA Apps: ESM service at https://ubuntu.com/esm |
881 | + """)) |
882 | + |
883 | |
884 | if __name__ == "__main__": |
885 | import logging |
I'd reviewed the focal/bionic/xenial versions of this branch previously. Lucas had added some code docs for some of the new functions that should be included here as well, so they're preserved in the devel tree going forward.
I'd also appreciate a summary of any other known differences between this MP and the focal/bionic/xenial one. Offhand this looks the same as that but I didn't do a strict comparison.