diff --git a/onionshare/onion.py b/onionshare/onion.py index 3aeffe91..3d7b4514 100644 --- a/onionshare/onion.py +++ b/onionshare/onion.py @@ -146,6 +146,9 @@ class Onion(object): # The tor process self.tor_proc = None + # The Tor controller + self.c = None + # Start out not connected to Tor self.connected_to_tor = False diff --git a/onionshare_gui/settings_dialog.py b/onionshare_gui/settings_dialog.py index 1ff20b31..92c84262 100644 --- a/onionshare_gui/settings_dialog.py +++ b/onionshare_gui/settings_dialog.py @@ -89,8 +89,8 @@ class SettingsDialog(QtWidgets.QDialog): self.shutdown_timeout_widget.setLayout(shutdown_timeout_layout) # Label telling user to connect to Tor for onion service settings - connect_to_tor_label = QtWidgets.QLabel(strings._("gui_connect_to_tor_for_onion_settings")) - connect_to_tor_label.setStyleSheet(self.common.css['settings_connect_to_tor']) + self.connect_to_tor_label = QtWidgets.QLabel(strings._("gui_connect_to_tor_for_onion_settings")) + self.connect_to_tor_label.setStyleSheet(self.common.css['settings_connect_to_tor']) # Whether or not to use legacy v2 onions self.use_legacy_v2_onions_checkbox = QtWidgets.QCheckBox() @@ -161,15 +161,15 @@ class SettingsDialog(QtWidgets.QDialog): onion_settings_layout.addWidget(self.use_stealth_widget) onion_settings_layout.addWidget(hidservauth_details) onion_settings_layout.addWidget(self.hidservauth_copy_button) - onion_settings_widget = QtWidgets.QWidget() - onion_settings_widget.setLayout(onion_settings_layout) + self.onion_settings_widget = QtWidgets.QWidget() + self.onion_settings_widget.setLayout(onion_settings_layout) # General options layout general_group_layout = QtWidgets.QVBoxLayout() general_group_layout.addWidget(self.public_mode_widget) general_group_layout.addWidget(self.shutdown_timeout_widget) - general_group_layout.addWidget(connect_to_tor_label) - general_group_layout.addWidget(onion_settings_widget) + general_group_layout.addWidget(self.connect_to_tor_label) + general_group_layout.addWidget(self.onion_settings_widget) general_group = QtWidgets.QGroupBox(strings._("gui_settings_general_label")) general_group.setLayout(general_group_layout) @@ -471,7 +471,9 @@ class SettingsDialog(QtWidgets.QDialog): self.setLayout(layout) self.cancel_button.setFocus() + self.reload_settings() + def reload_settings(self): # Load settings, and fill them in self.old_settings = Settings(self.common, self.config) self.old_settings.load() @@ -593,8 +595,8 @@ class SettingsDialog(QtWidgets.QDialog): # If we're connected to Tor, show onion service settings, show label if not if self.onion.is_authenticated(): - connect_to_tor_label.hide() - onion_settings_widget.show() + self.connect_to_tor_label.hide() + self.onion_settings_widget.show() # If v3 onion services are supported, allow using legacy mode if self.onion.supports_v3_onions: @@ -605,8 +607,8 @@ class SettingsDialog(QtWidgets.QDialog): self.use_legacy_v2_onions_widget.hide() self.use_legacy_v2_onions_checkbox_clicked(True) else: - connect_to_tor_label.show() - onion_settings_widget.hide() + self.connect_to_tor_label.show() + self.onion_settings_widget.hide() def connection_type_bundled_toggled(self, checked): diff --git a/tests/SettingsGuiBaseTest.py b/tests/SettingsGuiBaseTest.py index e59a58a8..57626d1d 100644 --- a/tests/SettingsGuiBaseTest.py +++ b/tests/SettingsGuiBaseTest.py @@ -1,5 +1,7 @@ import json import os +import unittest +from PyQt5 import QtCore, QtTest from onionshare import strings from onionshare.common import Common @@ -8,10 +10,27 @@ from onionshare.onion import Onion from onionshare_gui import Application, OnionShare from onionshare_gui.settings_dialog import SettingsDialog + +class OnionStub(object): + def __init__(self, is_authenticated, supports_v3_onions=False): + self._is_authenticated = is_authenticated + self.supports_v3_onions = True + + def is_authenticated(self): + return self._is_authenticated + + class SettingsGuiBaseTest(object): @staticmethod - def set_up(test_settings): + def set_up(): '''Create the GUI''' + + # Default settings for the settings GUI tests + test_settings = { + "no_bridges": False, + "tor_bridges_use_custom_bridges": "Bridge 1.2.3.4:56 EEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEE\nBridge 5.6.7.8:910 EEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEE\nBridge 11.12.13.14:1516 EEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEE\n", + } + # Create our test file testfile = open('/tmp/test.txt', 'w') testfile.write('onionshare') @@ -37,8 +56,187 @@ class SettingsGuiBaseTest(object): gui = SettingsDialog(common, testonion, qtapp, '/tmp/settings.json', True) return gui - @staticmethod def tear_down(): '''Clean up after tests''' os.remove('/tmp/settings.json') + + def run_settings_gui_tests(self): + self.gui.show() + self.gui.qtapp.processEvents() + + # Window is shown + self.assertTrue(self.gui.isVisible()) + self.assertEqual(self.gui.windowTitle(), strings._('gui_settings_window_title')) + + # Check for updates button is hidden + self.assertFalse(self.gui.check_for_updates_button.isVisible()) + + # public mode is off + self.assertFalse(self.gui.public_mode_checkbox.isChecked()) + # enable public mode + QtTest.QTest.mouseClick(self.gui.public_mode_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.public_mode_checkbox.height()/2)) + self.assertTrue(self.gui.public_mode_checkbox.isChecked()) + + # shutdown timer is off + self.assertFalse(self.gui.shutdown_timeout_checkbox.isChecked()) + # enable shutdown timer + QtTest.QTest.mouseClick(self.gui.shutdown_timeout_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.shutdown_timeout_checkbox.height()/2)) + self.assertTrue(self.gui.shutdown_timeout_checkbox.isChecked()) + + # legacy mode checkbox and related widgets + if self.gui.onion.is_authenticated(): + if self.gui.onion.supports_v3_onions: + # legacy mode is off + self.assertFalse(self.gui.use_legacy_v2_onions_checkbox.isChecked()) + # persistence, stealth is hidden and disabled + self.assertFalse(self.gui.save_private_key_widget.isVisible()) + self.assertFalse(self.gui.save_private_key_checkbox.isChecked()) + self.assertFalse(self.gui.use_stealth_widget.isVisible()) + self.assertFalse(self.gui.stealth_checkbox.isChecked()) + self.assertFalse(self.gui.hidservauth_copy_button.isVisible()) + + # enable legacy mode + QtTest.QTest.mouseClick(self.gui.use_legacy_v2_onions_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.use_legacy_v2_onions_checkbox.height()/2)) + self.assertTrue(self.gui.use_legacy_v2_onions_checkbox.isChecked()) + self.assertTrue(self.gui.save_private_key_checkbox.isVisible()) + self.assertTrue(self.gui.use_stealth_widget.isVisible()) + + # enable persistent mode + QtTest.QTest.mouseClick(self.gui.save_private_key_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.save_private_key_checkbox.height()/2)) + self.assertTrue(self.gui.save_private_key_checkbox.isChecked()) + # enable stealth mode + QtTest.QTest.mouseClick(self.gui.stealth_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.stealth_checkbox.height()/2)) + self.assertTrue(self.gui.stealth_checkbox.isChecked()) + # now that stealth, persistence are enabled, we can't turn off legacy mode + self.assertFalse(self.gui.use_legacy_v2_onions_checkbox.isEnabled()) + # disable stealth, persistence + QtTest.QTest.mouseClick(self.gui.save_private_key_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.save_private_key_checkbox.height()/2)) + QtTest.QTest.mouseClick(self.gui.stealth_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.stealth_checkbox.height()/2)) + # legacy mode checkbox is enabled again + self.assertTrue(self.gui.use_legacy_v2_onions_checkbox.isEnabled()) + # uncheck legacy mode + QtTest.QTest.mouseClick(self.gui.use_legacy_v2_onions_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.use_legacy_v2_onions_checkbox.height()/2)) + # legacy options hidden again + self.assertFalse(self.gui.save_private_key_widget.isVisible()) + self.assertFalse(self.gui.use_stealth_widget.isVisible()) + + # re-enable legacy mode + QtTest.QTest.mouseClick(self.gui.use_legacy_v2_onions_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.use_legacy_v2_onions_checkbox.height()/2)) + + else: + # legacy mode setting is hidden + self.assertFalse(self.gui.use_legacy_v2_onions_checkbox.isVisible()) + # legacy options are showing + self.assertTrue(self.gui.save_private_key_widget.isVisible()) + self.assertTrue(self.gui.use_stealth_widget.isVisible()) + + # enable them all again so that we can see the setting stick in settings.json + QtTest.QTest.mouseClick(self.gui.save_private_key_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.save_private_key_checkbox.height()/2)) + QtTest.QTest.mouseClick(self.gui.stealth_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.stealth_checkbox.height()/2)) + else: + # None of the onion settings should appear + self.assertFalse(self.gui.use_legacy_v2_onions_checkbox.isVisible()) + self.assertFalse(self.gui.save_private_key_widget.isVisible()) + self.assertFalse(self.gui.save_private_key_checkbox.isChecked()) + self.assertFalse(self.gui.use_stealth_widget.isVisible()) + self.assertFalse(self.gui.stealth_checkbox.isChecked()) + self.assertFalse(self.gui.hidservauth_copy_button.isVisible()) + + # stay open toggled off, on + self.assertTrue(self.gui.close_after_first_download_checkbox.isChecked()) + QtTest.QTest.mouseClick(self.gui.close_after_first_download_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.close_after_first_download_checkbox.height()/2)) + self.assertFalse(self.gui.close_after_first_download_checkbox.isChecked()) + + # receive mode + self.gui.downloads_dir_lineedit.setText('/tmp/OnionShareSettingsTest') + + + # bundled mode is enabled + self.assertTrue(self.gui.connection_type_bundled_radio.isEnabled()) + self.assertTrue(self.gui.connection_type_bundled_radio.isChecked()) + # bridge options are shown + self.assertTrue(self.gui.connection_type_bridges_radio_group.isVisible()) + # bridges are set to custom + self.assertFalse(self.gui.tor_bridges_no_bridges_radio.isChecked()) + self.assertTrue(self.gui.tor_bridges_use_custom_radio.isChecked()) + + # switch to obfs4 + QtTest.QTest.mouseClick(self.gui.tor_bridges_use_obfs4_radio, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.tor_bridges_use_obfs4_radio.height()/2)) + self.assertTrue(self.gui.tor_bridges_use_obfs4_radio.isChecked()) + + # custom bridges are hidden + self.assertFalse(self.gui.tor_bridges_use_custom_textbox_options.isVisible()) + # other modes are unchecked but enabled + self.assertTrue(self.gui.connection_type_automatic_radio.isEnabled()) + self.assertTrue(self.gui.connection_type_control_port_radio.isEnabled()) + self.assertTrue(self.gui.connection_type_socket_file_radio.isEnabled()) + self.assertFalse(self.gui.connection_type_automatic_radio.isChecked()) + self.assertFalse(self.gui.connection_type_control_port_radio.isChecked()) + self.assertFalse(self.gui.connection_type_socket_file_radio.isChecked()) + + # enable automatic mode + QtTest.QTest.mouseClick(self.gui.connection_type_automatic_radio, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.connection_type_automatic_radio.height()/2)) + self.assertTrue(self.gui.connection_type_automatic_radio.isChecked()) + # bundled is off + self.assertFalse(self.gui.connection_type_bundled_radio.isChecked()) + # bridges are hidden + self.assertFalse(self.gui.connection_type_bridges_radio_group.isVisible()) + + # auth type is hidden in bundled or automatic mode + self.assertFalse(self.gui.authenticate_no_auth_radio.isVisible()) + self.assertFalse(self.gui.authenticate_password_radio.isVisible()) + + # enable control port mode + QtTest.QTest.mouseClick(self.gui.connection_type_control_port_radio, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.connection_type_control_port_radio.height()/2)) + self.assertTrue(self.gui.connection_type_control_port_radio.isChecked()) + # automatic is off + self.assertFalse(self.gui.connection_type_automatic_radio.isChecked()) + # auth options appear + self.assertTrue(self.gui.authenticate_no_auth_radio.isVisible()) + self.assertTrue(self.gui.authenticate_password_radio.isVisible()) + + # enable socket mode + QtTest.QTest.mouseClick(self.gui.connection_type_socket_file_radio, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.connection_type_socket_file_radio.height()/2)) + self.assertTrue(self.gui.connection_type_socket_file_radio.isChecked()) + # control port is off + self.assertFalse(self.gui.connection_type_control_port_radio.isChecked()) + # auth options are still present + self.assertTrue(self.gui.authenticate_no_auth_radio.isVisible()) + self.assertTrue(self.gui.authenticate_password_radio.isVisible()) + + # re-enable bundled mode + QtTest.QTest.mouseClick(self.gui.connection_type_bundled_radio, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.connection_type_bundled_radio.height()/2)) + # go back to custom bridges + QtTest.QTest.mouseClick(self.gui.tor_bridges_use_custom_radio, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.tor_bridges_use_custom_radio.height()/2)) + self.assertTrue(self.gui.tor_bridges_use_custom_radio.isChecked()) + self.assertTrue(self.gui.tor_bridges_use_custom_textbox.isVisible()) + self.assertFalse(self.gui.tor_bridges_use_obfs4_radio.isChecked()) + self.gui.tor_bridges_use_custom_textbox.setPlainText('94.242.249.2:83 E25A95F1DADB739F0A83EB0223A37C02FD519306\n148.251.90.59:7510 019F727CA6DCA6CA5C90B55E477B7D87981E75BC\n93.80.47.217:41727 A6A0D497D98097FCFE91D639548EE9E34C15CDD3') + + # Test that the Settings Dialog can save the settings and close itself + QtTest.QTest.mouseClick(self.gui.save_button, QtCore.Qt.LeftButton) + self.assertFalse(self.gui.isVisible()) + + # Test our settings are reflected in the settings json + with open('/tmp/settings.json') as f: + data = json.load(f) + + self.assertTrue(data["public_mode"]) + self.assertTrue(data["shutdown_timeout"]) + + if self.gui.onion.is_authenticated(): + if self.gui.onion.supports_v3_onions: + self.assertTrue(data["use_legacy_v2_onions"]) + self.assertTrue(data["save_private_key"]) + self.assertTrue(data["use_stealth"]) + else: + self.assertFalse(data["use_legacy_v2_onions"]) + self.assertFalse(data["save_private_key"]) + self.assertFalse(data["use_stealth"]) + + self.assertEqual(data["downloads_dir"], "/tmp/OnionShareSettingsTest") + self.assertFalse(data["close_after_first_download"]) + self.assertEqual(data["connection_type"], "bundled") + self.assertFalse(data["tor_bridges_use_obfs4"]) + self.assertEqual(data["tor_bridges_use_custom_bridges"], "Bridge 94.242.249.2:83 E25A95F1DADB739F0A83EB0223A37C02FD519306\nBridge 148.251.90.59:7510 019F727CA6DCA6CA5C90B55E477B7D87981E75BC\nBridge 93.80.47.217:41727 A6A0D497D98097FCFE91D639548EE9E34C15CDD3\n") diff --git a/tests/local_onionshare_settings_dialog_legacy_tor_test.py b/tests/local_onionshare_settings_dialog_legacy_tor_test.py new file mode 100644 index 00000000..d08362f1 --- /dev/null +++ b/tests/local_onionshare_settings_dialog_legacy_tor_test.py @@ -0,0 +1,27 @@ +#!/usr/bin/env python3 +import json +import unittest +import time +from PyQt5 import QtCore, QtTest + +from onionshare import strings +from .SettingsGuiBaseTest import SettingsGuiBaseTest, OnionStub + + +class SettingsGuiTest(unittest.TestCase, SettingsGuiBaseTest): + @classmethod + def setUpClass(cls): + cls.gui = SettingsGuiBaseTest.set_up() + + @classmethod + def tearDownClass(cls): + SettingsGuiBaseTest.tear_down() + + def test_gui_legacy_tor(self): + self.gui.onion = OnionStub(True, False) + self.gui.reload_settings() + self.run_settings_gui_tests() + + +if __name__ == "__main__": + unittest.main() diff --git a/tests/local_onionshare_settings_dialog_no_tor_test.py b/tests/local_onionshare_settings_dialog_no_tor_test.py new file mode 100644 index 00000000..a10c2f2e --- /dev/null +++ b/tests/local_onionshare_settings_dialog_no_tor_test.py @@ -0,0 +1,27 @@ +#!/usr/bin/env python3 +import json +import unittest +import time +from PyQt5 import QtCore, QtTest + +from onionshare import strings +from .SettingsGuiBaseTest import SettingsGuiBaseTest, OnionStub + + +class SettingsGuiTest(unittest.TestCase, SettingsGuiBaseTest): + @classmethod + def setUpClass(cls): + cls.gui = SettingsGuiBaseTest.set_up() + + @classmethod + def tearDownClass(cls): + SettingsGuiBaseTest.tear_down() + + def test_gui_no_tor(self): + self.gui.onion = OnionStub(False) + self.gui.reload_settings() + self.run_settings_gui_tests() + + +if __name__ == "__main__": + unittest.main() diff --git a/tests/local_onionshare_settings_dialog_test.py b/tests/local_onionshare_settings_dialog_test.py deleted file mode 100644 index c1e48122..00000000 --- a/tests/local_onionshare_settings_dialog_test.py +++ /dev/null @@ -1,172 +0,0 @@ -#!/usr/bin/env python3 -import json -import unittest -from PyQt5 import QtCore, QtTest - -from onionshare import strings -from .SettingsGuiBaseTest import SettingsGuiBaseTest - -class SettingsGuiTest(unittest.TestCase, SettingsGuiBaseTest): - @classmethod - def setUpClass(cls): - test_settings = { - "no_bridges": False, - "tor_bridges_use_custom_bridges": "Bridge 1.2.3.4:56 EEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEE\nBridge 5.6.7.8:910 EEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEE\nBridge 11.12.13.14:1516 EEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEE\n", - } - cls.gui = SettingsGuiBaseTest.set_up(test_settings) - - @classmethod - def tearDownClass(cls): - SettingsGuiBaseTest.tear_down() - - def test_gui(self): - self.gui.show() - # Window is shown - self.assertTrue(self.gui.isVisible()) - self.assertEqual(self.gui.windowTitle(), strings._('gui_settings_window_title')) - # Check for updates button is hidden - self.assertFalse(self.gui.check_for_updates_button.isVisible()) - - # public mode is off - self.assertFalse(self.gui.public_mode_checkbox.isChecked()) - # enable public mode - QtTest.QTest.mouseClick(self.gui.public_mode_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.public_mode_checkbox.height()/2)) - self.assertTrue(self.gui.public_mode_checkbox.isChecked()) - - # shutdown timer is off - self.assertFalse(self.gui.shutdown_timeout_checkbox.isChecked()) - # enable shutdown timer - QtTest.QTest.mouseClick(self.gui.shutdown_timeout_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.shutdown_timeout_checkbox.height()/2)) - self.assertTrue(self.gui.shutdown_timeout_checkbox.isChecked()) - - # legacy mode checkbox and related widgets - # legacy mode is off - self.assertFalse(self.gui.use_legacy_v2_onions_checkbox.isChecked()) - # persistence, stealth is hidden and disabled - self.assertFalse(self.gui.save_private_key_widget.isVisible()) - self.assertFalse(self.gui.save_private_key_checkbox.isChecked()) - self.assertFalse(self.gui.use_stealth_widget.isVisible()) - self.assertFalse(self.gui.stealth_checkbox.isChecked()) - self.assertFalse(self.gui.hidservauth_copy_button.isVisible()) - - # enable legacy mode - QtTest.QTest.mouseClick(self.gui.use_legacy_v2_onions_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.use_legacy_v2_onions_checkbox.height()/2)) - self.assertTrue(self.gui.use_legacy_v2_onions_checkbox.isChecked()) - self.assertTrue(self.gui.save_private_key_checkbox.isVisible()) - self.assertTrue(self.gui.use_stealth_widget.isVisible()) - # enable persistent mode - QtTest.QTest.mouseClick(self.gui.save_private_key_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.save_private_key_checkbox.height()/2)) - self.assertTrue(self.gui.save_private_key_checkbox.isChecked()) - # enable stealth mode - QtTest.QTest.mouseClick(self.gui.stealth_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.stealth_checkbox.height()/2)) - self.assertTrue(self.gui.stealth_checkbox.isChecked()) - # now that stealth, persistence are enabled, we can't turn off legacy mode - self.assertFalse(self.gui.use_legacy_v2_onions_checkbox.isEnabled()) - # disable stealth, persistence - QtTest.QTest.mouseClick(self.gui.save_private_key_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.save_private_key_checkbox.height()/2)) - QtTest.QTest.mouseClick(self.gui.stealth_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.stealth_checkbox.height()/2)) - # legacy mode checkbox is enabled again - self.assertTrue(self.gui.use_legacy_v2_onions_checkbox.isEnabled()) - # uncheck legacy mode - QtTest.QTest.mouseClick(self.gui.use_legacy_v2_onions_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.use_legacy_v2_onions_checkbox.height()/2)) - # legacy options hidden again - self.assertFalse(self.gui.save_private_key_widget.isVisible()) - self.assertFalse(self.gui.use_stealth_widget.isVisible()) - # enable them all again so that we can see the setting stick in settings.json - QtTest.QTest.mouseClick(self.gui.use_legacy_v2_onions_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.use_legacy_v2_onions_checkbox.height()/2)) - QtTest.QTest.mouseClick(self.gui.save_private_key_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.save_private_key_checkbox.height()/2)) - QtTest.QTest.mouseClick(self.gui.stealth_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.stealth_checkbox.height()/2)) - - - # stay open toggled off, on - self.assertTrue(self.gui.close_after_first_download_checkbox.isChecked()) - QtTest.QTest.mouseClick(self.gui.close_after_first_download_checkbox, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.close_after_first_download_checkbox.height()/2)) - self.assertFalse(self.gui.close_after_first_download_checkbox.isChecked()) - - # receive mode - self.gui.downloads_dir_lineedit.setText('/tmp/OnionShareSettingsTest') - - - # bundled mode is enabled - self.assertTrue(self.gui.connection_type_bundled_radio.isEnabled()) - self.assertTrue(self.gui.connection_type_bundled_radio.isChecked()) - # bridge options are shown - self.assertTrue(self.gui.connection_type_bridges_radio_group.isVisible()) - # bridges are set to custom - self.assertFalse(self.gui.tor_bridges_no_bridges_radio.isChecked()) - self.assertTrue(self.gui.tor_bridges_use_custom_radio.isChecked()) - - # switch to obfs4 - QtTest.QTest.mouseClick(self.gui.tor_bridges_use_obfs4_radio, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.tor_bridges_use_obfs4_radio.height()/2)) - self.assertTrue(self.gui.tor_bridges_use_obfs4_radio.isChecked()) - - # custom bridges are hidden - self.assertFalse(self.gui.tor_bridges_use_custom_textbox_options.isVisible()) - # other modes are unchecked but enabled - self.assertTrue(self.gui.connection_type_automatic_radio.isEnabled()) - self.assertTrue(self.gui.connection_type_control_port_radio.isEnabled()) - self.assertTrue(self.gui.connection_type_socket_file_radio.isEnabled()) - self.assertFalse(self.gui.connection_type_automatic_radio.isChecked()) - self.assertFalse(self.gui.connection_type_control_port_radio.isChecked()) - self.assertFalse(self.gui.connection_type_socket_file_radio.isChecked()) - - # enable automatic mode - QtTest.QTest.mouseClick(self.gui.connection_type_automatic_radio, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.connection_type_automatic_radio.height()/2)) - self.assertTrue(self.gui.connection_type_automatic_radio.isChecked()) - # bundled is off - self.assertFalse(self.gui.connection_type_bundled_radio.isChecked()) - # bridges are hidden - self.assertFalse(self.gui.connection_type_bridges_radio_group.isVisible()) - - # auth type is hidden in bundled or automatic mode - self.assertFalse(self.gui.authenticate_no_auth_radio.isVisible()) - self.assertFalse(self.gui.authenticate_password_radio.isVisible()) - - # enable control port mode - QtTest.QTest.mouseClick(self.gui.connection_type_control_port_radio, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.connection_type_control_port_radio.height()/2)) - self.assertTrue(self.gui.connection_type_control_port_radio.isChecked()) - # automatic is off - self.assertFalse(self.gui.connection_type_automatic_radio.isChecked()) - # auth options appear - self.assertTrue(self.gui.authenticate_no_auth_radio.isVisible()) - self.assertTrue(self.gui.authenticate_password_radio.isVisible()) - - # enable socket mode - QtTest.QTest.mouseClick(self.gui.connection_type_socket_file_radio, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.connection_type_socket_file_radio.height()/2)) - self.assertTrue(self.gui.connection_type_socket_file_radio.isChecked()) - # control port is off - self.assertFalse(self.gui.connection_type_control_port_radio.isChecked()) - # auth options are still present - self.assertTrue(self.gui.authenticate_no_auth_radio.isVisible()) - self.assertTrue(self.gui.authenticate_password_radio.isVisible()) - - # re-enable bundled mode - QtTest.QTest.mouseClick(self.gui.connection_type_bundled_radio, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.connection_type_bundled_radio.height()/2)) - # go back to custom bridges - QtTest.QTest.mouseClick(self.gui.tor_bridges_use_custom_radio, QtCore.Qt.LeftButton, pos=QtCore.QPoint(2,self.gui.tor_bridges_use_custom_radio.height()/2)) - self.assertTrue(self.gui.tor_bridges_use_custom_radio.isChecked()) - self.assertTrue(self.gui.tor_bridges_use_custom_textbox.isVisible()) - self.assertFalse(self.gui.tor_bridges_use_obfs4_radio.isChecked()) - self.gui.tor_bridges_use_custom_textbox.setPlainText('94.242.249.2:83 E25A95F1DADB739F0A83EB0223A37C02FD519306\n148.251.90.59:7510 019F727CA6DCA6CA5C90B55E477B7D87981E75BC\n93.80.47.217:41727 A6A0D497D98097FCFE91D639548EE9E34C15CDD3') - - # Test that the Settings Dialog can save the settings and close itself - QtTest.QTest.mouseClick(self.gui.save_button, QtCore.Qt.LeftButton) - self.assertFalse(self.gui.isVisible()) - - # Test our settings are reflected in the settings json - with open('/tmp/settings.json') as f: - data = json.load(f) - - self.assertTrue(data["public_mode"]) - self.assertTrue(data["shutdown_timeout"]) - self.assertTrue(data["use_legacy_v2_onions"]) - self.assertTrue(data["save_private_key"]) - self.assertTrue(data["use_stealth"]) - self.assertEqual(data["downloads_dir"], "/tmp/OnionShareSettingsTest") - self.assertFalse(data["close_after_first_download"]) - self.assertEqual(data["connection_type"], "bundled") - self.assertFalse(data["tor_bridges_use_obfs4"]) - self.assertEqual(data["tor_bridges_use_custom_bridges"], "Bridge 94.242.249.2:83 E25A95F1DADB739F0A83EB0223A37C02FD519306\nBridge 148.251.90.59:7510 019F727CA6DCA6CA5C90B55E477B7D87981E75BC\nBridge 93.80.47.217:41727 A6A0D497D98097FCFE91D639548EE9E34C15CDD3\n") - -if __name__ == "__main__": - unittest.main() diff --git a/tests/local_onionshare_settings_dialog_v3_tor_test.py b/tests/local_onionshare_settings_dialog_v3_tor_test.py new file mode 100644 index 00000000..815b2f72 --- /dev/null +++ b/tests/local_onionshare_settings_dialog_v3_tor_test.py @@ -0,0 +1,26 @@ +#!/usr/bin/env python3 +import json +import unittest +from PyQt5 import QtCore, QtTest + +from onionshare import strings +from .SettingsGuiBaseTest import SettingsGuiBaseTest, OnionStub + + +class SettingsGuiTest(unittest.TestCase, SettingsGuiBaseTest): + @classmethod + def setUpClass(cls): + cls.gui = SettingsGuiBaseTest.set_up() + + @classmethod + def tearDownClass(cls): + SettingsGuiBaseTest.tear_down() + + def test_gui_v3_tor(self): + self.gui.onion = OnionStub(True, True) + self.gui.reload_settings() + self.run_settings_gui_tests() + + +if __name__ == "__main__": + unittest.main()