1
# -*- coding: utf-8 -*-
2
# vim: autoindent shiftwidth=4 expandtab textwidth=120 tabstop=4 softtabstop=4
4
##########################################################################
5
# OpenLP - Open Source Lyrics Projection #
6
# ---------------------------------------------------------------------- #
7
# Copyright (c) 2008-2019 OpenLP Developers #
8
# ---------------------------------------------------------------------- #
9
# This program is free software: you can redistribute it and/or modify #
10
# it under the terms of the GNU General Public License as published by #
11
# the Free Software Foundation, either version 3 of the License, or #
12
# (at your option) any later version. #
14
# This program is distributed in the hope that it will be useful, #
15
# but WITHOUT ANY WARRANTY; without even the implied warranty of #
16
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the #
17
# GNU General Public License for more details. #
19
# You should have received a copy of the GNU General Public License #
20
# along with this program. If not, see <https://www.gnu.org/licenses/>. #
21
##########################################################################
23
Functional tests to test the Mac LibreOffice class and related methods.
26
from tempfile import mkdtemp
27
from unittest import TestCase
28
from unittest.mock import MagicMock, patch, call
30
from openlp.core.common.settings import Settings
31
from openlp.core.common.path import Path
32
from openlp.plugins.presentations.lib.maclocontroller import MacLOController, MacLODocument
33
from openlp.plugins.presentations.presentationplugin import __default_settings__
35
from tests.helpers.testmixin import TestMixin
36
from tests.utils.constants import TEST_RESOURCES_PATH
39
class TestMacLOController(TestCase, TestMixin):
41
Test the MacLOController Class
46
Set up the patches and mocks need for all tests.
48
self.setup_application()
50
self.mock_plugin = MagicMock()
51
self.temp_folder = mkdtemp()
52
self.mock_plugin.settings_section = self.temp_folder
58
self.destroy_settings()
59
shutil.rmtree(self.temp_folder)
61
@patch('openlp.plugins.presentations.lib.maclocontroller.MacLOController._start_server')
62
def test_constructor(self, mocked_start_server):
64
Test the Constructor from the MacLOController
66
# GIVEN: No presentation controller
69
# WHEN: The presentation controller object is created
70
controller = MacLOController(plugin=self.mock_plugin)
72
# THEN: The name of the presentation controller should be correct
73
assert controller.name == 'maclo', \
74
'The name of the presentation controller should be correct'
75
assert controller.display_name == 'Impress on macOS', \
76
'The display name of the presentation controller should be correct'
77
mocked_start_server.assert_called_once_with()
79
@patch('openlp.plugins.presentations.lib.maclocontroller.MacLOController._start_server')
80
@patch('openlp.plugins.presentations.lib.maclocontroller.Proxy')
81
def test_client(self, MockedProxy, mocked_start_server):
83
Test the client property of the Controller
85
# GIVEN: A controller without a client and a mocked out Pyro
86
controller = MacLOController(plugin=self.mock_plugin)
87
mocked_client = MagicMock()
88
MockedProxy.return_value = mocked_client
89
mocked_client._pyroConnection = None
91
# WHEN: the client property is called the first time
92
client = controller.client
94
# THEN: a client is created
95
assert client == mocked_client
96
MockedProxy.assert_called_once_with('PYRO:openlp.libreofficeserver@localhost:4310')
97
mocked_client._pyroReconnect.assert_called_once_with()
99
@patch('openlp.plugins.presentations.lib.maclocontroller.MacLOController._start_server')
100
def test_check_available(self, mocked_start_server):
102
Test the check_available() method
104
from openlp.plugins.presentations.lib.maclocontroller import macuno_available
106
# GIVEN: A controller
107
controller = MacLOController(plugin=self.mock_plugin)
109
# WHEN: check_available() is run
110
result = controller.check_available()
112
# THEN: it should return false
113
assert result == macuno_available
115
@patch('openlp.plugins.presentations.lib.maclocontroller.MacLOController._start_server')
116
def test_start_process(self, mocked_start_server):
118
Test the start_process() method
120
# GIVEN: A controller and a client
121
controller = MacLOController(plugin=self.mock_plugin)
122
controller._client = MagicMock()
124
# WHEN: start_process() is called
125
controller.start_process()
127
# THEN: The client's start_process() should have been called
128
controller._client.start_process.assert_called_once_with()
130
@patch('openlp.plugins.presentations.lib.maclocontroller.MacLOController._start_server')
131
def test_kill(self, mocked_start_server):
133
Test the kill() method
135
# GIVEN: A controller and a client
136
controller = MacLOController(plugin=self.mock_plugin)
137
controller._client = MagicMock()
138
controller.server_process = MagicMock()
140
# WHEN: start_process() is called
143
# THEN: The client's start_process() should have been called
144
controller._client.shutdown.assert_called_once_with()
145
controller.server_process.kill.assert_called_once_with()
148
class TestMacLODocument(TestCase):
150
Test the MacLODocument Class
153
mocked_plugin = MagicMock()
154
mocked_plugin.settings_section = 'presentations'
155
Settings().extend_default_settings(__default_settings__)
156
self.file_name = Path(TEST_RESOURCES_PATH) / 'presentations' / 'test.odp'
157
self.mocked_client = MagicMock()
158
with patch('openlp.plugins.presentations.lib.maclocontroller.MacLOController._start_server'):
159
self.controller = MacLOController(mocked_plugin)
160
self.controller._client = self.mocked_client
161
self.document = MacLODocument(self.controller, self.file_name)
163
@patch('openlp.plugins.presentations.lib.maclocontroller.ScreenList')
164
def test_load_presentation_cannot_load(self, MockedScreenList):
166
Test the load_presentation() method when the server can't load the presentation
168
# GIVEN: A document and a mocked client
169
mocked_screen_list = MagicMock()
170
MockedScreenList.return_value = mocked_screen_list
171
mocked_screen_list.current.number = 0
172
self.mocked_client.load_presentation.return_value = False
174
# WHEN: load_presentation() is called
175
result = self.document.load_presentation()
177
# THEN: Stuff should work right
178
self.mocked_client.load_presentation.assert_called_once_with(str(self.file_name), 1)
179
assert result is False
181
@patch('openlp.plugins.presentations.lib.maclocontroller.ScreenList')
182
def test_load_presentation(self, MockedScreenList):
184
Test the load_presentation() method
186
# GIVEN: A document and a mocked client
187
mocked_screen_list = MagicMock()
188
MockedScreenList.return_value = mocked_screen_list
189
mocked_screen_list.current.number = 0
190
self.mocked_client.load_presentation.return_value = True
192
# WHEN: load_presentation() is called
193
with patch.object(self.document, 'create_thumbnails') as mocked_create_thumbnails, \
194
patch.object(self.document, 'create_titles_and_notes') as mocked_create_titles_and_notes:
195
result = self.document.load_presentation()
197
# THEN: Stuff should work right
198
self.mocked_client.load_presentation.assert_called_once_with(str(self.file_name), 1)
199
mocked_create_thumbnails.assert_called_once_with()
200
mocked_create_titles_and_notes.assert_called_once_with()
201
assert result is True
203
def test_create_thumbnails_already_exist(self):
205
Test the create_thumbnails() method when thumbnails already exist
207
# GIVEN: thumbnails that exist and a mocked client
208
self.document.check_thumbnails = MagicMock(return_value=True)
210
# WHEN: create_thumbnails() is called
211
self.document.create_thumbnails()
213
# THEN: The method should exit early
214
assert self.mocked_client.extract_thumbnails.call_count == 0
216
@patch('openlp.plugins.presentations.lib.maclocontroller.delete_file')
217
def test_create_thumbnails(self, mocked_delete_file):
219
Test the create_thumbnails() method
221
# GIVEN: thumbnails that don't exist and a mocked client
222
self.document.check_thumbnails = MagicMock(return_value=False)
223
self.mocked_client.extract_thumbnails.return_value = ['thumb1.png', 'thumb2.png']
225
# WHEN: create_thumbnails() is called
226
with patch.object(self.document, 'convert_thumbnail') as mocked_convert_thumbnail, \
227
patch.object(self.document, 'get_temp_folder') as mocked_get_temp_folder:
228
mocked_get_temp_folder.return_value = 'temp'
229
self.document.create_thumbnails()
231
# THEN: The method should complete successfully
232
self.mocked_client.extract_thumbnails.assert_called_once_with('temp')
233
assert mocked_convert_thumbnail.call_args_list == [
234
call(Path('thumb1.png'), 1), call(Path('thumb2.png'), 2)]
235
assert mocked_delete_file.call_args_list == [call(Path('thumb1.png')), call(Path('thumb2.png'))]
237
def test_create_titles_and_notes(self):
239
Test create_titles_and_notes() method
241
# GIVEN: mocked client and mocked save_titles_and_notes() method
242
self.mocked_client.get_titles_and_notes.return_value = ('OpenLP', 'This is a note')
244
# WHEN: create_titles_and_notes() is called
245
with patch.object(self.document, 'save_titles_and_notes') as mocked_save_titles_and_notes:
246
self.document.create_titles_and_notes()
248
# THEN save_titles_and_notes should have been called
249
self.mocked_client.get_titles_and_notes.assert_called_once_with()
250
mocked_save_titles_and_notes.assert_called_once_with('OpenLP', 'This is a note')
252
def test_close_presentation(self):
254
Test the close_presentation() method
256
# GIVEN: A mocked client and mocked remove_doc() method
257
# WHEN: close_presentation() is called
258
with patch.object(self.controller, 'remove_doc') as mocked_remove_doc:
259
self.document.close_presentation()
261
# THEN: The presentation should have been closed
262
self.mocked_client.close_presentation.assert_called_once_with()
263
mocked_remove_doc.assert_called_once_with(self.document)
265
def test_is_loaded(self):
267
Test the is_loaded() method
269
# GIVEN: A mocked client
270
self.mocked_client.is_loaded.return_value = True
272
# WHEN: is_loaded() is called
273
result = self.document.is_loaded()
275
# THEN: Then the result should be correct
276
assert result is True
278
def test_is_active(self):
280
Test the is_active() method
282
# GIVEN: A mocked client
283
self.mocked_client.is_active.return_value = True
285
# WHEN: is_active() is called
286
result = self.document.is_active()
288
# THEN: Then the result should be correct
289
assert result is True
291
def test_unblank_screen(self):
293
Test the unblank_screen() method
295
# GIVEN: A mocked client
296
self.mocked_client.unblank_screen.return_value = True
298
# WHEN: unblank_screen() is called
299
result = self.document.unblank_screen()
301
# THEN: Then the result should be correct
302
self.mocked_client.unblank_screen.assert_called_once_with()
303
assert result is True
305
def test_blank_screen(self):
307
Test the blank_screen() method
309
# GIVEN: A mocked client
310
self.mocked_client.blank_screen.return_value = True
312
# WHEN: blank_screen() is called
313
self.document.blank_screen()
315
# THEN: Then the result should be correct
316
self.mocked_client.blank_screen.assert_called_once_with()
318
def test_is_blank(self):
320
Test the is_blank() method
322
# GIVEN: A mocked client
323
self.mocked_client.is_blank.return_value = True
325
# WHEN: is_blank() is called
326
result = self.document.is_blank()
328
# THEN: Then the result should be correct
329
assert result is True
331
def test_stop_presentation(self):
333
Test the stop_presentation() method
335
# GIVEN: A mocked client
336
self.mocked_client.stop_presentation.return_value = True
338
# WHEN: stop_presentation() is called
339
self.document.stop_presentation()
341
# THEN: Then the result should be correct
342
self.mocked_client.stop_presentation.assert_called_once_with()
344
@patch('openlp.plugins.presentations.lib.maclocontroller.ScreenList')
345
@patch('openlp.plugins.presentations.lib.maclocontroller.Registry')
346
def test_start_presentation(self, MockedRegistry, MockedScreenList):
348
Test the start_presentation() method
350
# GIVEN: a mocked client, and multiple screens
351
mocked_screen_list = MagicMock()
352
mocked_screen_list.__len__.return_value = 2
353
mocked_registry = MagicMock()
354
mocked_main_window = MagicMock()
355
MockedScreenList.return_value = mocked_screen_list
356
MockedRegistry.return_value = mocked_registry
357
mocked_screen_list.screen_list = [0, 1]
358
mocked_registry.get.return_value = mocked_main_window
360
# WHEN: start_presentation() is called
361
self.document.start_presentation()
363
# THEN: The presentation should be started
364
self.mocked_client.start_presentation.assert_called_once_with()
365
mocked_registry.get.assert_called_once_with('main_window')
366
mocked_main_window.activateWindow.assert_called_once_with()
368
def test_get_slide_number(self):
370
Test the get_slide_number() method
372
# GIVEN: A mocked client
373
self.mocked_client.get_slide_number.return_value = 5
375
# WHEN: get_slide_number() is called
376
result = self.document.get_slide_number()
378
# THEN: Then the result should be correct
381
def test_get_slide_count(self):
383
Test the get_slide_count() method
385
# GIVEN: A mocked client
386
self.mocked_client.get_slide_count.return_value = 8
388
# WHEN: get_slide_count() is called
389
result = self.document.get_slide_count()
391
# THEN: Then the result should be correct
394
def test_goto_slide(self):
396
Test the goto_slide() method
398
# GIVEN: A mocked client
399
# WHEN: goto_slide() is called
400
self.document.goto_slide(3)
402
# THEN: Then the result should be correct
403
self.mocked_client.goto_slide.assert_called_once_with(3)
405
def test_next_step(self):
407
Test the next_step() method
409
# GIVEN: A mocked client
410
# WHEN: next_step() is called
411
self.document.next_step()
413
# THEN: Then the result should be correct
414
self.mocked_client.next_step.assert_called_once_with()
416
def test_previous_step(self):
418
Test the previous_step() method
420
# GIVEN: A mocked client
421
# WHEN: previous_step() is called
422
self.document.previous_step()
424
# THEN: Then the result should be correct
425
self.mocked_client.previous_step.assert_called_once_with()
427
def test_get_slide_text(self):
429
Test the get_slide_text() method
431
# GIVEN: A mocked client
432
self.mocked_client.get_slide_text.return_value = 'Some slide text'
434
# WHEN: get_slide_text() is called
435
result = self.document.get_slide_text(1)
437
# THEN: Then the result should be correct
438
self.mocked_client.get_slide_text.assert_called_once_with(1)
439
assert result == 'Some slide text'
441
def test_get_slide_notes(self):
443
Test the get_slide_notes() method
445
# GIVEN: A mocked client
446
self.mocked_client.get_slide_notes.return_value = 'This is a note'
448
# WHEN: get_slide_notes() is called
449
result = self.document.get_slide_notes(2)
451
# THEN: Then the result should be correct
452
self.mocked_client.get_slide_notes.assert_called_once_with(2)
453
assert result == 'This is a note'