Fix bug related to empty excludes, add version and app icon.

This commit is contained in:
Manu 2018-10-28 23:40:38 +08:00
parent af453d8a6c
commit 4c375f9547
10 changed files with 50 additions and 40 deletions

View File

@ -3,5 +3,7 @@ current_version = 0.0.3
commit = True commit = True
tag = True tag = True
[bumpversion:file:vorta/__init__.py] [bumpversion:file:Makefile]
[bumpversion:file:vorta.spec]
[bumpversion:file:vorta/_version.py]

1
.gitignore vendored
View File

@ -6,3 +6,4 @@ docs/
*.autosave *.autosave
bin/ bin/
__pycache__ __pycache__
Makefile

View File

@ -4,22 +4,22 @@
[Vorta](http://memory-alpha.wikia.com/wiki/Vorta) is a GUI for [BorgBackup](https://borgbackup.readthedocs.io). It's in alpha status and currently has the following features: [Vorta](http://memory-alpha.wikia.com/wiki/Vorta) is a GUI for [BorgBackup](https://borgbackup.readthedocs.io). It's in alpha status and currently has the following features:
- Select and manage SSH keys - [x] Select and manage SSH keys
- Initialize new remote Borg repositories - [x] Initialize new remote Borg repositories
- Create new Borg snapshots (backups) from local folders - [x] Create new Borg snapshots (backups) from local folders
- Mount existing snapshots with FUSE - [x] Mount existing snapshots with FUSE
- Settings stored in sqlite - [x] Settings stored in sqlite
- [x] Exclude options/patterns.
Missing features: Missing features:
- Scheduling for background backups. - [ ] Scheduling for background backups.
- Rule-based scheduling by time, Wifi SSID, etc. - [ ] Rule-based scheduling by time, Wifi SSID, etc.
- Repo pruning - [ ] Repo pruning
- Repo checking - [ ] Repo checking
- Securely save repo password in Keychain instead of database. - [ ] Securely save repo password in Keychain instead of database.
- Handle encrypted SSH keys - [ ] Handle encrypted SSH keys
- Check for duplicate source dirs - [ ] Check for duplicate source dirs
- Exclude options/patterns.
## Download ## Download
The app package under [Releases](https://github.com/borgbase/vorta/releases) should include everything. Just download, unzip and run. The app package under [Releases](https://github.com/borgbase/vorta/releases) should include everything. Just download, unzip and run.

View File

@ -2,7 +2,6 @@
block_cipher = None block_cipher = None
a = Analysis(['vorta/__main__.py'], a = Analysis(['vorta/__main__.py'],
pathex=['/Users/manu/Workspace/vorta'], pathex=['/Users/manu/Workspace/vorta'],
binaries=[ binaries=[
@ -35,15 +34,18 @@ exe = EXE(pyz,
upx=True, upx=True,
runtime_tmpdir=None, runtime_tmpdir=None,
console=False ) console=False )
app = BUNDLE(exe, app = BUNDLE(exe,
name='Vorta.app', name='Vorta.app',
icon=None, icon='vorta/UI/icons/app-icon.icns',
bundle_identifier=None, bundle_identifier='com.borgbase.client.macos',
info_plist={ info_plist={
'NSHighResolutionCapable': 'True', 'NSHighResolutionCapable': 'True',
'LSUIElement': '1' 'LSUIElement': '1',
'CFBundleShortVersionString': '0.0.3'
}, },
) )
# Debug package. (inspired from borg) # Debug package. (inspired from borg)
if False: if False:
coll = COLLECT(exe, coll = COLLECT(exe,

Binary file not shown.

View File

@ -1 +0,0 @@
__version__ = '0.0.3'

View File

@ -5,6 +5,6 @@ from vorta.tray_menu import TrayMenu
app = QApplication(sys.argv) app = QApplication(sys.argv)
app.thread = None app.thread = None
app.setQuitOnLastWindowClosed(False) app.setQuitOnLastWindowClosed(False)
menu = TrayMenu(app) TrayMenu(app)
sys.exit(app.exec_()) sys.exit(app.exec_())

1
vorta/_version.py Normal file
View File

@ -0,0 +1 @@
__version__ = '0.0.3'

View File

@ -27,15 +27,14 @@ class BorgThread(QtCore.QThread):
cmd[0] = meipass_borg cmd[0] = meipass_borg
self.cmd = cmd self.cmd = cmd
print(cmd)
env = os.environ.copy() env = os.environ.copy()
env['BORG_HOSTNAME_IS_UNIQUE'] = '1' env['BORG_HOSTNAME_IS_UNIQUE'] = '1'
if params.get('password') and params['password']: if params.get('password') and params['password']:
env['BORG_PASSPHRASE'] = params['password'] env['BORG_PASSPHRASE'] = params['password']
env['BORG_RSH'] = 'ssh -oStrictHostKeyChecking=no'
if params.get('ssh_key') and params['ssh_key']: if params.get('ssh_key') and params['ssh_key']:
env['BORG_RSH'] = f'ssh -i ~/.ssh/{params["ssh_key"]}' env['BORG_RSH'] += f' -i ~/.ssh/{params["ssh_key"]}'
self.env = env self.env = env
self.params = params self.params = params
@ -93,22 +92,24 @@ class BorgThread(QtCore.QThread):
cmd = ['borg', 'create', '--list', '--info', '--log-json', '--json', '-C', profile.compression] cmd = ['borg', 'create', '--list', '--info', '--log-json', '--json', '-C', profile.compression]
# Add excludes # Add excludes
# Inspired by borgmatic/borgmatic/borg/create.py # Partly inspired by borgmatic/borgmatic/borg/create.py
exclude_dirs = [] if profile.exclude_patterns is not None:
for p in profile.exclude_patterns.split('\n'): exclude_dirs = []
if p.strip(): for p in profile.exclude_patterns.split('\n'):
expanded_directory = os.path.expanduser(p.strip()) if p.strip():
exclude_dirs.append(expanded_directory) expanded_directory = os.path.expanduser(p.strip())
exclude_dirs.append(expanded_directory)
if exclude_dirs: if exclude_dirs:
pattern_file = tempfile.NamedTemporaryFile('w') pattern_file = tempfile.NamedTemporaryFile('w')
pattern_file.write('\n'.join(exclude_dirs)) pattern_file.write('\n'.join(exclude_dirs))
pattern_file.flush() pattern_file.flush()
cmd.extend(['--exclude-from', pattern_file.name]) cmd.extend(['--exclude-from', pattern_file.name])
for f in profile.exclude_if_present.split('\n'): if profile.exclude_if_present is not None:
if f.strip(): for f in profile.exclude_if_present.split('\n'):
cmd.extend(['--exclude-if-present', f.strip()]) if f.strip():
cmd.extend(['--exclude-if-present', f.strip()])
# Add repo url and source dirs. # Add repo url and source dirs.
cmd.append(f'{profile.repo.url}::{platform.node()}-{dt.now().isoformat()}') cmd.append(f'{profile.repo.url}::{platform.node()}-{dt.now().isoformat()}')

View File

@ -29,6 +29,10 @@ class SnapshotTab(SnapshotBase, SnapshotUI):
self.populate() self.populate()
def set_status(self, text):
self.mountErrors.setText(text)
self.mountErrors.repaint()
def populate(self): def populate(self):
if self.profile.repo: if self.profile.repo:
snapshots = [s for s in self.profile.repo.snapshots.select()] snapshots = [s for s in self.profile.repo.snapshots.select()]
@ -61,8 +65,9 @@ class SnapshotTab(SnapshotBase, SnapshotUI):
if mountPoint: if mountPoint:
cmd.append(mountPoint) cmd.append(mountPoint)
self.set_status('Mounting snapshot into folder', 0) self.set_status('Mounting snapshot into folder...')
thread = BorgThread(self, cmd, {}) params = {'password': self.profile.repo.password}
thread = BorgThread(self, cmd, params)
thread.updated.connect(self.mount_update_log) thread.updated.connect(self.mount_update_log)
thread.result.connect(self.mount_get_result) thread.result.connect(self.mount_get_result)
thread.start() thread.start()
@ -71,6 +76,5 @@ class SnapshotTab(SnapshotBase, SnapshotUI):
self.mountErrors.setText(text) self.mountErrors.setText(text)
def mount_get_result(self, result): def mount_get_result(self, result):
self.set_status(progress_max=100)
if result['returncode'] == 0: if result['returncode'] == 0:
self.set_status('Mounted successfully.') self.set_status('Mounted successfully.')