diff --git a/CHANGELOG.md b/CHANGELOG.md index 266c6266..6a5d77ab 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,24 @@ All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/). +## [0.7.2] 2019-11-01 +### Improvements +- Snap + - not showing **License** in the info window if it defined as **unset** +- Flatpak: + - "Remotes not set" warning informing to the user that Flatpak support can be disabled +- showing suggestions if the user changes the application types available and there are no applications installed +- i18n: spanish contributions by [fitojb](https://github.com/fitojb) +- minor labels improvements + +### UI +- Displaying a **verified** green icon next to a verified publisher's name + +### Fixes +- Snap + - The application crashes due to Snap API checking when snap is not installed ( introduced in **0.7.1** ) + + ## [0.7.1] 2019-10-25 ### Features - Snap: diff --git a/bauh/__init__.py b/bauh/__init__.py index 3fdb7b7e..85695271 100644 --- a/bauh/__init__.py +++ b/bauh/__init__.py @@ -1,4 +1,4 @@ -__version__ = '0.7.1' +__version__ = '0.7.2' __app_name__ = 'bauh' import os diff --git a/bauh/gems/flatpak/controller.py b/bauh/gems/flatpak/controller.py index 0da44b1c..2f6a688b 100644 --- a/bauh/gems/flatpak/controller.py +++ b/bauh/gems/flatpak/controller.py @@ -9,7 +9,7 @@ from bauh.api.abstract.disk import DiskCacheLoader from bauh.api.abstract.handler import ProcessWatcher from bauh.api.abstract.model import PackageHistory, PackageUpdate, SoftwarePackage, PackageSuggestion from bauh.api.abstract.view import MessageType -from bauh.commons.html import strip_html +from bauh.commons.html import strip_html, bold from bauh.commons.system import SystemProcess, ProcessHandler from bauh.gems.flatpak import flatpak, suggestions from bauh.gems.flatpak.constants import FLATHUB_API_URL @@ -253,7 +253,8 @@ class FlatpakManager(SoftwareManager): def list_warnings(self, internet_available: bool) -> List[str]: if flatpak.is_installed(): if not flatpak.has_remotes_set(): - return [self.i18n['flatpak.notification.no_remotes']] + return [self.i18n['flatpak.notification.no_remotes'], + self.i18n['flatpak.notification.disable'].format(bold('Flatpak'), bold(self.i18n['manage_window.settings.gems']))] def list_suggestions(self, limit: int) -> List[PackageSuggestion]: cli_version = flatpak.get_version() diff --git a/bauh/gems/flatpak/resources/locale/en b/bauh/gems/flatpak/resources/locale/en index b538dd9d..b0415238 100644 --- a/bauh/gems/flatpak/resources/locale/en +++ b/bauh/gems/flatpak/resources/locale/en @@ -1,5 +1,6 @@ gem.flatpak.info=Applications available in the repositories configured on your system flatpak.notification.no_remotes=No Flatpak remotes set. It will not be possible to search for Flatpak apps. +flatpak.notification.disable=If you do not want to use Flatpak applications, uncheck {} in {} flatpak.downgrade.impossible.title=Error flatpak.downgrade.impossible.body=Impossible to downgrade: the app is in its first version flatpak.downgrade.commits=Reading package commits diff --git a/bauh/gems/flatpak/resources/locale/es b/bauh/gems/flatpak/resources/locale/es index 9840c5a1..9a276d5a 100644 --- a/bauh/gems/flatpak/resources/locale/es +++ b/bauh/gems/flatpak/resources/locale/es @@ -19,6 +19,7 @@ flatpak.info.subject=tema flatpak.info.type=tipo flatpak.info.version=versión flatpak.notification.no_remotes=No hay repositorios (remotes) Flatpak configurados. No será posible buscar aplicativos Flatpak. +flatpak.notification.disable=Si no desea usar aplicativos Flatpak, desmarque {} en {} flatpak.downgrade.impossible.title=Error flatpak.downgrade.impossible.body=Imposible revertir la versión: el aplicativo está en su primera versión flatpak.history.date=fecha diff --git a/bauh/gems/flatpak/resources/locale/pt b/bauh/gems/flatpak/resources/locale/pt index c811fe16..986bfdd3 100644 --- a/bauh/gems/flatpak/resources/locale/pt +++ b/bauh/gems/flatpak/resources/locale/pt @@ -19,6 +19,7 @@ flatpak.info.subject=assunto flatpak.info.type=tipo flatpak.info.version=versão flatpak.notification.no_remotes=Não há repositórios (remotes) Flatpak configurados. Não será possível buscar aplicativos Flatpak. +flatpak.notification.disable=Se não deseja usar aplicativos Flatpak, desmarque {} em {} flatpak.downgrade.impossible.title=Erro flatpak.downgrade.impossible.body=Impossível reverter a versão: o aplicativo está na sua primeira versão flatpak.history.date=data diff --git a/bauh/gems/snap/controller.py b/bauh/gems/snap/controller.py index 7ce13691..24a5f42e 100644 --- a/bauh/gems/snap/controller.py +++ b/bauh/gems/snap/controller.py @@ -45,7 +45,8 @@ class SnapManager(SoftwareManager): name=app_json.get('name'), version=app_json.get('version'), latest_version=app_json.get('version'), - description=app_json.get('description', app_json.get('summary'))) + description=app_json.get('description', app_json.get('summary')), + verified_publisher=app_json.get('developer_validation', '') == 'verified') if app.publisher and app.publisher.endswith('*'): app.verified_publisher = True @@ -140,6 +141,9 @@ class SnapManager(SoftwareManager): if info.get('commands'): info['commands'] = ' '.join(info['commands']) + if info.get('license') and info['license'] == 'unset': + del info['license'] + return info def get_history(self, pkg: SnapApplication) -> PackageHistory: @@ -197,17 +201,18 @@ class SnapManager(SoftwareManager): pass def list_warnings(self, internet_available: bool) -> List[str]: - if snap.is_installed() and not snap.is_snapd_running(): - snap_bold = bold('Snap') - return [self.i18n['snap.notification.snapd_unavailable'].format(bold('snapd'), snap_bold), - self.i18n['snap.notification.snap.disable'].format(snap_bold, bold(self.i18n['manage_window.settings.gems']))] + if snap.is_installed(): + if not snap.is_snapd_running(): + snap_bold = bold('Snap') + return [self.i18n['snap.notification.snapd_unavailable'].format(bold('snapd'), snap_bold), + self.i18n['snap.notification.snap.disable'].format(snap_bold, bold(self.i18n['manage_window.settings.gems']))] - if internet_available: - available, output = snap.is_api_available() + elif internet_available: + available, output = snap.is_api_available() - if not available: - self.logger.warning('It seems Snap API is not available. Search output: {}'.format(output)) - return [self.i18n['snap.notifications.api.unavailable'].format(bold('Snaps'), bold('Snap'))] + if not available: + self.logger.warning('It seems Snap API is not available. Search output: {}'.format(output)) + return [self.i18n['snap.notifications.api.unavailable'].format(bold('Snaps'), bold('Snap'))] def _fill_suggestion(self, pkg_name: str, priority: SuggestionPriority, out: List[PackageSuggestion]): res = self.http_client.get_json(SNAP_API_URL + '/search?q=package_name:{}'.format(pkg_name)) diff --git a/bauh/gems/snap/model.py b/bauh/gems/snap/model.py index 6a48928d..0dd7441c 100644 --- a/bauh/gems/snap/model.py +++ b/bauh/gems/snap/model.py @@ -56,6 +56,9 @@ class SnapApplication(SoftwarePackage): def get_disk_cache_path(self): return super(SnapApplication, self).get_disk_cache_path() + '/installed/' + self.name + def is_trustable(self) -> bool: + return self.verified_publisher + def get_data_to_cache(self): return { "icon_url": self.icon_url, diff --git a/bauh/gems/snap/resources/locale/en b/bauh/gems/snap/resources/locale/en index cfe914b8..36f39134 100644 --- a/bauh/gems/snap/resources/locale/en +++ b/bauh/gems/snap/resources/locale/en @@ -1,5 +1,5 @@ gem.snap.info=Applications published at https://snapcraft.io/store -snap.notification.snapd_unavailable={} seems not to be installed or enabled. {} packages will not be available. +snap.notification.snapd_unavailable={} seems not to be started or enabled. {} packages will not be available. snap.notification.snap.disable=If you do not want to use Snap applications, uncheck {} in {} snap.notifications.api.unavailable=It seems the {} API is unavailable at the moment. It will not be possible to search for new {} applications. snap.action.refresh.status=Refreshing diff --git a/bauh/gems/snap/resources/locale/es b/bauh/gems/snap/resources/locale/es index 030edd69..07e0501d 100644 --- a/bauh/gems/snap/resources/locale/es +++ b/bauh/gems/snap/resources/locale/es @@ -3,14 +3,13 @@ snap.info.commands=comandos snap.info.contact=contacto snap.info.description=descripción snap.info.license=licencia -snap.info.license.unset=no está definida snap.info.revision=revisión snap.info.tracking=tracking snap.info.installed=instalado snap.info.publisher=publicador snap.info.version=versión snap.info.size=tamaño -snap.notification.snapd_unavailable={} no parece estar instalado o habilitado. Los paquetes {} estarán indisponibles. +snap.notification.snapd_unavailable={} parece no estar inicializado o habilitado. Los paquetes {} estarán indisponibles. snap.notification.snap.disable=Si no desea usar aplicativos Snap, desmarque {} en {} snap.notifications.api.unavailable=Parece que la API de {} no está disponible en este momento. No será posible buscar nuevos aplicativos {}. snap.action.refresh.status=Actualizando diff --git a/bauh/gems/snap/resources/locale/pt b/bauh/gems/snap/resources/locale/pt index d705e1f3..4960ddc5 100644 --- a/bauh/gems/snap/resources/locale/pt +++ b/bauh/gems/snap/resources/locale/pt @@ -3,14 +3,13 @@ snap.info.commands=comandos snap.info.contact=contato snap.info.description=descrição snap.info.license=licença -snap.info.license.unset=não definida snap.info.revision=revisão snap.info.tracking=tracking snap.info.installed=instalado snap.info.publisher=publicador snap.info.version=versão snap.info.size=tamanho -snap.notification.snapd_unavailable={} não parece estar instalado ou habilitado. Os pacotes {} estarão indisponíveis. +snap.notification.snapd_unavailable={} parece não estar inicializado ou habilitado. Os pacotes {} estarão indisponíveis. snap.notification.snap.disable=Se não deseja usar aplicativos Snap, desmarque {} em {} snap.notifications.api.unavailable=Parece que a API de {} está indisponível no momento. Não será possível buscar novos aplicativos {}. snap.action.refresh.status=Atualizando diff --git a/bauh/view/qt/apps_table.py b/bauh/view/qt/apps_table.py index c4c39a4a..c9ea76c4 100644 --- a/bauh/view/qt/apps_table.py +++ b/bauh/view/qt/apps_table.py @@ -11,10 +11,10 @@ from PyQt5.QtWidgets import QTableWidget, QTableView, QMenu, QAction, QTableWidg from bauh.api.abstract.cache import MemoryCache from bauh.api.abstract.model import PackageStatus from bauh.commons.html import strip_html -from bauh.view.util import resource from bauh.view.qt import dialog from bauh.view.qt.components import IconButton from bauh.view.qt.view_model import PackageView, PackageViewStatus +from bauh.view.util import resource INSTALL_BT_STYLE = 'background: {back}; color: white; font-size: 10px; font-weight: bold' @@ -76,6 +76,7 @@ class AppsTable(QTableWidget): self.setHorizontalHeaderLabels(['' for _ in range(self.columnCount())]) self.setHorizontalScrollBarPolicy(Qt.ScrollBarAlwaysOff) self.icon_logo = QIcon(resource.get_path('img/logo.svg')) + self.pixmap_verified = QPixmap(resource.get_path('img/verified.svg')) self.network_man = QNetworkAccessManager() self.network_man.finished.connect(self._load_icon_and_cache) @@ -372,7 +373,7 @@ class AppsTable(QTableWidget): self.setItem(pkg.table_index, col, item) def _set_col_publisher(self, col: int, pkg: PackageView): - item = QLabel() + item = QToolBar() publisher = pkg.model.get_publisher() full_publisher = None @@ -384,19 +385,25 @@ class AppsTable(QTableWidget): if len(publisher) > PUBLISHER_MAX_SIZE: publisher = full_publisher[0: PUBLISHER_MAX_SIZE - 3] + '...' - if len(publisher) < PUBLISHER_MAX_SIZE: - publisher = publisher + ' ' * (PUBLISHER_MAX_SIZE - len(publisher)) - if not publisher: if not pkg.model.installed: item.setStyleSheet('QLabel { color: red; }') publisher = self.i18n['unknown'] - item.setText(' {} '.format(publisher)) + lb_name = QLabel(' {}'.format(publisher)) + item.addWidget(lb_name) if publisher and full_publisher: - item.setToolTip(self.i18n['publisher'].capitalize() + ((': ' + full_publisher) if full_publisher else '')) + lb_name.setToolTip(self.i18n['publisher'].capitalize() + ((': ' + full_publisher) if full_publisher else '')) + + if pkg.model.is_trustable(): + lb_verified = QLabel() + lb_verified.setPixmap(self.pixmap_verified) + lb_verified.setToolTip(self.i18n['publisher.verified'].capitalize()) + item.addWidget(lb_verified) + else: + lb_name.setText(lb_name.text() + " ") self.setCellWidget(pkg.table_index, col, item) diff --git a/bauh/view/qt/gem_selector.py b/bauh/view/qt/gem_selector.py index 54cced57..be810f7f 100644 --- a/bauh/view/qt/gem_selector.py +++ b/bauh/view/qt/gem_selector.py @@ -32,7 +32,7 @@ class GemSelectorPanel(QWidget): self.bt_proceed.setStyleSheet(css.OK_BUTTON) self.bt_proceed.clicked.connect(self.save) - self.bt_exit = QPushButton(i18n['exit'].capitalize()) + self.bt_exit = QPushButton(i18n['close'].capitalize()) self.bt_exit.clicked.connect(self.exit) self.gem_map = {} @@ -91,6 +91,7 @@ class GemSelectorPanel(QWidget): self.manager.reset_cache() self.manager.prepare() self.window.verify_warnings() + self.window.types_changed = True self.window.refresh_apps() self.close() diff --git a/bauh/view/qt/window.py b/bauh/view/qt/window.py index a4272147..16da819d 100755 --- a/bauh/view/qt/window.py +++ b/bauh/view/qt/window.py @@ -284,6 +284,7 @@ class ManageWindow(QWidget): self.progress_controll_enabled = True self.recent_installation = False self.recent_uninstall = False + self.types_changed = False self.dialog_about = None self.first_refresh = suggestions @@ -474,6 +475,7 @@ class ManageWindow(QWidget): self.update_pkgs(res['installed'], as_installed=as_installed, types=res['types'], keep_filters=self.recent_uninstall and res['types']) self.first_refresh = False self.recent_uninstall = False + self.types_changed = False self._hide_fields_after_recent_installation() def uninstall_app(self, app: PackageView): @@ -640,7 +642,7 @@ class ManageWindow(QWidget): commons.apply_filters(pkgv, filters, pkgs_info) if pkgs_info['apps_count'] == 0: - if self.first_refresh: + if self.first_refresh or self.types_changed: self._begin_search('') self.thread_suggestions.start() return diff --git a/bauh/view/resources/img/verified.svg b/bauh/view/resources/img/verified.svg new file mode 100644 index 00000000..5cf6c99d --- /dev/null +++ b/bauh/view/resources/img/verified.svg @@ -0,0 +1,62 @@ + + + + + + image/svg+xml + + + + + + + + + diff --git a/bauh/view/resources/locale/en b/bauh/view/resources/locale/en index 9e34ffbe..b876f5f8 100644 --- a/bauh/view/resources/locale/en +++ b/bauh/view/resources/locale/en @@ -146,4 +146,6 @@ screenshots,download.running=downloading image screenshots.download.no_content=No content to display screenshots.download.no_response=Image not found continue=continue -stable=stable \ No newline at end of file +stable=stable +close=close +publisher.verified=verified \ No newline at end of file diff --git a/bauh/view/resources/locale/es b/bauh/view/resources/locale/es index 2474c832..323c8e16 100644 --- a/bauh/view/resources/locale/es +++ b/bauh/view/resources/locale/es @@ -191,3 +191,5 @@ screenshots.download.no_content=No hay contenido para mostrar screenshots.download.no_response=No se encontró la imagen continue=continuar stable=estable +close=cerrar +publisher.verified=verificado diff --git a/bauh/view/resources/locale/pt b/bauh/view/resources/locale/pt index eeb3c40e..b3f9a166 100644 --- a/bauh/view/resources/locale/pt +++ b/bauh/view/resources/locale/pt @@ -193,4 +193,6 @@ screenshots,download.running=baixando imagem screenshots.download.no_content=Sem conteúdo para exibir screenshots.download.no_response=Imagem não encontrada continue=continuar -stable=estável \ No newline at end of file +stable=estável +close=fechar +publisher.verified=verificado \ No newline at end of file