diff --git a/CHANGELOG.md b/CHANGELOG.md
index cd1cd927..e22b5ed6 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -39,12 +39,13 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
-
- checking specific version requirements and marking packages as "cannot upgrade" when these requirements are not met (e.g: package A depends on version 1.0 of B. If A and B were selected to upgrade, and B would be upgrade to 2.0, then B would be excluded from the transaction. This new checking behavior can be disabled through the property (**check_dependency_breakage**):
+ - allowing the user to bypass dependency breakage scenarios (a popup will be displayed)
+
- AUR
- caching the PKGBUILD file used for the package installation/upgrade/downgrade (**~/.cache/bauh/arch/installed/$pkgname/PKGBUILD**)
- new settings property **aur_build_dir** -> it allows to define a custom build dir.
diff --git a/bauh/gems/arch/controller.py b/bauh/gems/arch/controller.py
index b6511bc2..f60f6fc8 100644
--- a/bauh/gems/arch/controller.py
+++ b/bauh/gems/arch/controller.py
@@ -23,7 +23,7 @@ from bauh.api.abstract.model import PackageUpdate, PackageHistory, SoftwarePacka
SuggestionPriority, CustomSoftwareAction
from bauh.api.abstract.view import MessageType, FormComponent, InputOption, SingleSelectComponent, SelectViewType, \
ViewComponent, PanelComponent, MultipleSelectComponent, TextInputComponent, TextInputType, \
- FileChooserComponent
+ FileChooserComponent, TextComponent
from bauh.api.constants import TEMP_DIR
from bauh.commons import user, internet, system
from bauh.commons.category import CategoriesDownloader
@@ -59,6 +59,7 @@ RE_PRE_DOWNLOAD_WL_PROTOCOLS = re.compile(r'^(.+::)?(https?|ftp)://.+')
RE_PRE_DOWNLOAD_BL_EXT = re.compile(r'.+\.(git|gpg)$')
RE_PKGBUILD_PKGNAME = re.compile(r'pkgname\s*=.+')
RE_CONFLICT_DETECTED = re.compile(r'\n::\s*(.+)\s+are in conflict\s*.')
+RE_DEPENDENCY_BREAKAGE = re.compile(r'\n?::\s+installing\s+(.+\s\(.+\))\sbreaks\sdependency\s\'(.+)\'\srequired\sby\s(.+)\s*', flags=re.IGNORECASE)
class TransactionContext:
@@ -795,6 +796,21 @@ class ArchManager(SoftwareManager):
return [MultipleSelectComponent(options=files, default_options={*files}, label='')]
+ def _map_dependencies_breakage(self, output: str) -> List[ViewComponent]:
+ errors = RE_DEPENDENCY_BREAKAGE.findall(output)
+
+ if errors:
+ opts = []
+
+ for idx, err in enumerate(errors):
+ opts.append(InputOption(label=self.i18n['arch.upgrade.error.dep_breakage.item'].format(*err), value=idx, read_only=True))
+
+ return [MultipleSelectComponent(label='',
+ options=opts,
+ default_options={*opts})]
+ else:
+ return [TextComponent(output)]
+
def list_related(self, pkgs: Iterable[str], all_pkgs: Iterable[str], data: Dict[str, dict], related: Set[str], provided_map: Dict[str, Set[str]]) -> Set[str]:
related.update(pkgs)
@@ -832,7 +848,7 @@ class ArchManager(SoftwareManager):
def _upgrade_repo_pkgs(self, to_upgrade: List[str], to_remove: Optional[Set[str]], handler: ProcessHandler, root_password: str,
multithread_download: bool, pkgs_data: Dict[str, dict], overwrite_files: bool = False,
status_handler: TransactionStatusHandler = None, sizes: Dict[str, int] = None, download: bool = True,
- check_syncfirst: bool = True) -> bool:
+ check_syncfirst: bool = True, skip_dependency_checks: bool = False) -> bool:
to_sync_first = None
if check_syncfirst:
@@ -883,8 +899,9 @@ class ArchManager(SoftwareManager):
self.logger.info("Upgrading {} repository packages: {}".format(len(to_upgrade), ', '.join(to_upgrade)))
success, upgrade_output = handler.handle_simple(pacman.upgrade_several(pkgnames=to_upgrade_remaining,
root_password=root_password,
- overwrite_conflicting_files=overwrite_files),
- output_handler=output_handler.handle,)
+ overwrite_conflicting_files=overwrite_files,
+ skip_dependency_checks=skip_dependency_checks),
+ output_handler=output_handler.handle)
handler.watcher.change_substatus('')
if success:
@@ -921,7 +938,31 @@ class ArchManager(SoftwareManager):
check_syncfirst=False,
pkgs_data=pkgs_data,
to_remove=None,
- sizes=sizes)
+ sizes=sizes,
+ skip_dependency_checks=skip_dependency_checks)
+ else:
+ output_handler.stop_working()
+ output_handler.join()
+ handler.watcher.print("Aborted by the user")
+ return False
+ elif ' breaks dependency ' in upgrade_output:
+ if not handler.watcher.request_confirmation(title=self.i18n['warning'].capitalize(),
+ body=self.i18n['arch.upgrade.error.dep_breakage'] + ':',
+ deny_label=self.i18n['arch.upgrade.error.dep_breakage.proceed'],
+ confirmation_label=self.i18n['arch.upgrade.error.dep_breakage.stop'],
+ components=self._map_dependencies_breakage(upgrade_output)):
+ return self._upgrade_repo_pkgs(to_upgrade=to_upgrade_remaining,
+ handler=handler,
+ root_password=root_password,
+ overwrite_files=overwrite_files,
+ status_handler=output_handler,
+ multithread_download=multithread_download,
+ download=False,
+ check_syncfirst=False,
+ pkgs_data=pkgs_data,
+ to_remove=None,
+ sizes=sizes,
+ skip_dependency_checks=True)
else:
output_handler.stop_working()
output_handler.join()
diff --git a/bauh/gems/arch/pacman.py b/bauh/gems/arch/pacman.py
index 1d3491b5..5c042d2d 100644
--- a/bauh/gems/arch/pacman.py
+++ b/bauh/gems/arch/pacman.py
@@ -707,12 +707,15 @@ def map_updates_data(pkgs: Iterable[str], files: bool = False) -> dict:
return res
-def upgrade_several(pkgnames: Iterable[str], root_password: str, overwrite_conflicting_files: bool = False) -> SimpleProcess:
+def upgrade_several(pkgnames: Iterable[str], root_password: str, overwrite_conflicting_files: bool = False, skip_dependency_checks: bool = False) -> SimpleProcess:
cmd = ['pacman', '-S', *pkgnames, '--noconfirm']
if overwrite_conflicting_files:
cmd.append('--overwrite=*')
+ if skip_dependency_checks:
+ cmd.append('-d')
+
return SimpleProcess(cmd=cmd,
root_password=root_password,
error_phrases={'error: failed to prepare transaction', 'error: failed to commit transaction', 'error: target not found'},
diff --git a/bauh/gems/arch/resources/locale/ca b/bauh/gems/arch/resources/locale/ca
index 4350d047..a5521e78 100644
--- a/bauh/gems/arch/resources/locale/ca
+++ b/bauh/gems/arch/resources/locale/ca
@@ -229,6 +229,10 @@ arch.update_summary.to_update.conflicts_dep=Conflicts with the dependency {} of
arch.update_summary.to_update.dep_conflicts=Dependency {} conflicts with {}
arch.upgrade.caching_pkgs_data=Caching updates data
arch.upgrade.error.conflicting_files=Some of the packages being upgraded want to overwrite files of another installed packages
+arch.upgrade.error.dep_breakage=Some dependency breakage issues have been detected
+arch.upgrade.error.dep_breakage.item=The new version of {} breaks the dependency {} required by the installed version of {}
+arch.upgrade.error.dep_breakage.proceed=Proceed anyway
+arch.upgrade.error.dep_breakage.stop=Cancel upgrade
arch.upgrade.conflicting_files.proceed=Allow and continue
arch.upgrade.conflicting_files.stop=Cancel upgrading
arch.upgrade.fail=Package {} upgrade failed
diff --git a/bauh/gems/arch/resources/locale/de b/bauh/gems/arch/resources/locale/de
index 9e9ce49b..a0f8a813 100644
--- a/bauh/gems/arch/resources/locale/de
+++ b/bauh/gems/arch/resources/locale/de
@@ -229,6 +229,10 @@ arch.update_summary.to_update.conflicts_dep=Conflicts with the dependency {} of
arch.update_summary.to_update.dep_conflicts=Dependency {} conflicts with {}
arch.upgrade.caching_pkgs_data=Caching updates data
arch.upgrade.error.conflicting_files=Some of the packages being upgraded want to overwrite files of another installed packages
+arch.upgrade.error.dep_breakage=Some dependency breakage issues have been detected
+arch.upgrade.error.dep_breakage.item=The new version of {} breaks the dependency {} required by the installed version of {}
+arch.upgrade.error.dep_breakage.proceed=Proceed anyway
+arch.upgrade.error.dep_breakage.stop=Cancel upgrade
arch.upgrade.conflicting_files.proceed=Allow and continue
arch.upgrade.conflicting_files.stop=Cancel upgrading
arch.upgrade.fail=Package {} upgrade failed
diff --git a/bauh/gems/arch/resources/locale/en b/bauh/gems/arch/resources/locale/en
index 13bb8423..c58dc999 100644
--- a/bauh/gems/arch/resources/locale/en
+++ b/bauh/gems/arch/resources/locale/en
@@ -230,6 +230,10 @@ arch.update_summary.to_update.conflicts_dep=Conflicts with the dependency {} of
arch.update_summary.to_update.dep_conflicts=Dependency {} conflicts with {}
arch.upgrade.caching_pkgs_data=Caching updates data
arch.upgrade.error.conflicting_files=Some of the packages being upgraded want to overwrite files of another installed packages
+arch.upgrade.error.dep_breakage=Some dependency breakage issues have been detected
+arch.upgrade.error.dep_breakage.item=The new version of {} breaks the dependency {} required by the installed version of {}
+arch.upgrade.error.dep_breakage.proceed=Proceed anyway
+arch.upgrade.error.dep_breakage.stop=Cancel upgrade
arch.upgrade.conflicting_files.proceed=Allow and continue
arch.upgrade.conflicting_files.stop=Cancel upgrading
arch.upgrade.fail=Package {} upgrade failed
diff --git a/bauh/gems/arch/resources/locale/es b/bauh/gems/arch/resources/locale/es
index bcf416a5..98c81add 100644
--- a/bauh/gems/arch/resources/locale/es
+++ b/bauh/gems/arch/resources/locale/es
@@ -229,6 +229,10 @@ arch.update_summary.to_update.conflicts_dep=Conflicta con la dependencia {} de {
arch.update_summary.to_update.dep_conflicts=La dependencia {} conflicta con {}
arch.upgrade.caching_pkgs_data=Caching upgrades data
arch.upgrade.error.conflicting_files=Algunos de los paquetes que se están actualizando desean sobrescribir archivos de otros paquetes instalados
+arch.upgrade.error.dep_breakage=Se han detectado algunos problemas de ruptura de dependencias
+arch.upgrade.error.dep_breakage.item=La nueva versión de {} rompe la dependencia {} requerida por la versión instalada de {}
+arch.upgrade.error.dep_breakage.proceed=Continuar de todos modos
+arch.upgrade.error.dep_breakage.stop=Cancelar actualización
arch.upgrade.conflicting_files.proceed=Permitir y continuar
arch.upgrade.conflicting_files.stop=Cancelar la actualización
arch.upgrade.fail=Falló la actualización del paquete {}
diff --git a/bauh/gems/arch/resources/locale/it b/bauh/gems/arch/resources/locale/it
index ddad0842..488db7aa 100644
--- a/bauh/gems/arch/resources/locale/it
+++ b/bauh/gems/arch/resources/locale/it
@@ -229,6 +229,10 @@ arch.update_summary.to_update.conflicts_dep=Conflicts with the dependency {} of
arch.update_summary.to_update.dep_conflicts=Dependency {} conflicts with {}
arch.upgrade.caching_pkgs_data=Caching updates data
arch.upgrade.error.conflicting_files=Some of the packages being upgraded want to overwrite files of another installed packages
+arch.upgrade.error.dep_breakage=Some dependency breakage issues have been detected
+arch.upgrade.error.dep_breakage.item=The new version of {} breaks the dependency {} required by the installed version of {}
+arch.upgrade.error.dep_breakage.proceed=Proceed anyway
+arch.upgrade.error.dep_breakage.stop=Cancel upgrade
arch.upgrade.conflicting_files.proceed=Allow and continue
arch.upgrade.conflicting_files.stop=Cancel upgrading
arch.upgrade.fail=Package {} upgrade failed
diff --git a/bauh/gems/arch/resources/locale/pt b/bauh/gems/arch/resources/locale/pt
index 21d92811..bf148f0c 100644
--- a/bauh/gems/arch/resources/locale/pt
+++ b/bauh/gems/arch/resources/locale/pt
@@ -229,6 +229,10 @@ arch.update_summary.to_update.conflicts_dep=Conflita com a dependência {} de {}
arch.update_summary.to_update.dep_conflicts=A dependência {} conflita com {}
arch.upgrade.caching_pkgs_data=Armazenando dados das atualizações
arch.upgrade.error.conflicting_files=Alguns dos pacotes que estão sendo atualizados querem sobrepor arquivos de outros pacotes instalados
+arch.upgrade.error.dep_breakage=Foram detectados os seguintes probemas de quebra de dependência
+arch.upgrade.error.dep_breakage.item=A nova versão de {} quebra a dependência {} requerida pela versão instalada de {}
+arch.upgrade.error.dep_breakage.proceed=Continuar mesmo assim
+arch.upgrade.error.dep_breakage.stop=Cancelar atualização
arch.upgrade.conflicting_files.proceed=Permitir e continuar
arch.upgrade.conflicting_files.stop=Cancelar atualização
arch.upgrade.fail=Atualização do pacote {} falhou
diff --git a/bauh/gems/arch/resources/locale/ru b/bauh/gems/arch/resources/locale/ru
index 51fe3fa1..9a848975 100644
--- a/bauh/gems/arch/resources/locale/ru
+++ b/bauh/gems/arch/resources/locale/ru
@@ -229,6 +229,10 @@ arch.update_summary.to_update.conflicts_dep=Конфликты с зависим
arch.update_summary.to_update.dep_conflicts=Зависимость {} конфликтует с {}
arch.upgrade.caching_pkgs_data=Caching updates data
arch.upgrade.error.conflicting_files=Some of the packages being upgraded want to overwrite files of another installed packages
+arch.upgrade.error.dep_breakage=Some dependency breakage issues have been detected
+arch.upgrade.error.dep_breakage.item=The new version of {} breaks the dependency {} required by the installed version of {}
+arch.upgrade.error.dep_breakage.proceed=Proceed anyway
+arch.upgrade.error.dep_breakage.stop=Cancel upgrade
arch.upgrade.conflicting_files.proceed=Allow and continue
arch.upgrade.conflicting_files.stop=Cancel upgrading
arch.upgrade.fail=Package {} upgrade failed
diff --git a/bauh/gems/arch/resources/locale/tr b/bauh/gems/arch/resources/locale/tr
index 0ae6eb28..8e867b99 100644
--- a/bauh/gems/arch/resources/locale/tr
+++ b/bauh/gems/arch/resources/locale/tr
@@ -229,6 +229,10 @@ arch.update_summary.to_update.conflicts_dep={} / {} bağımlılığıyla ilgili
arch.update_summary.to_update.dep_conflicts=Bağımlılık {} ile {} çakışıyor
arch.upgrade.caching_pkgs_data=Yükseltme verileri önbelleğe alınıyor
arch.upgrade.error.conflicting_files=Some of the packages being upgraded want to overwrite files of another installed packages
+arch.upgrade.error.dep_breakage=Some dependency breakage issues have been detected
+arch.upgrade.error.dep_breakage.item=The new version of {} breaks the dependency {} required by the installed version of {}
+arch.upgrade.error.dep_breakage.proceed=Proceed anyway
+arch.upgrade.error.dep_breakage.stop=Cancel upgrade
arch.upgrade.conflicting_files.proceed=Allow and continue
arch.upgrade.conflicting_files.stop=Cancel upgrading
arch.upgrade.fail={} paketi yükseltilemedi