libept  0.5.25
debtags.h
Go to the documentation of this file.
1 // -*- mode: c++; tab-width: 4; indent-tabs-mode: t -*-
2 /* @file
3  * @author Enrico Zini (enrico) <enrico@enricozini.org>
4  */
5 
6 /*
7  * libpkg Debtags data provider
8  *
9  * Copyright (C) 2003-2007 Enrico Zini <enrico@debian.org>
10  *
11  * This program is free software; you can redistribute it and/or modify
12  * it under the terms of the GNU General Public License as published by
13  * the Free Software Foundation; either version 2 of the License, or
14  * (at your option) any later version.
15  *
16  * This program is distributed in the hope that it will be useful,
17  * but WITHOUT ANY WARRANTY; without even the implied warranty of
18  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19  * GNU General Public License for more details.
20  *
21  * You should have received a copy of the GNU General Public License
22  * along with this program; if not, write to the Free Software
23  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
24  */
25 
26 #ifndef EPT_DEBTAGS_DEBTAGS_H
27 #define EPT_DEBTAGS_DEBTAGS_H
28 
29 #include <ept/debtags/tag.h>
30 #include <ept/debtags/vocabulary.h>
32 
33 #include <tagcoll/coll/base.h>
34 #include <tagcoll/coll/intdiskindex.h>
35 #include <tagcoll/coll/patched.h>
36 
37 namespace ept {
38 namespace debtags {
39 class Debtags;
40 }
41 }
42 
43 namespace tagcoll {
44 template< typename _, typename _1 > class PatchList;
45 
46 namespace coll {
47 
48 template<>
49 struct coll_traits< ept::debtags::Debtags >
50 {
51  typedef std::string item_type;
53  typedef std::set< ept::debtags::Tag > tagset_type;
54  typedef std::set< std::string > itemset_type;
55 };
56 
57 }
58 }
59 
60 namespace ept {
61 namespace debtags {
62 
75 class Debtags : public tagcoll::coll::Collection<Debtags>
76 {
77 protected:
78  // Master mmap index container
79  tagcoll::diskindex::MasterMMap mastermmap;
80 
81  // Debtags database
82  tagcoll::coll::IntDiskIndex m_rocoll;
83  tagcoll::coll::Patched< tagcoll::coll::IntDiskIndex > m_coll;
84 
85  // Package name to ID mapping
87 
88  // Tag vocabulary
90 
91  // User rc directory to store patches
92  std::string rcdir;
93 
94  // Last modification timestamp of the index
95  time_t m_timestamp;
96 
97  std::string packageByID(int id) const
98  {
99  return m_pkgid.byID(id);
100  }
101 
102  template<typename IDS>
103  std::set<std::string> packagesById(const IDS& ids) const
104  {
105  std::set<std::string> pkgs;
106  for (typename IDS::const_iterator i = ids.begin();
107  i != ids.end(); ++i)
108  pkgs.insert(packageByID(*i));
109  return pkgs;
110  }
111 
112  int idByPackage(const std::string& pkg) const
113  {
114  return m_pkgid.byName(pkg);
115  }
116 
117  template<typename PKGS>
118  std::set<int> idsByPackages(const PKGS& pkgs) const
119  {
120  std::set<int> ids;
121  for (typename PKGS::const_iterator i = pkgs.begin();
122  i != pkgs.end(); ++i)
123  ids.insert(idByPackage(*i));
124  return ids;
125  }
126 
127 public:
128  typedef tagcoll::coll::Patched< tagcoll::coll::IntDiskIndex > coll_type;
129  typedef std::pair< std::string, std::set<Tag> > value_type;
130 
132  {
133  const Debtags& coll;
134  Debtags::coll_type::const_iterator ci;
135  mutable const Debtags::value_type* cached_val;
136 
137  protected:
138  const_iterator(const Debtags& coll,
139  const Debtags::coll_type::const_iterator& ci)
140  : coll(coll), ci(ci), cached_val(0) {}
141 
142  public:
144  {
145  if (cached_val)
146  delete cached_val;
147  }
149  {
150  if (cached_val)
151  return *cached_val;
152 
153  return make_pair(coll.packageByID(ci->first), coll.vocabulary().tagsByID(ci->second));
154  }
156  {
157  if (cached_val)
158  return cached_val;
159  return cached_val = new Debtags::value_type(*(*this));
160  }
162  {
163  ++ci;
164  if (cached_val)
165  {
166  delete cached_val;
167  cached_val = 0;
168  }
169  return *this;
170  }
171  bool operator==(const const_iterator& iter) const
172  {
173  return ci == iter.ci;
174  }
175  bool operator!=(const const_iterator& iter) const
176  {
177  return ci != iter.ci;
178  }
179 
180  friend class Debtags;
181  };
182  const_iterator begin() const { return const_iterator(*this, m_coll.begin()); }
183  const_iterator end() const { return const_iterator(*this, m_coll.end()); }
184 
193  Debtags(bool editable = false);
194  ~Debtags() {}
195 
197  time_t timestamp() const { return m_timestamp; }
198 
200  bool hasData() const { return m_timestamp != 0; }
201 
202  coll_type& tagdb() { return m_coll; }
203  const coll_type& tagdb() const { return m_coll; }
205 
206 #if 0
207  template<typename ITEMS, typename TAGS>
208  void insert(const ITEMS& items, const TAGS& tags)
209  {
210  for (typename ITEMS::const_iterator i = items.begin();
211  i != items.end(); ++i)
212  m_changes.addPatch(Patch(*i, tags, TagSet()));
213  }
214 
215  template<typename ITEMS>
216  void insert(const ITEMS& items, const wibble::Empty<Tag>& tags)
217  {
218  // Nothing to do in this case
219  }
220 
224  const Patches& changes() const { return m_changes; }
225 
229  void resetChanges() { m_changes.clear(); }
230 
234  void setChanges(const Patches& changes);
235 
239  void addChanges(const Patches& changes);
240 #endif
241 
242  bool hasTag(const Tag& tag) const { return m_coll.hasTag(tag.id()); }
243 
244  std::set<Tag> getTagsOfItem(const std::string& item) const
245  {
246  int id = idByPackage(item);
247  if (id == -1) return std::set<Tag>();
248  return vocabulary().tagsByID(m_coll.getTagsOfItem(id));
249  }
250 
251  template<typename ITEMS>
252  std::set<Tag> getTagsOfItems(const ITEMS& items) const
253  {
254  return vocabulary().tagsByID(m_coll.getTagsOfItems(idsByPackages(items)));
255  }
256 
257  std::set<std::string> getItemsHavingTag(const Tag& tag) const
258  {
259  return packagesById(m_coll.getItemsHavingTag(tag.id()));
260  }
261  template<typename TAGS>
262  std::set<std::string> getItemsHavingTags(const TAGS& tags) const
263  {
264  std::set<int> itags;
265  for (typename TAGS::const_iterator i = tags.begin();
266  i != tags.end(); ++i)
267  itags.insert(i->id());
268  return packagesById(m_coll.getItemsHavingTags(itags));
269  }
270 
271 #if 0
272  ItemSet getTaggedItems() const;
273 #endif
274  std::set<Tag> getAllTags() const
275  {
276  return vocabulary().tagsByID(m_coll.getAllTags());
277  }
278 
280  Vocabulary& vocabulary() { return m_voc; }
282  const Vocabulary& vocabulary() const { return m_voc; }
283 
289  PkgId& pkgid() { return m_pkgid; }
295  const PkgId& pkgid() const { return m_pkgid; }
296 
297  int getCardinality(const Tag& tag) const
298  {
299  return m_coll.getCardinality(tag.id());
300  }
301 
303  {
304  using namespace tagcoll;
305  PatchList<int, int> intp;
306  for (PatchList<std::string, Tag>::const_iterator i = change.begin();
307  i != change.end(); ++i)
308  {
309  Patch<int, int> p(idByPackage(i->first));
310  for (std::set<Tag>::const_iterator j = i->second.added.begin();
311  j != i->second.added.end(); ++j)
312  p.add(j->id());
313  for (std::set<Tag>::const_iterator j = i->second.removed.begin();
314  j != i->second.removed.end(); ++j)
315  p.remove(j->id());
316  intp.addPatch(p);
317  }
318  m_coll.applyChange(intp);
319  }
320 
321 #if 0
322  template<typename OUT>
323  void output(OUT out) const
324  {
325  for (const_iterator i = begin(); i != end(); ++i)
326  {
327  *out = *i;
328  ++out;
329  }
330  }
331 #endif
332 
333 
334 
339  //static bool hasTagDatabase();
340 
341 
346  void savePatch();
347 
353 
359 
364  void sendPatch();
365 
370 
375 
376 
382  template<typename OUT>
383  void outputSystem(const OUT& cons);
384 
390  template<typename OUT>
391  void outputSystem(const std::string& filename, const OUT& out);
392 
399  template<typename OUT>
400  void outputPatched(const OUT& cons);
401 
408  template<typename OUT>
409  void outputPatched(const std::string& filename, const OUT& out);
410 };
411 
412 
413 }
414 }
415 
416 // vim:set ts=4 sw=4:
417 #endif
Debtags facets and tags.
int byName(const std::string &name) const
Get the ID of a package given its name.
Definition: pkgid.cc:40
void outputSystem(const OUT &cons)
Output the current Debian tags database to a consumer of <std::string, Tag>
Definition: debtags.cc:232
std::string item_type
Definition: debtags.h:51
int id() const
Return the ID of this tag.
Definition: tag.h:242
bool hasTag(const Tag &tag) const
Definition: debtags.h:242
ept::debtags::Tag tag_type
Definition: debtags.h:52
std::set< Tag > getAllTags() const
Definition: debtags.h:274
const Debtags::value_type operator*() const
Definition: debtags.h:148
Vocabulary & vocabulary()
Access the vocabulary in use.
Definition: debtags.h:280
std::string packageByID(int id) const
Definition: debtags.h:97
tagcoll::coll::Patched< tagcoll::coll::IntDiskIndex > coll_type
Definition: debtags.h:128
std::set< std::string > getItemsHavingTags(const TAGS &tags) const
Definition: debtags.h:262
std::set< std::string > packagesById(const IDS &ids) const
Definition: debtags.h:103
int getCardinality(const Tag &tag) const
Definition: debtags.h:297
bool operator==(const const_iterator &iter) const
Definition: debtags.h:171
std::pair< std::string, std::set< Tag > > value_type
Definition: debtags.h:129
Vocabulary m_voc
Definition: debtags.h:89
std::set< ept::debtags::Tag > tagset_type
Definition: debtags.h:53
const Vocabulary & vocabulary() const
Access the vocabulary in use.
Definition: debtags.h:282
bool operator!=(const const_iterator &iter) const
Definition: debtags.h:175
Access the on-disk Debtags tag database.
Definition: debtags.h:75
time_t m_timestamp
Definition: debtags.h:95
Representation of a tag.
Definition: tag.h:163
~Debtags()
Definition: debtags.h:194
std::string rcdir
Definition: debtags.h:92
void outputPatched(const OUT &cons)
Output the current Debian tags database, patched with local patch, to a Consumer of <std::string...
Definition: debtags.cc:238
tagcoll::PatchList< std::string, Tag > changes() const
Definition: debtags.cc:88
std::set< std::string > itemset_type
Definition: debtags.h:54
std::string byID(int id) const
Get a package name given its ID.
Definition: pkgid.h:68
bool hasData() const
Return true if this data source has data, false if it's empty.
Definition: debtags.h:200
void sendPatch()
Send to the central archive a patch that can be used to turn the system database into the collection ...
Definition: debtags.cc:177
const_iterator begin() const
Definition: debtags.h:182
void applyChange(const tagcoll::PatchList< std::string, Tag > &change)
Definition: debtags.h:302
int idByPackage(const std::string &pkg) const
Definition: debtags.h:112
const PkgId & pkgid() const
Access the PkgId in use.
Definition: debtags.h:295
Maps Packages to IDs and vice-versa.
Definition: pkgid.h:40
const coll_type & tagdb() const
Definition: debtags.h:203
Definition: vocabulary.h:37
const_iterator end() const
Definition: debtags.h:183
tagcoll::coll::IntDiskIndex m_rocoll
Definition: debtags.h:82
tagcoll::diskindex::MasterMMap mastermmap
Definition: debtags.h:79
PkgId m_pkgid
Definition: debtags.h:86
const_iterator & operator++()
Definition: debtags.h:161
void savePatch()
Check if the tag database has been created (i.e.
Definition: debtags.cc:137
std::set< Tag > getTagsOfItem(const std::string &item) const
Definition: debtags.h:244
~const_iterator()
Definition: debtags.h:143
std::set< std::string > getItemsHavingTag(const Tag &tag) const
Definition: debtags.h:257
std::set< Tag > tagsByID(const IDS &ids) const
Definition: vocabulary.h:181
std::set< int > idsByPackages(const PKGS &pkgs) const
Definition: debtags.h:118
const Debtags::value_type * operator->() const
Definition: debtags.h:155
Definition: debtags.h:131
Debtags(bool editable=false)
Create a new accessor for the on-disk Debtags database.
Definition: debtags.cc:55
std::set< Tag > getTagsOfItems(const ITEMS &items) const
Definition: debtags.h:252
coll_type & tagdb()
Definition: debtags.h:202
Definition: debtags.h:44
time_t timestamp() const
Get the timestamp of when the index was last updated.
Definition: debtags.h:197
const_iterator(const Debtags &coll, const Debtags::coll_type::const_iterator &ci)
Definition: debtags.h:138
PkgId & pkgid()
Access the PkgId in use.
Definition: debtags.h:289
tagcoll::coll::Patched< tagcoll::coll::IntDiskIndex > m_coll
Definition: debtags.h:83