Merge ~jocave/checkbox-support:improved-assertion-parsing into checkbox-support:master
- Git
- lp:~jocave/checkbox-support
- improved-assertion-parsing
- Merge into master
Status: | Merged |
---|---|
Approved by: | Jonathan Cave |
Approved revision: | 58435e249f5cd325465f00417369dc226083c1a9 |
Merged at revision: | afa6910c4b69dd8d6e7d1c2ae5d2aadfe820e84c |
Proposed branch: | ~jocave/checkbox-support:improved-assertion-parsing |
Merge into: | checkbox-support:master |
Diff against target: |
442 lines (+338/-31) 7 files modified
checkbox_support/snap_utils/asserts.py (+69/-0) checkbox_support/snap_utils/system.py (+16/-31) checkbox_support/snap_utils/tests/asserts_data/MODEL_FOCAL_DESKTOP.txt (+19/-0) checkbox_support/snap_utils/tests/asserts_data/MODEL_UC18.txt (+23/-0) checkbox_support/snap_utils/tests/asserts_data/MODEL_UC20.txt (+43/-0) checkbox_support/snap_utils/tests/asserts_data/SERIAL_FOCAL_DESKTOP.txt (+30/-0) checkbox_support/snap_utils/tests/test_asserts.py (+138/-0) |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
Devices Certification Bot | Needs Fixing | ||
Sylvain Pineau (community) | Approve | ||
Maciej Kisielewski | Approve | ||
Review via email: mp+391270@code.launchpad.net |
Commit message
Description of the change
Given model assertions created for UC20 have a different format to previous series there was a need to rework the previous simplistic parsing functions. They previously existed in a couple of places where tests (snapd resource, fde tests) used them to identify information about the system.
This makes the parsing somewhat less crude and located in checkbox-support for reuse.
Sheila Miguez (codersquid) wrote : | # |
Sheila Miguez (codersquid) wrote : | # |
I have a few minor questions.
Jonathan Cave (jocave) wrote : | # |
Pushed fixes for spelling mistakes
Jonathan Cave (jocave) : | # |
Sheila Miguez (codersquid) wrote : | # |
lgtm but maybe wait to see if maciej or spineau have any comments?
Maciej Kisielewski (kissiel) wrote : | # |
I like the heuristics. I like the tests. I like the code. +1 :)
Minor nitpicks inline below.
Jonathan Cave (jocave) wrote : | # |
Squashed the addition of a docstring in to the first commit
Sylvain Pineau (sylvain-pineau) wrote : | # |
Nice use of yaml here. +1 (and I also like the tests!)
Devices Certification Bot (ce-certification-qa) wrote : | # |
The merge was fine but running tests failed.
[xenial] [14:40:53] starting container
Device project added to xenial-testing
[focal] [14:40:58] starting container
Device project added to focal-testing
[xenial] [14:41:04] provisioning container
[focal] [14:41:12] provisioning container
[focal] [14:41:26] Starting tests...
[focal] Found a test script: ./requirements/
[xenial] [14:41:29] Starting tests...
[xenial] Found a test script: ./requirements/
[focal] [14:42:10] container-
[focal] [14:42:10] Fixing file permissions in source directory
[focal] [14:42:10] Destroying container
[xenial] [14:42:13] container-
[xenial] output: https:/
[xenial] [14:42:17] Fixing file permissions in source directory
[xenial] [14:42:18] Destroying container
[bionic] [14:42:26] starting container
Device project added to bionic-testing
[bionic] [14:42:39] provisioning container
[bionic] [14:42:57] Starting tests...
[bionic] Found a test script: ./requirements/
[bionic] [14:43:45] container-
[bionic] output: https:/
[bionic] [14:43:48] Fixing file permissions in source directory
[bionic] [14:43:48] Destroying container
Preview Diff
1 | diff --git a/checkbox_support/snap_utils/asserts.py b/checkbox_support/snap_utils/asserts.py |
2 | new file mode 100644 |
3 | index 0000000..1569b22 |
4 | --- /dev/null |
5 | +++ b/checkbox_support/snap_utils/asserts.py |
6 | @@ -0,0 +1,69 @@ |
7 | +# Copyright 2020 Canonical Ltd. |
8 | +# All rights reserved. |
9 | +# |
10 | +# Written by: |
11 | +# Jonathan Cave <jonathan.cave@canonical.com> |
12 | + |
13 | +import yaml |
14 | + |
15 | + |
16 | +def decode(assertion_stream): |
17 | + """Generate individual assertions in yaml format from a stream. |
18 | + |
19 | + Multiple assertions are identified in the stream by a double empty line as |
20 | + per the REST API documentation. Signatures are not verified and removed |
21 | + so any data returned should be used only for informational purposes. |
22 | + """ |
23 | + count = int(assertion_stream.headers['X-Ubuntu-Assertions-Count']) |
24 | + if count > 0: |
25 | + # split in to individual assertions |
26 | + for assertion in assertion_stream.text.split('\n\n\n\n'): |
27 | + # split to remove signature |
28 | + content = assertion.split('\n\n')[0] |
29 | + if int(yaml.__version__.split('.')[0]) < 5: |
30 | + yield yaml.load(content) |
31 | + else: |
32 | + yield yaml.load(content, Loader=yaml.FullLoader) |
33 | + |
34 | + |
35 | +def model_to_resource(model_assertion): |
36 | + """ Convert assertion yaml to flat dict for resource output.""" |
37 | + resource = {} |
38 | + # list keys that can just be copied over |
39 | + wanted_keys = ('type', 'authority-id', 'brand-id', 'model', 'architecture', |
40 | + 'base', 'grade', 'sign-key-sha3-384') |
41 | + for key, val in model_assertion.items(): |
42 | + if key in wanted_keys: |
43 | + resource[key] = val |
44 | + # handle other more complicated keys |
45 | + if 'grade' in model_assertion: |
46 | + # is in UC20 format |
47 | + resource['grade'] = model_assertion.get('grade') |
48 | + for snap in model_assertion['snaps']: |
49 | + if snap['type'] in ('kernel', 'gadget'): |
50 | + resource[snap['type']] = snap['name'] |
51 | + resource['{}_track'.format( |
52 | + snap['type'])] = snap['default-channel'] |
53 | + else: |
54 | + # older formats |
55 | + for key in ('kernel', 'gadget'): |
56 | + val = model_assertion.get(key) |
57 | + if '=' in val: |
58 | + snap, track = [x.strip() for x in val.split('=')] |
59 | + resource[key] = snap |
60 | + resource['{}_track'.format(key)] = track |
61 | + else: |
62 | + resource[key] = val |
63 | + return resource |
64 | + |
65 | + |
66 | +def serial_to_resource(serial_assertion): |
67 | + """ Convert assertion yaml to flat dict for resource output.""" |
68 | + resource = {} |
69 | + # list keys that can just be copied over |
70 | + wanted_keys = ('type', 'authority-id', 'brand-id', 'model', 'serial', |
71 | + 'sign-key-sha3-384') |
72 | + for key, val in serial_assertion.items(): |
73 | + if key in wanted_keys: |
74 | + resource[key] = val |
75 | + return resource |
76 | diff --git a/checkbox_support/snap_utils/system.py b/checkbox_support/snap_utils/system.py |
77 | index 8086a4b..1c029d1 100644 |
78 | --- a/checkbox_support/snap_utils/system.py |
79 | +++ b/checkbox_support/snap_utils/system.py |
80 | @@ -4,7 +4,6 @@ |
81 | # Written by: |
82 | # Jonathan Cave <jonathan.cave@canonical.com> |
83 | |
84 | -import io |
85 | import os |
86 | import re |
87 | import subprocess as sp |
88 | @@ -13,6 +12,8 @@ import yaml |
89 | import distro |
90 | |
91 | from checkbox_support.parsers.kernel_cmdline import parse_kernel_cmdline |
92 | +from checkbox_support.snap_utils.asserts import decode |
93 | +from checkbox_support.snap_utils.asserts import model_to_resource |
94 | from checkbox_support.snap_utils.snapd import Snapd |
95 | |
96 | |
97 | @@ -28,44 +29,28 @@ def in_classic_snap(): |
98 | snap = os.getenv("SNAP") |
99 | if snap: |
100 | with open(os.path.join(snap, 'meta/snap.yaml')) as f: |
101 | - for l in f.readlines(): |
102 | - if l == "confinement: classic\n": |
103 | + for line in f.readlines(): |
104 | + if line == "confinement: classic\n": |
105 | return True |
106 | return False |
107 | |
108 | |
109 | def get_kernel_snap(): |
110 | - snap = None |
111 | - assertion_stream = Snapd().get_assertions('model') |
112 | - count = int(assertion_stream.headers['X-Ubuntu-Assertions-Count']) |
113 | - if count > 0: |
114 | - for line in io.StringIO(assertion_stream.text): |
115 | - if line.count(':') == 1: |
116 | - key, val = [x.strip() for x in line.split(':')] |
117 | - if key == 'kernel': |
118 | - if '=' in val: |
119 | - snap, _ = [x.strip() for x in val.split('=')] |
120 | - else: |
121 | - snap = val |
122 | - break |
123 | - return snap |
124 | + model = next(decode(Snapd().get_assertions('model')), None) |
125 | + if model: |
126 | + # convert to resource to handle presence of track info |
127 | + resource = model_to_resource(model) |
128 | + return resource.get('kernel') |
129 | + return None |
130 | |
131 | |
132 | def get_gadget_snap(): |
133 | - snap = None |
134 | - assertion_stream = Snapd().get_assertions('model') |
135 | - count = int(assertion_stream.headers['X-Ubuntu-Assertions-Count']) |
136 | - if count > 0: |
137 | - for line in io.StringIO(assertion_stream.text): |
138 | - if line.count(':') == 1: |
139 | - key, val = [x.strip() for x in line.split(':')] |
140 | - if key == 'gadget': |
141 | - if '=' in val: |
142 | - snap, _ = [x.strip() for x in val.split('=')] |
143 | - else: |
144 | - snap = val |
145 | - break |
146 | - return snap |
147 | + model = next(decode(Snapd().get_assertions('model')), None) |
148 | + if model: |
149 | + # convert to resource to handle presence of track info |
150 | + resource = model_to_resource(model) |
151 | + return resource.get('gadget') |
152 | + return None |
153 | |
154 | |
155 | def get_bootloader(): |
156 | diff --git a/checkbox_support/snap_utils/tests/asserts_data/MODEL_FOCAL_DESKTOP.txt b/checkbox_support/snap_utils/tests/asserts_data/MODEL_FOCAL_DESKTOP.txt |
157 | new file mode 100644 |
158 | index 0000000..c16f1b3 |
159 | --- /dev/null |
160 | +++ b/checkbox_support/snap_utils/tests/asserts_data/MODEL_FOCAL_DESKTOP.txt |
161 | @@ -0,0 +1,19 @@ |
162 | +type: model |
163 | +authority-id: generic |
164 | +series: 16 |
165 | +brand-id: generic |
166 | +model: generic-classic |
167 | +classic: true |
168 | +timestamp: 2017-07-27T00:00:00.0Z |
169 | +sign-key-sha3-384: d-JcZF9nD9eBw7bwMnH61x-bklnQOhQud1Is6o_cn2wTj8EYDi9musrIT9z2MdAa |
170 | + |
171 | +AcLBXAQAAQoABgUCWYuXiAAKCRAdLQyY+/mCiST0D/0XGQauzV2bbTEy6DkrR1jlNbI6x8vfIdS8 |
172 | +KvEWYvzOWNhNlVSfwNOkFjs3uMHgCO6/fCg03wGXTyV9D7ZgrMeUzWrYp6EmXk8/LQSaBnff86XO |
173 | +4/vYyfyvEYavhF0kQ6QGg8Cqr0EaMyw0x9/zWEO/Ll9fH/8nv9qcQq8N4AbebNvNxtGsCmJuXpSe |
174 | +2rxl3Dw8XarYBmqgcBQhXxRNpa6/AgaTNBpPOTqgNA8ZtmbZwYLuaFjpZP410aJSs+evSKepy/ce |
175 | ++zTA7RB3384YQVeZDdTudX2fGtuCnBZBAJ+NYlk0t8VFXxyOhyMSXeylSpNSx4pCqmUZRyaf5SDS |
176 | +g1XxJet4IP0stZH1SfPOwc9oE81/bJlKsb9QIQKQRewvtUCLfe9a6Vy/CYd2elvcWOmeANVrJK0m |
177 | +nRaz6VBm09RJTuwUT6vNugXSOCeF7W3WN1RHJuex0zw+nP3eCehxFSr33YrVniaA7zGfjXvS8tKx |
178 | +AINNQB4g2fpfet4na6lPPMYM41WHIHPCMTz/fJQ6dZBSEg6UUZ/GiQhGEfWPBteK7yd9pQ8qB3fj |
179 | +ER4UvKnR7hcVI26e3NGNkXP5kp0SFCkV5NQs8rzXzokpB7p/V5Pnqp3Km6wu45cU6UiTZFhR2IMT |
180 | +l+6AMtrS4gDGHktOhwfmOMWqmhvR/INF+TjaWbsB6g== |
181 | \ No newline at end of file |
182 | diff --git a/checkbox_support/snap_utils/tests/asserts_data/MODEL_UC18.txt b/checkbox_support/snap_utils/tests/asserts_data/MODEL_UC18.txt |
183 | new file mode 100644 |
184 | index 0000000..b213dc4 |
185 | --- /dev/null |
186 | +++ b/checkbox_support/snap_utils/tests/asserts_data/MODEL_UC18.txt |
187 | @@ -0,0 +1,23 @@ |
188 | +type: model |
189 | +authority-id: canonical |
190 | +series: 16 |
191 | +brand-id: canonical |
192 | +model: ubuntu-core-18-amd64 |
193 | +architecture: amd64 |
194 | +base: core18 |
195 | +display-name: Ubuntu Core 18 (amd64) |
196 | +gadget: pc=18 |
197 | +kernel: pc-kernel=18 |
198 | +timestamp: 2018-08-13T09:00:00+00:00 |
199 | +sign-key-sha3-384: 9tydnLa6MTJ-jaQTFUXEwHl1yRx7ZS4K5cyFDhYDcPzhS7uyEkDxdUjg9g08BtNn |
200 | + |
201 | +AcLBXAQAAQoABgUCW37NBwAKCRDgT5vottzAEut9D/4u9lD3lFWXoHx1VQT+mUCROcFHdXQBY/PJ |
202 | +NriRiDwBaOjEo5mvHMRJ2UulWvHnwqyMJctJKBP+RCKlrJEPX8eaLP/lmihwIiFfmzm49BLaNwli |
203 | +si0entond1sVWfiNr7azXoEuAIgYvxmJIvE+GZADDT0/OTFQRcLU69bhNEAQKBnkT0y/HTpuXwlJ |
204 | +TuwwJtDR0vZuFtwzj6Bdx7W42+vGmuXE7M4Ni6HUySNKYByB5BsrDf3/79p8huXyBtnWp+HBsHtb |
205 | +fgjzQoBcspj65Gi+crBrJ4jS+nfowRRVXLL1clXJOJLz12za+kN0/FC0PhussiQb5UI7USXJ+RvA |
206 | +Y8U1vrqG7bG5GYGqe1KB9GbLEm+GBPQZcZI3jRmm9V7tm9OWQzK98/uPwTD73IW7LrDT35WQrIYM |
207 | +fBfThJcRqpgzwZD/CBx82maLB9tmsRF5Mhcj2H1v7cn8nSkbv7+cCzh25lKv48Vqz1WTgO3HMPWW |
208 | +0kb6BSoC+YGpstSUslqtpLdY/MfFI0DhshH2Y+h0c9/g4mux/Zb8Gs9V55HGn9mr2KKDmHsU2k+C |
209 | +maZWcXOxRpverZ2Pi9L4fZxhZ9H+FDcMGiHn2vJFQhI3u+LiK3aUUAov4k3vNRPGSvi1AGhuEtUa |
210 | +NG54bznx12KgOT3+YiHtfE95WiXUcJUrEXAgfVBVoA== |
211 | \ No newline at end of file |
212 | diff --git a/checkbox_support/snap_utils/tests/asserts_data/MODEL_UC20.txt b/checkbox_support/snap_utils/tests/asserts_data/MODEL_UC20.txt |
213 | new file mode 100644 |
214 | index 0000000..ee19f86 |
215 | --- /dev/null |
216 | +++ b/checkbox_support/snap_utils/tests/asserts_data/MODEL_UC20.txt |
217 | @@ -0,0 +1,43 @@ |
218 | +type: model |
219 | +authority-id: canonical |
220 | +revision: 1 |
221 | +series: 16 |
222 | +brand-id: canonical |
223 | +model: ubuntu-core-20-amd64-dangerous |
224 | +architecture: amd64 |
225 | +base: core20 |
226 | +grade: dangerous |
227 | +snaps: |
228 | + - |
229 | + default-channel: 20/edge |
230 | + id: UqFziVZDHLSyO3TqSWgNBoAdHbLI4dAH |
231 | + name: pc |
232 | + type: gadget |
233 | + - |
234 | + default-channel: 20/edge |
235 | + id: pYVQrBcKmBa0mZ4CCN7ExT6jH8rY1hza |
236 | + name: pc-kernel |
237 | + type: kernel |
238 | + - |
239 | + default-channel: latest/edge |
240 | + id: DLqre5XGLbDqg9jPtiAhRRjDuPVa5X1q |
241 | + name: core20 |
242 | + type: base |
243 | + - |
244 | + default-channel: latest/edge |
245 | + id: PMrrV4ml8uWuEUDBT8dSGnKUYbevVhc4 |
246 | + name: snapd |
247 | + type: snapd |
248 | +timestamp: 2020-04-29T11:18:00.0Z |
249 | +sign-key-sha3-384: 9tydnLa6MTJ-jaQTFUXEwHl1yRx7ZS4K5cyFDhYDcPzhS7uyEkDxdUjg9g08BtNn |
250 | + |
251 | +AcLBXAQAAQoABgUCWYuXiAAKCRAdLQyY+/mCiST0D/0XGQauzV2bbTEy6DkrR1jlNbI6x8vfIdS8 |
252 | +KvEWYvzOWNhNlVSfwNOkFjs3uMHgCO6/fCg03wGXTyV9D7ZgrMeUzWrYp6EmXk8/LQSaBnff86XO |
253 | +4/vYyfyvEYavhF0kQ6QGg8Cqr0EaMyw0x9/zWEO/Ll9fH/8nv9qcQq8N4AbebNvNxtGsCmJuXpSe |
254 | +2rxl3Dw8XarYBmqgcBQhXxRNpa6/AgaTNBpPOTqgNA8ZtmbZwYLuaFjpZP410aJSs+evSKepy/ce |
255 | ++zTA7RB3384YQVeZDdTudX2fGtuCnBZBAJ+NYlk0t8VFXxyOhyMSXeylSpNSx4pCqmUZRyaf5SDS |
256 | +g1XxJet4IP0stZH1SfPOwc9oE81/bJlKsb9QIQKQRewvtUCLfe9a6Vy/CYd2elvcWOmeANVrJK0m |
257 | +nRaz6VBm09RJTuwUT6vNugXSOCeF7W3WN1RHJuex0zw+nP3eCehxFSr33YrVniaA7zGfjXvS8tKx |
258 | +AINNQB4g2fpfet4na6lPPMYM41WHIHPCMTz/fJQ6dZBSEg6UUZ/GiQhGEfWPBteK7yd9pQ8qB3fj |
259 | +ER4UvKnR7hcVI26e3NGNkXP5kp0SFCkV5NQs8rzXzokpB7p/V5Pnqp3Km6wu45cU6UiTZFhR2IMT |
260 | +l+6AMtrS4gDGHktOhwfmOMWqmhvR/INF+TjaWbsB6g== |
261 | \ No newline at end of file |
262 | diff --git a/checkbox_support/snap_utils/tests/asserts_data/SERIAL_FOCAL_DESKTOP.txt b/checkbox_support/snap_utils/tests/asserts_data/SERIAL_FOCAL_DESKTOP.txt |
263 | new file mode 100644 |
264 | index 0000000..c42add8 |
265 | --- /dev/null |
266 | +++ b/checkbox_support/snap_utils/tests/asserts_data/SERIAL_FOCAL_DESKTOP.txt |
267 | @@ -0,0 +1,30 @@ |
268 | +type: serial |
269 | +authority-id: generic |
270 | +brand-id: generic |
271 | +model: generic-classic |
272 | +serial: 12345678-1234-1234-1234-b4f4dc4a1f9a |
273 | +device-key: |
274 | + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA |
275 | + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA |
276 | + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA |
277 | + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA |
278 | + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA |
279 | + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA |
280 | + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA |
281 | + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA |
282 | + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA |
283 | + AAAAAAAAAAAAAAAAAAAAAAAA |
284 | +device-key-sha3-384: AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA |
285 | +timestamp: 2020-03-03T16:27:34.048105Z |
286 | +sign-key-sha3-384: wrfougkz3Huq2T_KklfnufCC0HzG7bJ9wP99GV0FF-D3QH3eJtuSRlQc2JhrAoh1 |
287 | + |
288 | +AcLBUgQAAQoABgUCXl6FdgAAtGsQAHSDiPo5MmtZt/Itv0dD2BR+eZ4D66SzzGLUPJv5wa8G1Ji2 |
289 | +SIQ1MyzthyN+1vOPF3etkrHMB4wtPnpRK84E1Yfl3P7XfiKVBI46PNxx/o7BknH2iMxckhELM9jT |
290 | +sbUFQDfOrif9NEG2GrAzG7WTaSfxVfF3aNMC1BelCbBbB0C33nf8YaiOWATT5PNG+ynDvDLSKB2M |
291 | +BQn2V7KWrBXQw7oZoZCG/Ct1OVifACoi3/u/ceN4qzzIpQz40hoImwnuJoMGAxwqUcnbesQYmT4b |
292 | +s+EZ+vtLMoyh99AM6TbEif/qmGTi3Otm8RGqqBADLUSypEquAVUcxmr/P3Cn6MvfDalcCSx3VH3Q |
293 | +NO0Fs3phnpJQszXEGwi7FnLyql6H7b/zAtUriBkEjIfwGby5gOEavyOpwQ5JPblt3PKnhZ9Quh2B |
294 | +eZzcjdElAP6OjQlCk9mSlNOErrpWFTRdOQnn6B4ZBql773rsAQXMwm/9FZURJpzJ7oYkLIUJmcQo |
295 | +/WACY5ht45+fG+76mToHLOWlFS0IPNGuKTAaMrrkc2LvfE+rdGMgmGD7TnqjEoUAQsVsjvbykcGe |
296 | +Sp7zj/42BdXpmHP/MCOjM3J9DPMKpEvsw4X8DdS/4p1AdK3qFaT5l3emKzoodfHwEp1IO30FQUDB |
297 | +QOddARNK0QkdYwo4Kj0FpMKxyTOW |
298 | \ No newline at end of file |
299 | diff --git a/checkbox_support/snap_utils/tests/test_asserts.py b/checkbox_support/snap_utils/tests/test_asserts.py |
300 | new file mode 100644 |
301 | index 0000000..741a101 |
302 | --- /dev/null |
303 | +++ b/checkbox_support/snap_utils/tests/test_asserts.py |
304 | @@ -0,0 +1,138 @@ |
305 | +# Copyright 2020 Canonical Ltd. |
306 | +# All rights reserved. |
307 | +# |
308 | +# Written by: |
309 | +# Jonathan Cave <jonathan.cave@canonical.com> |
310 | + |
311 | +from requests.models import Response |
312 | +import unittest |
313 | +from unittest.mock import Mock |
314 | + |
315 | +from pkg_resources import resource_filename |
316 | + |
317 | +from checkbox_support.snap_utils.asserts import decode |
318 | +from checkbox_support.snap_utils.asserts import model_to_resource |
319 | +from checkbox_support.snap_utils.asserts import serial_to_resource |
320 | + |
321 | +model_focal_desktop = 'snap_utils/tests/asserts_data/MODEL_FOCAL_DESKTOP.txt' |
322 | +serial_focal_desktop = 'snap_utils/tests/asserts_data/SERIAL_FOCAL_DESKTOP.txt' |
323 | +model_uc18 = 'snap_utils/tests/asserts_data/MODEL_UC18.txt' |
324 | +model_uc20 = 'snap_utils/tests/asserts_data/MODEL_UC20.txt' |
325 | + |
326 | + |
327 | +def create_mock_response(assert_path): |
328 | + mock_response = Mock(spec=Response) |
329 | + mock_response.status_code = 400 |
330 | + mock_response.headers = {'X-Ubuntu-Assertions-Count': 1} |
331 | + with open(resource_filename('checkbox_support', assert_path), 'r') as f: |
332 | + mock_response.text = f.read() |
333 | + return mock_response |
334 | + |
335 | + |
336 | +class TestModelAsserts(unittest.TestCase): |
337 | + |
338 | + def test_decode_focal(self): |
339 | + assertion_stream = create_mock_response(model_focal_desktop) |
340 | + iter = decode(assertion_stream) |
341 | + a = next(iter) |
342 | + self.assertIn('type', a) |
343 | + self.assertEqual(a['type'], 'model') |
344 | + self.assertIn('model', a) |
345 | + self.assertEqual(a['model'], 'generic-classic') |
346 | + with self.assertRaises(StopIteration): |
347 | + next(iter) |
348 | + |
349 | + def test_decode_uc18(self): |
350 | + assertion_stream = create_mock_response(model_uc18) |
351 | + iter = decode(assertion_stream) |
352 | + a = next(iter) |
353 | + self.assertIn('type', a) |
354 | + self.assertEqual(a['type'], 'model') |
355 | + self.assertIn('model', a) |
356 | + self.assertEqual(a['model'], 'ubuntu-core-18-amd64') |
357 | + with self.assertRaises(StopIteration): |
358 | + next(iter) |
359 | + |
360 | + def test_decode_uc20(self): |
361 | + assertion_stream = create_mock_response(model_uc20) |
362 | + iter = decode(assertion_stream) |
363 | + a = next(iter) |
364 | + self.assertIn('type', a) |
365 | + self.assertEqual(a['type'], 'model') |
366 | + self.assertIn('model', a) |
367 | + self.assertEqual(a['model'], 'ubuntu-core-20-amd64-dangerous') |
368 | + with self.assertRaises(StopIteration): |
369 | + next(iter) |
370 | + |
371 | + def test_model_to_resource_uc18(self): |
372 | + assertion_stream = create_mock_response(model_uc18) |
373 | + iter = decode(assertion_stream) |
374 | + a = next(iter) |
375 | + correct_resource = { |
376 | + 'type': 'model', |
377 | + 'authority-id': 'canonical', |
378 | + 'brand-id': 'canonical', |
379 | + 'model': 'ubuntu-core-18-amd64', |
380 | + 'architecture': 'amd64', |
381 | + 'base': 'core18', |
382 | + 'sign-key-sha3-384': '9tydnLa6MTJ-jaQTFUXEwHl1yRx7ZS4K5cyFDhYDcPzhS7uyEkDxdUjg9g08BtNn', |
383 | + 'kernel': 'pc-kernel', |
384 | + 'kernel_track': '18', |
385 | + 'gadget': 'pc', |
386 | + 'gadget_track': '18' |
387 | + } |
388 | + self.assertDictEqual(correct_resource, model_to_resource(a)) |
389 | + with self.assertRaises(StopIteration): |
390 | + next(iter) |
391 | + |
392 | + def test_model_to_resource_uc20(self): |
393 | + assertion_stream = create_mock_response(model_uc20) |
394 | + iter = decode(assertion_stream) |
395 | + a = next(iter) |
396 | + correct_resource = { |
397 | + 'type': 'model', |
398 | + 'authority-id': 'canonical', |
399 | + 'brand-id': 'canonical', |
400 | + 'model': 'ubuntu-core-20-amd64-dangerous', |
401 | + 'architecture': 'amd64', |
402 | + 'base': 'core20', |
403 | + 'grade': 'dangerous', |
404 | + 'sign-key-sha3-384': '9tydnLa6MTJ-jaQTFUXEwHl1yRx7ZS4K5cyFDhYDcPzhS7uyEkDxdUjg9g08BtNn', |
405 | + 'gadget': 'pc', |
406 | + 'gadget_track': '20/edge', |
407 | + 'kernel': 'pc-kernel', |
408 | + 'kernel_track': '20/edge' |
409 | + } |
410 | + self.assertDictEqual(correct_resource, model_to_resource(a)) |
411 | + with self.assertRaises(StopIteration): |
412 | + next(iter) |
413 | + |
414 | + |
415 | +class TestSerialAsserts(unittest.TestCase): |
416 | + |
417 | + def test_decode_focal(self): |
418 | + assertion_stream = create_mock_response(serial_focal_desktop) |
419 | + iter = decode(assertion_stream) |
420 | + a = next(iter) |
421 | + self.assertIn('type', a) |
422 | + self.assertEqual(a['type'], 'serial') |
423 | + self.assertIn('serial', a) |
424 | + self.assertEqual(a['serial'], '12345678-1234-1234-1234-b4f4dc4a1f9a') |
425 | + with self.assertRaises(StopIteration): |
426 | + next(iter) |
427 | + |
428 | + def test_serial_to_resource_focal(self): |
429 | + assertion_stream = create_mock_response(serial_focal_desktop) |
430 | + iter = decode(assertion_stream) |
431 | + a = next(iter) |
432 | + correct_resource = { |
433 | + 'type': 'serial', |
434 | + 'authority-id': 'generic', |
435 | + 'brand-id': 'generic', |
436 | + 'model': 'generic-classic', |
437 | + 'serial': '12345678-1234-1234-1234-b4f4dc4a1f9a', |
438 | + 'sign-key-sha3-384': 'wrfougkz3Huq2T_KklfnufCC0HzG7bJ9wP99GV0FF-D3QH3eJtuSRlQc2JhrAoh1' |
439 | + } |
440 | + self.assertDictEqual(correct_resource, serial_to_resource(a)) |
441 | + with self.assertRaises(StopIteration): |
442 | + next(iter) |
I noticed a typo while reading this. See inline.