59
59
def test_installing_forbidden_without_edit_perm(self):
60
60
self.client_log_in(as_admin=False)
61
result = factory.make_node_install_result()
61
result = factory.make_NodeResult_for_installing()
62
62
response = self.client.get(
63
63
reverse('nodeinstallresult-view', args=[result.id]))
64
64
self.assertEqual(httplib.FORBIDDEN, response.status_code)
66
66
def test_installing_allowed_with_edit_perm(self):
68
user = factory.make_user(password=password)
69
node = factory.make_node(owner=user)
68
user = factory.make_User(password=password)
69
node = factory.make_Node(owner=user)
70
70
self.client.login(username=user.username, password=password)
71
71
self.logged_in_user = user
72
result = factory.make_node_install_result(node=node)
72
result = factory.make_NodeResult_for_installing(node=node)
73
73
response = self.client.get(
74
74
reverse('nodeinstallresult-view', args=[result.id]))
75
75
self.assertEqual(httplib.OK, response.status_code)
80
80
# un-escapes on parsing, and is very tolerant of malformed input.
81
81
# Parsing an un-escaped A<B>C, however, would produce text "AC"
82
82
# (because the <B> looks like a tag).
83
result = factory.make_node_install_result(data=b'A<B>C')
83
result = factory.make_NodeResult_for_installing(data=b'A<B>C')
84
84
doc = self.request_page(result)
85
85
self.assertEqual('A<B>C', extract_field(doc, 'output', 'pre'))
87
87
def test_installing_escapes_binary_in_output(self):
88
88
self.client_log_in(as_admin=True)
89
result = factory.make_node_install_result(data=b'A\xffB')
89
result = factory.make_NodeResult_for_installing(data=b'A\xffB')
90
90
doc = self.request_page(result)
91
91
self.assertEqual('A\ufffdB', extract_field(doc, 'output', 'pre'))
93
93
def test_installing_hides_output_if_empty(self):
94
94
self.client_log_in(as_admin=True)
95
result = factory.make_node_install_result(data=b'')
95
result = factory.make_NodeResult_for_installing(data=b'')
96
96
doc = self.request_page(result)
97
97
field = get_one(doc.cssselect('#output'))
98
98
self.assertEqual('', field.text_content().strip())
114
114
def test_commissioning_forbidden_without_edit_perm(self):
115
115
self.client_log_in(as_admin=False)
116
result = factory.make_node_commission_result()
116
result = factory.make_NodeResult_for_commissioning()
117
117
response = self.client.get(
118
118
reverse('nodecommissionresult-view', args=[result.id]))
119
119
self.assertEqual(httplib.FORBIDDEN, response.status_code)
121
121
def test_commissioning_allowed_with_edit_perm(self):
122
122
password = 'test'
123
user = factory.make_user(password=password)
124
node = factory.make_node(owner=user)
123
user = factory.make_User(password=password)
124
node = factory.make_Node(owner=user)
125
125
self.client.login(username=user.username, password=password)
126
126
self.logged_in_user = user
127
result = factory.make_node_commission_result(node=node)
127
result = factory.make_NodeResult_for_commissioning(node=node)
128
128
response = self.client.get(
129
129
reverse('nodecommissionresult-view', args=[result.id]))
130
130
self.assertEqual(httplib.OK, response.status_code)
132
132
def test_commissioning_displays_result(self):
133
133
self.client_log_in(as_admin=True)
134
result = factory.make_node_commission_result(
134
result = factory.make_NodeResult_for_commissioning(
135
135
data=factory.make_string().encode('ascii'))
136
136
doc = self.request_page(result)
150
150
# un-escapes on parsing, and is very tolerant of malformed input.
151
151
# Parsing an un-escaped A<B>C, however, would produce text "AC"
152
152
# (because the <B> looks like a tag).
153
result = factory.make_node_commission_result(data=b'A<B>C')
153
result = factory.make_NodeResult_for_commissioning(data=b'A<B>C')
154
154
doc = self.request_page(result)
155
155
self.assertEqual('A<B>C', extract_field(doc, 'output', 'pre'))
157
157
def test_commissioning_escapes_binary_in_output(self):
158
158
self.client_log_in(as_admin=True)
159
result = factory.make_node_commission_result(data=b'A\xffB')
159
result = factory.make_NodeResult_for_commissioning(data=b'A\xffB')
160
160
doc = self.request_page(result)
161
161
self.assertEqual('A\ufffdB', extract_field(doc, 'output', 'pre'))
163
163
def test_commissioning_hides_output_if_empty(self):
164
164
self.client_log_in(as_admin=True)
165
result = factory.make_node_commission_result(data=b'')
165
result = factory.make_NodeResult_for_commissioning(data=b'')
166
166
doc = self.request_page(result)
167
167
field = get_one(doc.cssselect('#output'))
168
168
self.assertEqual('', field.text_content().strip())
175
175
return '&'.join('node=%s' % node.system_id for node in nodes)
177
177
def request_page(self, nodes=None):
178
"""Request and parse the page for the given `NodeResult`.
178
"""Request and parse the page for the given `NodeResult`.
180
180
:param node: Optional list of `Node` for which results should be
181
181
displayed. If not given, all results are displayed.
214
214
def test_lists_results(self):
215
215
self.client_log_in(as_admin=True)
216
result = factory.make_node_commission_result(script_result=0)
216
result = factory.make_NodeResult_for_commissioning(script_result=0)
217
217
content = self.request_page()
218
218
result_row = get_one(content.cssselect('.result'))
219
219
fields = result_row.cssselect('td')
230
230
def test_shows_failure(self):
231
231
self.client_log_in(as_admin=True)
232
factory.make_node_commission_result(script_result=randint(1, 100))
232
factory.make_NodeResult_for_commissioning(
233
script_result=randint(1, 100))
233
234
content = self.request_page()
234
235
result_row = get_one(content.cssselect('.result'))
235
236
fields = result_row.cssselect('td')
240
241
def test_links_to_result(self):
241
242
self.client_log_in(as_admin=True)
242
result = factory.make_node_commission_result(
243
result = factory.make_NodeResult_for_commissioning(
243
244
script_result=randint(1, 100))
244
245
content = self.request_page()
245
246
result_row = get_one(content.cssselect('.result'))
251
252
link.get('href'))
253
254
def test_groups_by_node(self):
254
nodes = [factory.make_node() for _ in range(3)]
255
nodes = [factory.make_Node() for _ in range(3)]
255
256
# Create two results per node, but interleave them so the results for
256
257
# any given node are unlikely to occur side by side by accident.
257
258
for _ in range(2):
258
259
for node in nodes:
259
factory.make_node_commission_result(node=node)
260
factory.make_NodeResult_for_commissioning(node=node)
260
261
sorted_results = self.make_view().get_queryset()
261
262
self.assertEqual(sorted_results[0].node, sorted_results[1].node)
262
263
self.assertEqual(sorted_results[2].node, sorted_results[3].node)
263
264
self.assertEqual(sorted_results[4].node, sorted_results[5].node)
265
266
def test_sorts_by_creation_time_for_same_node(self):
266
node = factory.make_node()
267
node = factory.make_Node()
268
factory.make_node_commission_result(node=node)
269
factory.make_NodeResult_for_commissioning(node=node)
269
270
for _ in range(3)
271
272
for result in results:
277
278
list(self.make_view().get_queryset()))
279
280
def test_sorts_by_name_for_same_node_and_creation_time(self):
280
node = factory.make_node()
281
node = factory.make_Node()
282
factory.make_node_commission_result(
283
factory.make_NodeResult_for_commissioning(
283
284
node=node, name=factory.make_name().lower())
284
285
for _ in range(5)
288
289
list(self.make_view().get_queryset()))
290
291
def test_filters_by_node(self):
291
factory.make_node_commission_result()
292
node = factory.make_node()
292
factory.make_NodeResult_for_commissioning()
293
node = factory.make_Node()
294
factory.make_node_commission_result(node=node) for _ in range(3)
295
factory.make_NodeResult_for_commissioning(node=node)
296
factory.make_node_commission_result()
298
factory.make_NodeResult_for_commissioning()
298
300
self.assertEqual(
305
307
# naively would ignore all but the first node passed, so make sure we
306
308
# process all of them.
307
309
self.client_log_in(as_admin=True)
308
results = [factory.make_node_commission_result() for _ in range(3)]
311
factory.make_NodeResult_for_commissioning()
309
314
matching_results = results[1:3]
310
315
content = self.request_page(
311
316
nodes=[result.node for result in matching_results])
330
335
def test_shows_node_if_filtering_by_node(self):
331
336
self.client_log_in(as_admin=True)
332
node = factory.make_node()
337
node = factory.make_Node()
333
338
doc = self.request_page(nodes=[node])
334
339
header = get_one(doc.cssselect('#results_header'))
335
340
self.assertEqual(
339
344
def test_shows_nodes_if_filtering_by_multiple_nodes(self):
340
345
self.client_log_in(as_admin=True)
341
346
names = [factory.make_name('node').lower() for _ in range(2)]
342
nodes = [factory.make_node(hostname=name) for name in names]
347
nodes = [factory.make_Node(hostname=name) for name in names]
343
348
doc = self.request_page(nodes=nodes)
344
349
header = get_one(doc.cssselect('#results_header'))
345
350
self.assertEqual(
346
351
"Commissioning results for %s" % ', '.join(sorted(names)),
347
352
normalise_whitespace(header.text_content()))
354
def test_does_not_list_installation_results(self):
355
self.client_log_in(as_admin=True)
356
factory.make_NodeResult_for_installing()
357
content = self.request_page()
358
self.assertIsNotNone(
359
get_one(content.cssselect('#no_results')))
360
self.assertEqual([], content.cssselect('.result'))