[improvement][ui] uninstallation does not refresh the table if it succeeds

This commit is contained in:
Vinicius Moreira
2020-06-16 11:41:06 -03:00
parent 81ddae5cbd
commit eee9e9abf8
11 changed files with 196 additions and 100 deletions

View File

@@ -277,7 +277,7 @@ class AppImageManager(SoftwareManager):
type_=MessageType.ERROR)
return False
else:
if self.uninstall(pkg, root_password, watcher):
if self.uninstall(pkg, root_password, watcher).success:
old_release = versions.history[versions.pkg_status_idx + 1]
pkg.version = old_release['0_version']
pkg.latest_version = pkg.version
@@ -300,7 +300,7 @@ class AppImageManager(SoftwareManager):
for req in requirements.to_upgrade:
watcher.change_status("{} {} ({})...".format(self.i18n['manage_window.status.upgrading'], req.pkg.name, req.pkg.version))
if not self.uninstall(req.pkg, root_password, watcher):
if not self.uninstall(req.pkg, root_password, watcher).success:
watcher.show_message(title=self.i18n['error'],
body=self.i18n['appimage.error.uninstall_current_version'],
type_=MessageType.ERROR)
@@ -316,13 +316,13 @@ class AppImageManager(SoftwareManager):
watcher.change_substatus('')
return True
def uninstall(self, pkg: AppImage, root_password: str, watcher: ProcessWatcher) -> bool:
def uninstall(self, pkg: AppImage, root_password: str, watcher: ProcessWatcher, disk_loader: DiskCacheLoader = None) -> TransactionResult:
if os.path.exists(pkg.get_disk_cache_path()):
handler = ProcessHandler(watcher)
if not handler.handle(SystemProcess(new_subprocess(['rm', '-rf', pkg.get_disk_cache_path()]))):
watcher.show_message(title=self.i18n['error'], body=self.i18n['appimage.uninstall.error.remove_folder'].format(bold(pkg.get_disk_cache_path())))
return False
return TransactionResult.fail()
de_path = self._gen_desktop_entry_path(pkg)
if os.path.exists(de_path):
@@ -330,7 +330,7 @@ class AppImageManager(SoftwareManager):
self.revert_ignored_update(pkg)
return True
return TransactionResult(success=True, installed=None, removed=[pkg])
def get_managed_types(self) -> Set[Type[SoftwarePackage]]:
return {AppImage}
@@ -508,7 +508,6 @@ class AppImageManager(SoftwareManager):
except:
traceback.print_exc()
pkg.installed = True
return TransactionResult(success=True, installed=[pkg], removed=[])
else:
watcher.show_message(title=self.i18n['error'],

View File

@@ -997,9 +997,11 @@ class ArchManager(SoftwareManager):
return True
def _uninstall(self, context: TransactionContext, remove_unneeded: bool = False):
def _uninstall(self, context: TransactionContext, remove_unneeded: bool = False, disk_loader: DiskCacheLoader = None):
self._update_progress(context, 10)
net_available = internet.is_available() if disk_loader else True
required_by = self.deps_analyser.map_all_required_by({context.name}, set())
if required_by:
@@ -1040,9 +1042,26 @@ class ArchManager(SoftwareManager):
else:
all_deps_map = None
if disk_loader and len(to_uninstall) > 1: # loading package instances in case the uninstall succeeds
instances = self.read_installed(disk_loader=disk_loader,
names={n for n in to_uninstall if n != context.name},
internet_available=net_available).installed
if len(instances) + 1 < len(to_uninstall):
self.logger.warning("Not all packages to be uninstalled could be read")
else:
instances = None
uninstalled = self._uninstall_pkgs(to_uninstall, context.root_password, context.handler)
if uninstalled:
if disk_loader: # loading package instances in case the uninstall succeeds
context.removed[context.pkg.name] = context.pkg
if instances:
for p in instances:
context.removed[p.name] = p
self._update_progress(context, 70)
if all_deps_map:
@@ -1076,10 +1095,22 @@ class ArchManager(SoftwareManager):
all_unnecessary_to_uninstall = {*unnecessary_to_uninstall, *unnecessary_to_uninstall_deps}
if not unnecessary_to_uninstall_deps or self._request_all_unncessary_uninstall_confirmation(all_unnecessary_to_uninstall, context):
if disk_loader: # loading package instances in case the uninstall succeeds
unnecessary_instances = self.read_installed(disk_loader=disk_loader,
internet_available=net_available,
names=all_unnecessary_to_uninstall).installed
else:
unnecessary_instances = None
unneded_uninstalled = self._uninstall_pkgs(all_unnecessary_to_uninstall, context.root_password, context.handler)
if unneded_uninstalled:
to_uninstall.update(all_unnecessary_to_uninstall)
if disk_loader and unnecessary_instances: # loading package instances in case the uninstall succeeds
for p in unnecessary_instances:
context.removed[p.name] = p
else:
self.logger.error("Could not uninstall some unnecessary packages")
context.watcher.print("Could not uninstall some unnecessary packages")
@@ -1102,20 +1133,28 @@ class ArchManager(SoftwareManager):
self._update_progress(context, 100)
return uninstalled
def uninstall(self, pkg: ArchPackage, root_password: str, watcher: ProcessWatcher) -> bool:
def uninstall(self, pkg: ArchPackage, root_password: str, watcher: ProcessWatcher, disk_loader: DiskCacheLoader) -> TransactionResult:
self.aur_client.clean_caches()
handler = ProcessHandler(watcher)
if self._is_database_locked(handler, root_password):
return False
return TransactionResult.fail()
return self._uninstall(TransactionContext(name=pkg.name,
change_progress=True,
arch_config=read_config(),
watcher=watcher,
root_password=root_password,
handler=handler),
remove_unneeded=True)
removed = {}
success = self._uninstall(TransactionContext(name=pkg.name,
pkg=pkg,
change_progress=True,
arch_config=read_config(),
watcher=watcher,
root_password=root_password,
handler=handler,
removed=removed),
remove_unneeded=True,
disk_loader=disk_loader) # to be able to return all uninstalled packages
if success:
return TransactionResult(success=True, installed=None, removed=[*removed.values()] if removed else [])
else:
return TransactionResult.fail()
def get_managed_types(self) -> Set["type"]:
return {ArchPackage}
@@ -1744,9 +1783,6 @@ class ArchManager(SoftwareManager):
else:
uninstalled = [p for p in pkgs_to_uninstall if p.name == conflict]
if uninstalled:
uninstalled[0].icon_path = None
uninstalled[0].icon_url = None
uninstalled[0].installed = False
context.removed[conflict] = uninstalled[0]
else:
self.logger.info("No conflict detected for '{}'".format(context.name))
@@ -1799,9 +1835,6 @@ class ArchManager(SoftwareManager):
if installed_with_same_name:
for p in installed_with_same_name:
context.removed[p.name] = p
p.installed = False
p.icon_path = None
p.icon_url = None
context.watcher.change_substatus(self.i18n['status.caching_data'].format(bold(context.name)))

View File

@@ -226,15 +226,17 @@ class FlatpakManager(SoftwareManager):
watcher.change_substatus('')
return True
def uninstall(self, pkg: FlatpakApplication, root_password: str, watcher: ProcessWatcher) -> bool:
def uninstall(self, pkg: FlatpakApplication, root_password: str, watcher: ProcessWatcher, disk_loader: DiskCacheLoader) -> TransactionResult:
uninstalled = ProcessHandler(watcher).handle(SystemProcess(subproc=flatpak.uninstall(pkg.ref, pkg.installation)))
if self.suggestions_cache:
self.suggestions_cache.delete(pkg.id)
if uninstalled:
if self.suggestions_cache:
self.suggestions_cache.delete(pkg.id)
self.revert_ignored_update(pkg)
self.revert_ignored_update(pkg)
return TransactionResult(success=True, installed=None, removed=[pkg])
return uninstalled
return TransactionResult.fail()
def get_info(self, app: FlatpakApplication) -> dict:
if app.installed:
@@ -354,7 +356,6 @@ class FlatpakManager(SoftwareManager):
except:
traceback.print_exc()
pkg.installed = res
return TransactionResult(success=res, installed=[pkg] if res else [], removed=[])
def is_enabled(self):

View File

@@ -142,13 +142,16 @@ class SnapManager(SoftwareManager):
def upgrade(self, requirements: UpgradeRequirements, root_password: str, watcher: ProcessWatcher) -> SystemProcess:
raise Exception("'upgrade' is not supported by {}".format(SnapManager.__class__.__name__))
def uninstall(self, pkg: SnapApplication, root_password: str, watcher: ProcessWatcher) -> bool:
def uninstall(self, pkg: SnapApplication, root_password: str, watcher: ProcessWatcher, disk_loader: DiskCacheLoader) -> TransactionResult:
uninstalled = ProcessHandler(watcher).handle(SystemProcess(subproc=snap.uninstall_and_stream(pkg.name, root_password)))
if self.suggestions_cache:
self.suggestions_cache.delete(pkg.name)
if uninstalled:
if self.suggestions_cache:
self.suggestions_cache.delete(pkg.name)
return uninstalled
return TransactionResult(success=True, installed=None, removed=[pkg])
return TransactionResult.fail()
def get_managed_types(self) -> Set[Type[SoftwarePackage]]:
return {SnapApplication}
@@ -205,7 +208,6 @@ class SnapManager(SoftwareManager):
if res and info_path:
pkg.has_apps_field = snap.has_apps_field(pkg.name, info_path)
pkg.installed = res
return TransactionResult(success=res, installed=[pkg] if res else [], removed=[])
else:
self.logger.error("Could not find available channels in the installation output: {}".format(output))
@@ -213,7 +215,6 @@ class SnapManager(SoftwareManager):
if info_path:
pkg.has_apps_field = snap.has_apps_field(pkg.name, info_path)
pkg.installed = res
return TransactionResult(success=res, installed=[pkg] if res else [], removed=[])
def is_enabled(self) -> bool:

View File

@@ -348,14 +348,14 @@ class WebApplicationManager(SoftwareManager):
def upgrade(self, requirements: UpgradeRequirements, root_password: str, watcher: ProcessWatcher) -> bool:
pass
def uninstall(self, pkg: WebApplication, root_password: str, watcher: ProcessWatcher) -> bool:
def uninstall(self, pkg: WebApplication, root_password: str, watcher: ProcessWatcher, disk_loader: DiskCacheLoader) -> TransactionResult:
self.logger.info("Checking if {} installation directory {} exists".format(pkg.name, pkg.installation_dir))
if not os.path.exists(pkg.installation_dir):
watcher.show_message(title=self.i18n['error'],
body=self.i18n['web.uninstall.error.install_dir.not_found'].format(bold(pkg.installation_dir)),
type_=MessageType.ERROR)
return False
return TransactionResult.fail()
self.logger.info("Removing {} installation directory {}".format(pkg.name, pkg.installation_dir))
try:
@@ -365,7 +365,7 @@ class WebApplicationManager(SoftwareManager):
body=self.i18n['web.uninstall.error.remove'].format(bold(pkg.installation_dir)),
type_=MessageType.ERROR)
traceback.print_exc()
return False
return TransactionResult.fail()
self.logger.info("Checking if {} desktop entry file {} exists".format(pkg.name, pkg.desktop_entry))
if os.path.exists(pkg.desktop_entry):
@@ -412,7 +412,8 @@ class WebApplicationManager(SoftwareManager):
watcher.show_message(title=self.i18n['error'],
body=self.i18n['web.uninstall.error.remove'].format(bold(fix_path)),
type_=MessageType.WARNING)
return True
return TransactionResult(success=True, installed=None, removed=[pkg])
def get_managed_types(self) -> Set[Type[SoftwarePackage]]:
return {WebApplication}
@@ -763,7 +764,6 @@ class WebApplicationManager(SoftwareManager):
if install_options:
pkg.options_set = install_options
pkg.installed = True
return TransactionResult(success=True, installed=[pkg], removed=[])
def _gen_desktop_entry_content(self, pkg: WebApplication) -> str: