libyui-qt-pkg  2.45.28
YQPkgServiceList.cc
1 /**************************************************************************
2 Copyright (C) 2018 SUSE LLC
3 All Rights Reserved.
4 
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 2 of the License, or
8 (at your option) any later version.
9 
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
14 
15 You should have received a copy of the GNU General Public License along
16 with this program; if not, write to the Free Software Foundation, Inc.,
17 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18 
19 Textdomain "qt-pkg"
20 
21 /-*/
22 
23 #include <algorithm>
24 #include <set>
25 #include <string>
26 #include <QDateTime>
27 #include <QHeaderView>
28 #include <QString>
29 
30 #define YUILogComponent "qt-pkg"
31 #include "YUILog.h"
32 #include <zypp/PoolQuery.h>
33 #include <zypp/RepoManager.h>
34 #include <zypp/ServiceInfo.h>
35 
36 #include <QTreeWidget>
37 #include "YQPkgServiceList.h"
38 #include "YQPkgFilters.h"
39 #include "YQi18n.h"
40 #include "YQUI.h"
41 #include "utf8.h"
42 
43 using std::string;
44 using std::list;
45 using std::endl;
46 using std::set;
47 using std::vector;
48 
49 
51  : QY2ListView( parent )
52 {
53  yuiDebug() << "Creating service list" << endl;
54 
55  QStringList headers;
56 
57  // TRANSLATORS: Column header for the service list
58  headers << _("Name");
59  _nameCol = 0;
60 
61  setHeaderLabels( headers );
62  header()->setSectionResizeMode( _nameCol, QHeaderView::Stretch );
63 
64  setSelectionMode( QAbstractItemView::ExtendedSelection ); // allow multi-selection with Ctrl-mouse
65 
66  connect( this, SIGNAL( itemSelectionChanged() ),
67  this, SLOT ( filterIfVisible()) );
68  setIconSize(QSize(32,32));
69  fillList();
70  setSortingEnabled( true );
71  sortByColumn( nameCol(), Qt::AscendingOrder );
72  selectSomething();
73 
74  yuiDebug() << "Creating service list done" << endl;
75 }
76 
78 {
79  // NOP
80 }
81 
82 void
84 {
85  clear();
86  yuiDebug() << "Filling service list" << endl;
87 
88  std::set<std::string> added_services;
89  zypp::RepoManager repo_manager;
90 
91  std::for_each(ZyppRepositoriesBegin(), ZyppRepositoriesEnd(), [&](const zypp::Repository& repo) {
92  const std::string &service_name(repo.info().service());
93  if (!service_name.empty())
94  {
95  bool found = std::any_of(added_services.begin(), added_services.end(), [&](const std::string& name) {
96  return service_name == name;
97  });
98 
99  if (!found)
100  {
101  addService(service_name, repo_manager);
102  added_services.insert(service_name);
103  }
104  }
105  });
106 
107  yuiDebug() << "Service list filled" << endl;
108 }
109 
110 void
112 {
113  if ( isVisible() )
114  filter();
115 }
116 
117 void
119 {
120  emit filterStart();
121 
122  yuiMilestone() << "Collecting packages in selected services..." << endl;
123  QTime stopWatch;
124  stopWatch.start();
125 
126  //
127  // Collect all packages from repositories belonging to this service
128  //
129  QTreeWidgetItem * item;
130  QList<QTreeWidgetItem *> items = selectedItems();
131  QListIterator<QTreeWidgetItem *> it(items);
132 
133  while ( it.hasNext() )
134  {
135  item = it.next();
136  YQPkgServiceListItem * serviceItem = dynamic_cast<YQPkgServiceListItem *> (item);
137 
138  if ( serviceItem )
139  {
140  yuiMilestone() << "Selected service: " << serviceItem->zyppService() << endl;
141 
142  zypp::PoolQuery query;
143  std::for_each(ZyppRepositoriesBegin(), ZyppRepositoriesEnd(), [&](const zypp::Repository& repo) {
144  if (serviceItem->zyppService() == repo.info().service())
145  {
146  yuiMilestone() << "Adding repo filter: " << repo.info().alias() << endl;
147  query.addRepo( repo.info().alias() );
148  }
149  });
150  query.addKind(zypp::ResKind::package);
151 
152  std::for_each(query.selectableBegin(), query.selectableEnd(), [&](const zypp::ui::Selectable::Ptr &selectable) {
153  emit filterMatch( selectable, tryCastToZyppPkg( selectable->theObj() ) );
154  });
155  }
156  }
157 
158  yuiDebug() << "Packages sent to package list. Elapsed time: "
159  << stopWatch.elapsed() / 1000.0 << " sec"
160  << endl;
161 
162  emit filterFinished();
163 }
164 
165 void
166 YQPkgServiceList::addService( ZyppService service, const zypp::RepoManager &mgr )
167 {
168  new YQPkgServiceListItem( this, service, mgr );
169 }
170 
171 
174 {
175  QTreeWidgetItem * item = currentItem();
176  return dynamic_cast<YQPkgServiceListItem *> (item);
177 }
178 
180  ZyppService service, const zypp::RepoManager &mgr )
181  : QY2ListViewItem( parentList )
182  , _serviceList( parentList )
183  , _zyppService( service )
184 {
185 
186  zypp::ServiceInfo srvinfo = mgr.getService(service);
187  _zyppServiceName = srvinfo.name();
188  QString service_name(fromUTF8(_zyppServiceName));
189 
190  if ( nameCol() >= 0 && !service.empty() )
191  {
192  setText( nameCol(), service_name);
193  }
194 
195  QString infoToolTip("<p><b>" + service_name.toHtmlEscaped() + "</b></p>");
196 
197  // TRANSLATORS: Tooltip item, followed by service URL
198  infoToolTip += "<p><b>" + _("URL: ") + "</b>" + fromUTF8(srvinfo.url().asString()).toHtmlEscaped() + "</p>";
199 
200  ZyppProduct product = singleProduct( _zyppService );
201  if ( product )
202  {
203  // TRANSLATORS: Tooltip item, followed by product name
204  infoToolTip += ("<p><b>" + _("Product: ") + "</b>"
205  + fromUTF8(product->summary()).toHtmlEscaped() + "</p>");
206  }
207 
208  // TRANSLATORS: Tooltip item, followed by the list of repositories inluded in the libzypp service
209  infoToolTip += "<p><b>" + _("Repositories:") + "</b><ul>";
210  std::for_each(ZyppRepositoriesBegin(), ZyppRepositoriesEnd(), [&](const zypp::Repository& repo) {
211  if (service == repo.info().service())
212  infoToolTip += "<li>" + fromUTF8(repo.name()).toHtmlEscaped() + "</li>";
213  });
214  infoToolTip += "</ul></p>";
215 
216  setToolTip( nameCol(), infoToolTip);
217 
218  setIcon( 0, YQUI::ui()->loadIcon( "yast-update" ) );
219 }
220 
222 {
223  // NOP
224 }
225 
226 ZyppProduct
227 YQPkgServiceListItem::singleProduct( ZyppService zyppService )
228 {
229  return YQPkgFilters::singleProductFilter([&](const zypp::PoolItem& item) {
230  // filter the products from the requested service
231  return item.resolvable()->repoInfo().service() == zyppService;
232  });
233 }
234 
235 bool
236 YQPkgServiceListItem::operator< ( const QTreeWidgetItem & other ) const
237 {
238  const YQPkgServiceListItem * otherItem = dynamic_cast<const YQPkgServiceListItem *>(&other);
239 
240  // case insensitive compare
241  return QString::compare(fromUTF8(zyppServiceName()), fromUTF8(otherItem->zyppServiceName()), Qt::CaseInsensitive) < 0;
242 }
243 
void filterStart()
Emitted when the filtering starts.
void filter()
Filter according to the view&#39;s rules and current selection.
ZyppService zyppService() const
Returns the ZYPP service this item corresponds to (its alias)
virtual ~YQPkgServiceList()
Destructor.
std::string zyppServiceName() const
Returns the ZYPP service name this item corresponds to.
virtual ~YQPkgServiceListItem()
Destructor.
void filterIfVisible()
Same as filter(), but only if this widget is currently visible.
YQPkgServiceList(QWidget *parent)
Constructor.
void filterFinished()
Emitted when filtering is finished.
A widget to display a list of libzypp services.
static ZyppProduct singleProduct(ZyppService service)
Returns the product on a source if it has one single product or 0 if there are no or multiple product...
void fillList()
Fill the list.
static ZyppProduct singleProductFilter(std::function< bool(const zypp::PoolItem &item)> filter)
Returns the product if the filter finds a single product or null product if there are no or multiple ...
Definition: YQPkgFilters.cc:35
void addService(ZyppService service, const zypp::RepoManager &mgr)
Add a service to the list.
YQPkgServiceListItem * selection() const
Returns the currently selected item or 0 if there is none.
YQPkgServiceListItem(YQPkgServiceList *parentList, ZyppService service, const zypp::RepoManager &mgr)
Constructor.
void filterMatch(ZyppSel selectable, ZyppPkg pkg)
Emitted during filtering for each pkg that matches the filter and the candidate package comes from th...