diff --git a/CHANGELOG.md b/CHANGELOG.md index 8912add..66e0b1d 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,24 +1,5 @@ # Changelog Backuppy -## [0.10] - 2021-05-11 -### Added -- CLI-mode: check if user paths from user-input exists -- CLI-mode: prevent identical source and target path - -## [0.9] - 2021-05-10 -### Added -- CLI-mode: It's now possible to end the program anytime with ":q" (or ESC-key) and pressing ENTER. -- CLI-mode: Colored output on traces -- New helper script "utils.py" - -### Changed -- Code refactoring (get rid of global variables and constants, instead pass as arguments) - -## [0.8.1] - 2021-05-10 -### Fixed -- CLI-mode: Show text "Programm interrupted by user." instead of error message when Ctrl+C was pressed. -- CLI-mode: Removed obsolete trace messages - ## [0.8] - 2021-05-07 ### Added - GUI-mode: Introduce "Browse"-button on directory-selection dialogs diff --git a/install.py b/install.py index 9113aba..d6468be 100644 --- a/install.py +++ b/install.py @@ -1,7 +1,7 @@ #!/usr/bin/env python3 """ project: Backuppy -version: 0.10 +version: 0.8 file: install.py summary: python installer-script in CLI-mode """ @@ -9,90 +9,114 @@ summary: python installer-script in CLI-mode # Standard library imports import sys import os +import time # local imports -from utils import set_language, query, query_path, _print, trace, paths_are_identical +from languages import english +from languages import german # local globals -VERSION: str = "0.10" +# ---------------------- +VERSION: str = "0.8" EMAIL = "fotocoder@joschu.ch" EXCLUDE_FILE = "exclude.txt" BACKUPPY_SCRIPT = "Backuppy.sh" +# ---------------------- +MYDIR = os.getcwd() +EXCLUDE: bool = False +SHELL = os.environ.get("SHELL") +HOME = os.environ.get("HOME") +LANG_EN = "English" +LANG_DE = "German" +LANGUAGE = LANG_EN +RSYNC_CMD: str = None -def main_install_cli(mydir, exclude_file): - language = query("welcome") - if not language: - return False, None, None - set_language(language) +def set_language(language): + global LANGUAGE + LANGUAGE = language - _print("languagepack") +def trace(message_txt): + """ Print a formatted message to std out. """ + print("[ OK ] " + message_txt) - _print("intromsg1") +def get_lang_text(search_str: str): + global LANGUAGE + """ Returns a string from the appropriate language file. """ + return_str: str = eval("english." + search_str) + if LANGUAGE == LANG_DE: + return_str = eval("german." + search_str) + return return_str - _print("intromsg2") +def main_install_cli(): + language = input("Hello, first of all, which language do you prefer: German [DE] or English [EN]?\n> ") + if language.upper() == "DE": + set_language(LANG_DE) + print("Perfekt, nun ist das deutsche Sprachpaket aktiviert. Willkommen!\n") + else: + print("Perfect, the English language package is now activated. Welcome!.\n") + + time.sleep(1) + + print("\n" + get_lang_text("intromsg1") + "\n") + time.sleep(1) + + print("\n" + get_lang_text("intromsg2") + "\n") + time.sleep(1) # which Rsync options are available and which one you want to use - _print("rsyncopt", wait=2) + print(get_lang_text("rsyncopt") + "\n") + time.sleep(1) # asks if you want to exclude files/directories from backup and creates an exclude file in case of Yes - exclude = query("excludefile1") - if not exclude: - return False, None, None - elif exclude.upper() in ("J", "Y"): - _print("excludefile2") - exclude = True + exclude = input(get_lang_text("excludefile1") + "\n> ") + global EXCLUDE + if exclude.upper() in ("J", "Y"): + EXCLUDE = True + print(get_lang_text("excludefile2") + "\n") else: - _print("excludefile3") - exclude = False + EXCLUDE = False + print(get_lang_text("excludefile3") + "\n") + time.sleep(1) # Asks for the source directory which should be saved - _print("srcdir1") - sourcedir = query_path("srcdir2") - if not sourcedir: - return False, None, None + print(get_lang_text("srcdir1")) + time.sleep(1) + sourcedir = input(get_lang_text("srcdir2") + "\n> ") - #_print("srcdir3_1") - #print(sourcedir) - _print("srcdir3_2") + print(f"{get_lang_text('srcdir3_1')} {sourcedir} {get_lang_text('srcdir3_2')}") + time.sleep(1) # asks for the destination directory in which the backup should be saved - targetdir = query_path("targetdir1") - while paths_are_identical(sourcedir, targetdir): - _print("paths_must_differ") - targetdir = query_path("targetdir1") - if not targetdir: - return False, None, None - - #_print("targetdir2_1") - #print(targetdir) - _print("targetdir2_2") + targetdir = input(get_lang_text("targetdir1") + "\n> ") + print(f"{get_lang_text('targetdir2_1')} {targetdir} {get_lang_text('targetdir2_2')}") + time.sleep(1) # collects all the information needed to execute the rsync command and creates it. - _print("collect", wait=2) + print(get_lang_text("collect") + "\n") + time.sleep(1) + exclude_file = os.path.join(MYDIR, EXCLUDE_FILE) + + RSYNC_CMD = f"rsync -aqp --exclude-from={exclude_file} {sourcedir} {targetdir}" - rsync_cmd = f"rsync -aqp --exclude-from={os.path.join(mydir, exclude_file)} {sourcedir} {targetdir}" - - print(f"{rsync_cmd}") + print(f"{RSYNC_CMD}") + time.sleep(1) # Outro - _print("outro1", wait=2) + print(get_lang_text("outro1")) + time.sleep(2) + print(get_lang_text("outro2") + " " + EMAIL) - _print("outro2") - print(EMAIL) + return True, EXCLUDE, RSYNC_CMD - return True, exclude, rsync_cmd - -def create_exclude_file(mydir, exclude_file): - exclude_file = os.path.join(mydir, exclude_file) +def create_exclude_file(directory, exclude_file): + exclude_file = os.path.join(directory, exclude_file) with open(exclude_file, "w") as fExclude: trace(f"creating exclude-file '{exclude_file}'.") fExclude.write("\n") -def create_alias(mydir, backuppy_script): - shell = os.environ.get("SHELL") - home_dir = os.environ.get("HOME") +def create_alias(shell, home_dir, directory, backuppy_script): # alias entry in .bashrc or .zshrc - backuppy_script = os.path.join(mydir, backuppy_script) + backuppy_script = os.path.join(directory, backuppy_script) alias_str = f"alias backuppy='sudo {backuppy_script}'" # Check for installed ZSH @@ -124,32 +148,37 @@ def create_backuppy_script(directory, backuppy_script, rsync_cmd): os.chmod(backuppy_file, 0o777) # make file executable -def do_the_install(mydir: str, exclude_file, is_exclude: bool, backuppy_script: str, rsync_cmd: str): +def do_the_install(is_exclude: bool, rsync_cmd: str): """ Creates scripts and entries based on environment variables. """ if is_exclude: - create_exclude_file(mydir, exclude_file) + create_exclude_file(MYDIR, EXCLUDE_FILE) if rsync_cmd: - create_backuppy_script(mydir, backuppy_script, rsync_cmd) - create_alias(mydir, backuppy_script) + create_backuppy_script(MYDIR, BACKUPPY_SCRIPT, rsync_cmd) + create_alias(SHELL, HOME, MYDIR, BACKUPPY_SCRIPT) def main(argv): trace(f"Starting Backuppy install.py v{VERSION}") is_finalized = False - mydir = os.getcwd() if argv and argv[0] == "--gui": from install_gui import main_install_gui trace("Starting GUI-version.") - is_finalized, is_exclude, rsync_cmd = main_install_gui(mydir, EXCLUDE_FILE) # collect user input via GUI and store in env. variables + is_finalized, is_exclude, rsync_cmd = main_install_gui() # collect user input via GUI and store in env. variables else: trace("Starting CLI-version.\n") - is_finalized, is_exclude, rsync_cmd = main_install_cli(mydir, EXCLUDE_FILE) # collect user input via CLI and store in env. variables + is_finalized, is_exclude, rsync_cmd = main_install_cli() # collect user input via CLI and store in env. variables + if is_finalized: + print("CLI finalized.") + if is_exclude: + print("exclude is true.") + if rsync_cmd: + print("rsync command returned: " + rsync_cmd) if is_finalized: - do_the_install(mydir, EXCLUDE_FILE, is_exclude, BACKUPPY_SCRIPT, rsync_cmd) + do_the_install(is_exclude, rsync_cmd) trace("Ending Backuppy install.py") diff --git a/install.sh b/install.sh index 7a8c145..f1e9ffd 100755 --- a/install.sh +++ b/install.sh @@ -1,7 +1,7 @@ #!/bin/bash # """ # project: Backuppy -# version: 0.10 +# version: 0.8 # file: install.sh # summary: main entry shell script # """ diff --git a/install_gui.py b/install_gui.py index 6d9e1fd..6a3dfae 100644 --- a/install_gui.py +++ b/install_gui.py @@ -1,7 +1,7 @@ #!/usr/bin/env python3 """ project: Backuppy -version: 0.9 +version: 0.8 file: install_gui.py summary: python installer-script in GUI-mode (needs PySide2) """ @@ -13,21 +13,12 @@ import os from PySide2 import QtWidgets # local imports -from install import EXCLUDE_FILE, EMAIL -from utils import set_language, get_lang_text, LANG_EN, LANG_DE +from install import * class BackuppyWizard(QtWidgets.QWizard): - def __init__(self, parent=None, mydir=os.getcwd(), exclude_file=EXCLUDE_FILE): + def __init__(self, parent=None): super().__init__(parent) - # init instance variables - self.mydir = mydir - self.exclude_file = exclude_file - self.exclude = None - self.sourcedir = None - self.targetdir = None - self.rsync_cmd = None - self.setWindowTitle(get_lang_text("intromsg1")) self.addPage(Page01(self)) @@ -47,11 +38,11 @@ class BackuppyWizard(QtWidgets.QWizard): class Page01(QtWidgets.QWizardPage): def __init__(self, parent=None): super().__init__(parent) - self.label = QtWidgets.QLabel(get_lang_text("welcome")) + self.label = QtWidgets.QLabel("Hello, first of all, which language do you prefer: English or German?") self.comboBox = QtWidgets.QComboBox(self) - self.comboBox.addItem(LANG_EN) - self.comboBox.addItem(LANG_DE) + self.comboBox.addItem(LANG_EN, LANG_EN) + self.comboBox.addItem(LANG_DE, LANG_DE) layout = QtWidgets.QVBoxLayout() layout.addWidget(self.label) @@ -59,7 +50,8 @@ class Page01(QtWidgets.QWizardPage): self.setLayout(layout) def validatePage(self): - set_language(self.comboBox.currentText()) + if self.comboBox.currentText() == LANG_DE: + set_language(LANG_DE) return True @@ -85,9 +77,6 @@ class Page02(QtWidgets.QWizardPage): class Page03(QtWidgets.QWizardPage): def __init__(self, parent=None): super().__init__(parent) - - self.parent = parent - self.label = QtWidgets.QLabel() self.groupbox = QtWidgets.QGroupBox() self.groupbox.setFlat(True) @@ -112,26 +101,25 @@ class Page03(QtWidgets.QWizardPage): self.radio1.setChecked(True) def validatePage(self): + global EXCLUDE if self.radio1.isChecked(): - self.parent.exclude = True + EXCLUDE = True else: - self.parent.exclude = False + EXCLUDE = False return True class Page04(QtWidgets.QWizardPage): def __init__(self, parent=None): super().__init__(parent) - - self.parent = parent - self.label = QtWidgets.QLabel() layout = QtWidgets.QVBoxLayout() layout.addWidget(self.label) self.setLayout(layout) def initializePage(self): - if self.parent.exclude: + global EXCLUDE + if EXCLUDE: self.label.setText(get_lang_text("excludefile2")) else: self.label.setText(get_lang_text("excludefile3")) @@ -139,9 +127,6 @@ class Page04(QtWidgets.QWizardPage): class Page05(QtWidgets.QWizardPage): def __init__(self, parent=None): super().__init__(parent) - - self.parent = parent - self.label1 = QtWidgets.QLabel() self.label2 = QtWidgets.QLabel() self.efSourceDir = QtWidgets.QLineEdit() @@ -169,7 +154,8 @@ class Page05(QtWidgets.QWizardPage): self.efSourceDir.setText(dirName) def validatePage(self): - self.parent.sourcedir = self.efSourceDir.text() + global SOURCEDIR + SOURCEDIR = self.efSourceDir.text() return True @@ -177,9 +163,6 @@ class Page05(QtWidgets.QWizardPage): class Page06(QtWidgets.QWizardPage): def __init__(self, parent=None): super().__init__(parent) - - self.parent = parent - self.label1 = QtWidgets.QLabel() self.label2 = QtWidgets.QLabel() self.label3 = QtWidgets.QLabel() @@ -191,7 +174,7 @@ class Page06(QtWidgets.QWizardPage): def initializePage(self): self.label1.setText(get_lang_text("srcdir3_1")) - bold_text = f"
{self.parent.sourcedir}
" + bold_text = f"{SOURCEDIR}
" self.label2.setText(bold_text) self.label3.setText(get_lang_text("srcdir3_2")) @@ -199,9 +182,6 @@ class Page06(QtWidgets.QWizardPage): class Page07(QtWidgets.QWizardPage): def __init__(self, parent=None): super().__init__(parent) - - self.parent = parent - self.label1 = QtWidgets.QLabel() self.efTargetDir = QtWidgets.QLineEdit() self.pbBrowse = QtWidgets.QPushButton("Browse") @@ -226,7 +206,8 @@ class Page07(QtWidgets.QWizardPage): self.efTargetDir.setText(dirName) def validatePage(self): - self.parent.targetdir = self.efTargetDir.text() + global TARGETDIR + TARGETDIR = self.efTargetDir.text() return True @@ -234,9 +215,6 @@ class Page07(QtWidgets.QWizardPage): class Page08(QtWidgets.QWizardPage): def __init__(self, parent=None): super().__init__(parent) - - self.parent = parent - self.label1 = QtWidgets.QLabel() self.label2 = QtWidgets.QLabel() self.label3 = QtWidgets.QLabel() @@ -248,14 +226,15 @@ class Page08(QtWidgets.QWizardPage): def initializePage(self): self.label1.setText(get_lang_text("targetdir2_1")) - bold_text = f"{self.parent.targetdir}
" + bold_text = f"{TARGETDIR}
" self.label2.setText(bold_text) self.label3.setText(get_lang_text("targetdir2_2")) def validatePage(self): - exclude_file = os.path.join(self.parent.mydir, self.parent.exclude_file) + global RSYNC_CMD, MYDIR, SOURCEDIR, TARGETDIR + exclude_file = os.path.join(MYDIR, EXCLUDE_FILE) - self.parent.rsync_cmd = f"rsync -aqp --exclude-from={exclude_file} {self.parent.sourcedir} {self.parent.targetdir}" + RSYNC_CMD = f"rsync -aqp --exclude-from={exclude_file} {SOURCEDIR} {TARGETDIR}" return True @@ -263,9 +242,6 @@ class Page08(QtWidgets.QWizardPage): class Page09(QtWidgets.QWizardPage): def __init__(self, parent=None): super().__init__(parent) - - self.parent = parent - self.label1 = QtWidgets.QLabel() self.label2 = QtWidgets.QLabel() layout = QtWidgets.QVBoxLayout() @@ -275,7 +251,9 @@ class Page09(QtWidgets.QWizardPage): def initializePage(self): self.label1.setText(get_lang_text("collect")) - bold_text = f"{self.parent.rsync_cmd}
" + global RSYNC_CMD + #self.label2.setText(f"{RSYNC_CMD}") + bold_text = f"{RSYNC_CMD}
" self.label2.setText(bold_text) @@ -296,7 +274,6 @@ class Page10(QtWidgets.QWizardPage): def initializePage(self): self.label1.setText(get_lang_text("outro1")) self.label2.setText(get_lang_text("outro2")) - global EMAIL urlLink = f"{EMAIL}" self.label3.setText(urlLink) self.label3.setOpenExternalLinks(True) @@ -305,14 +282,14 @@ class Page10(QtWidgets.QWizardPage): return True -def main_install_gui(mydir, exclude_file): +def main_install_gui(): app = QtWidgets.QApplication() - wizard = BackuppyWizard(parent=None, mydir=mydir, exclude_file=exclude_file) + wizard = BackuppyWizard() wizard.show() app.exec_() - return True, wizard.exclude, wizard.rsync_cmd + return True, EXCLUDE, RSYNC_CMD if __name__ == '__main__': - is_finalized, is_exclude, rsync_cmd = main_install_gui(mydir=os.getcwd(), exclude_file=EXCLUDE_FILE) + is_finalized, is_exclude, rsync_cmd = main_install_gui() diff --git a/languages/english.py b/languages/english.py index d903678..e04cfe2 100644 --- a/languages/english.py +++ b/languages/english.py @@ -9,21 +9,15 @@ Yes="Yes" No="No" -welcome="Hello, first of all, which language do you prefer: German or English [de/EN]?" - -path_not_existing="Specified directory does not exist!" - -paths_must_differ="Source dir and target dir must differ!" - languagepack="Perfect, the English language package is now activated. Welcome!" intromsg1="Thanks for using Backuppy to make your backups!" intromsg2="The installer will now ask you a few things to adapt your backup script to your requirements." -rsyncopt="rsync offers various options, but to simplify the installation process, I have activated the options -a, -q and -p.\nIf you want to set more options, you can do that in the file 'Backuppy.sh'." +rsyncopt="rsync offers various options, but to simplify the installation process, I have activated the options -a, -q and -p. \n If you want to set more options, you can do thjat in the file 'Backuppy.sh'." -excludefile1="Now I need to know if you want to exclude one or more files/directories from your backups.\nThen you can adjust this in the 'exclude.txt'.\nThere you can exclude directories and files in the format '/directory' '/file.txt'.\nDo you want to exclude files/directories or not? [y/N]" +excludefile1="Now I need to know if you want to exclude one or more files/directories from your backups.\nThen you can adjust this in the 'exclude.txt'.\nThere you can exclude directories and files in the format '/directory' '/file.txt'.\nDo you want to exclude files/directories or not? [Y/N]" excludefile2="Perfect, then you can enter your files/directories to be excluded in the file 'exclude.txt' after completing the installation of Backuppy." @@ -34,12 +28,12 @@ srcdir1="Now we come to one of the most important parts of installing Backuppy:" srcdir2="Which directory do you want to save (e.g. the home directory)? Please enter an absolute path (e.g. '/home/username/')." srcdir3_1="you have typed in the following source path: " -srcdir3_2="(You may adjust this any time in the file 'Backuppy.sh'.)" +srcdir3_2="if this path is not correct, adjust it in the file 'Backuppy.sh'." targetdir1="Now I need to know where Backuppy should save your backups, i.e. the target directory. \n Please enter this carefully and in the same way as for the source directory." targetdir2_1="you have typed in the following destination path:" -targetdir2_2="(You may adjust this any time in the file 'Backuppy.sh'.)" +targetdir2_2="if this path is not correct, adjust it in the file 'backuppy.sh'." collect="Now we have almost reached the end of the installer. I will now create the rsync command for you and show it to you.\n If you notice a mistake, just cancel the installer and start again from the beginning.\nNote: I recommend that you download Backuppy completely again in this case." diff --git a/languages/german.py b/languages/german.py index acf978e..07508c9 100644 --- a/languages/german.py +++ b/languages/german.py @@ -9,19 +9,15 @@ Yes="Ja" No="Nein" -path_not_existing="Der angegebene Pfad existiert nicht!" - -paths_must_differ="Quell- and Zielpfad dürfen nicht identisch sein!" - languagepack="Perfekt, nun ist das deutsche Sprachpaket aktiviert. Willkommen!" intromsg1="Danke, dass du Backuppy nutzt, um deine Backups zu erstellen!" intromsg2="Der Installer wird dich nun einige Dinge abfragen, um dein Backup-Skript an deine Anforderungen anzupassen." -rsyncopt="rsync bietet verschiedene Optionen an, um das Ganze jedoch zu vereinfachen, habe ich die Optionen -a, -q und -p aktiviert.\nWenn du mehr einstellen willst, kannst du das in der Datei 'Backuppy.sh' machen." +rsyncopt="rsync bietet verschiedene Optionen an, um das Ganze jedoch zu vereinfachen, habe ich die Optionen -a, -q und -p aktiviert. \n Wenn du mehr einstellen willst, kannst du das in der Datei 'Backuppy.sh' machen." -excludefile1="Nun muss ich noch wissen, ob du ein oder mehrere Dateien/Verzeichnisse vom Backup ausschliessen möchtest.\nDann kannst du das in der 'exclude.txt' anpassen.\nDort kannst du dann im Format '/Verzeichnis' '/Datei.txt' Verzeichnisse und Dateien ausschliessen.\nMöchtest du Dateien/Verzeichnisse ausschliessen oder nicht? [j/N]" +excludefile1="Nun muss ich noch wissen, ob du ein oder mehrere Dateien/Verzeichnisse vom Backup ausschliessen möchtest.\nDann kannst du das in der 'exclude.txt' anpassen.\nDort kannst du dann im Format '/Verzeichnis' '/Datei.txt' Verzeichnisse und Dateien ausschliessen.\nMöchtest du Dateien/Verzeichnisse ausschliessen oder nicht? [J/N]" excludefile2="Perfekt, dann kannst du nach der Fertigstellung der Installation von Backuppy deine auszuschliessenden\nDateien/Verzeichnisse in der Datei 'exclude.txt eintragen." @@ -32,12 +28,12 @@ srcdir1="Nun kommen wir zu einem der wichtigesten Teile der Installation von Bac srcdir2="Welches Verzeichnis möchtest du sichern (z.B. das Homeverzeichnis)? Bitte gib einen absoluten Pfad (z.B. '/home/username/') an." srcdir3_1="du hast folgenden Quellpfad eingetippt: " -srcdir3_2="(Der Pfad kann jederzeit in der Datei 'Backuppy.sh' angepasst werden.)" +srcdir3_2="wenn dieser Pfad nicht stimmen sollte, dann passe ihn in der Datei 'Backuppy.sh' an." targetdir1="Nun muss ich noch wissen, wo Backuppy dein Backup ablegen soll, das Zielverzeichnis also.\nBitte tippe dieses gewissenhaft und auf die Weise wie beim Quellverzeichnis ein." targetdir2_1="du hast folgenden Zielpfad eingetippt:" -targetdir2_2="(Der Pfad kann jederzeit in der Datei 'Backuppy.sh' angepasst werden.)" +targetdir2_2="wenn dieser Pfad nicht stimmen sollte, dann passe ihn in der Datei 'backuppy.sh' an." collect="Nun sind wir fast am Ende des Installers angelangt. Ich erstelle nun den rsync-Befehl für dich und zeige ihn\ndir nachher nochmal.\nWenn dir da etwas auffallen sollte, brich den Installer einfach ab und fange nochmal von Vorne an.\nAchtung: ich empfehle dir, Backuppy in diesem Fall nochmal komplett neu zu installieren." diff --git a/utils.py b/utils.py deleted file mode 100644 index 4a8dea6..0000000 --- a/utils.py +++ /dev/null @@ -1,94 +0,0 @@ -#!/usr/bin/env python3 -""" -project: Backuppy -version: 0.9 -file: utils.py -summary: utilities script -""" - -# Standard library imports -import time -import os - -# local imports -from languages import english -from languages import german - -# local globals -LANG_EN = "EN" -LANG_DE = "DE" -LANGUAGE = LANG_EN -class bcolors: - """ Define colors for the std. output to console. """ - - OK = '\033[92m' #GREEN - WARNING = '\033[93m' #YELLOW - ERROR = '\033[91m' #RED - RESET = '\033[0m' #RESET COLOR - -def trace(message_txt, prefix_crlf=False, err=False): - """ Print a formatted message to std out. - - :param "message_txt" [in] The message text that should be displayed. - :param "prefix_crlf" [in] If True, a carriage return/line feed will be done prior to the message text. - - """ - - if prefix_crlf: - print("\n") - if err: - print("[ " + bcolors.ERROR + "ERR" + bcolors.RESET + " ] " + message_txt) - else: - print("[ " + bcolors.OK + "OK" + bcolors.RESET + " ] " + message_txt) - -def get_lang_text(search_str: str): - """ Returns a string from the appropriate language file. """ - return_str: str = eval("english." + search_str) - global LANGUAGE - if LANGUAGE == LANG_DE: - return_str = eval("german." + search_str) - return return_str - -def _print(message_txt: str, wait: int=1): - print("\n" + get_lang_text(message_txt) + "\n") - time.sleep(wait) - -def set_language(language): - """ Set global constant "LANGUAGE" to given language ("EN"/"DE"). """ - global LANGUAGE, LANG_DE, LANG_EN - - if str(language) and language.upper() == LANG_DE: - LANGUAGE = LANG_DE - else: - LANGUAGE = LANG_EN - -def paths_are_identical(path1: str, path2: str): - if os.path.isdir(path1): - if path1 == path2: - return True - return False - -def query_path(question_txt: str): - path = query(question_txt) - while not os.path.isdir(path): - _print("path_not_existing") - #path = input("Please retype an existing directory.\n> ") - path = query(question_txt) - return path - -def query(question_txt: str): - try: - answer_txt = input(get_lang_text(question_txt) + "\n> ") - - if not answer_txt: - answer_txt = "''" - - if answer_txt.upper() == ":Q" or answer_txt == chr(27): - trace("Program exited by user-input.") - return None - - except KeyboardInterrupt: - trace("Program interrupted by user.", prefix_crlf=True, err=True) - return None - - return answer_txt