summaryrefslogtreecommitdiff
path: root/ept/debtags
diff options
context:
space:
mode:
authorEnrico Zini <enrico@enricozini.org>2010-05-10 11:33:37 +0100
committerEnrico Zini <enrico@enricozini.org>2010-05-10 11:38:59 +0100
commit137b229b33189c173e383684808f4dea9fe1f235 (patch)
tree2d3ce76185b650204399d15aff2e6ca8adeba1ff /ept/debtags
parentf5c2f7507dfe4f8a5b7159073204dff2c87cb891 (diff)
downloadlibept-137b229b33189c173e383684808f4dea9fe1f235.tar.gz
Big debtags code simplification
no more indices to maintain, just read the text files no more int IDs and conversions to/from strings
Diffstat (limited to 'ept/debtags')
-rw-r--r--ept/debtags/debtags.cc95
-rw-r--r--ept/debtags/debtags.h242
-rw-r--r--ept/debtags/debtags.tcc30
-rw-r--r--ept/debtags/debtags.test.h63
-rw-r--r--ept/debtags/expression.cc51
-rw-r--r--ept/debtags/expression.h42
-rw-r--r--ept/debtags/expression.test.h10
-rw-r--r--ept/debtags/maint/debtagsindexer.cc265
-rw-r--r--ept/debtags/maint/debtagsindexer.h51
-rw-r--r--ept/debtags/maint/pkgid.cc66
-rw-r--r--ept/debtags/maint/pkgid.h91
-rw-r--r--ept/debtags/maint/pkgid.test.h75
-rw-r--r--ept/debtags/maint/serializer.h949
-rw-r--r--ept/debtags/maint/serializer.test.h133
-rw-r--r--ept/debtags/maint/sourcedir.cc3
-rw-r--r--ept/debtags/maint/sourcedir.h2
-rw-r--r--ept/debtags/maint/vocabularymerger.test.h144
-rw-r--r--ept/debtags/tag.cc138
-rw-r--r--ept/debtags/tag.h251
-rw-r--r--ept/debtags/tag.test.h107
-rw-r--r--ept/debtags/vocabulary.cc85
-rw-r--r--ept/debtags/vocabulary.h95
-rw-r--r--ept/debtags/vocabulary.test.h194
23 files changed, 306 insertions, 2876 deletions
diff --git a/ept/debtags/debtags.cc b/ept/debtags/debtags.cc
index 331c132..383bb02 100644
--- a/ept/debtags/debtags.cc
+++ b/ept/debtags/debtags.cc
@@ -25,9 +25,10 @@
#include <ept/debtags/debtags.h>
#include <ept/debtags/maint/path.h>
-#include <ept/debtags/maint/serializer.h>
-#include <ept/debtags/maint/debtagsindexer.h>
+#include <ept/debtags/maint/sourcedir.h>
+#include <tagcoll/patch.h>
+#include <tagcoll/coll/simple.h>
#include <tagcoll/input/stdio.h>
#include <tagcoll/TextFormat.h>
@@ -52,24 +53,17 @@ namespace ept {
namespace debtags {
Debtags::Debtags(bool editable)
- : m_coll(m_rocoll)
{
- std::string tagfname;
- std::string idxfname;
+ // Read and merge tag data
+ SourceDir mainSource(Path::debtagsSourceDir());
+ SourceDir userSource(Path::debtagsUserSourceDir());
- if (!DebtagsIndexer::obtainWorkingDebtags(vocabulary(), tagfname, idxfname))
- {
- m_timestamp = 0;
- return;
- } else {
- m_timestamp = Path::timestamp(idxfname);
-
- mastermmap.init(idxfname);
+ mainSource.readTags(inserter(*this));
+ userSource.readTags(inserter(*this));
- // Initialize the readonly index
- m_pkgid.init(mastermmap, 0);
- m_rocoll.init(mastermmap, 1, 2);
- }
+ time_t ts_main_src = mainSource.tagTimestamp();
+ time_t ts_user_src = userSource.tagTimestamp();
+ m_timestamp = ts_main_src > ts_user_src ? ts_main_src : ts_user_src;
// Initialize the patch collection layer
rcdir = Path::debtagsUserSourceDir();
@@ -78,29 +72,23 @@ Debtags::Debtags(bool editable)
if (Path::access(patchFile, F_OK) == 0)
{
input::Stdio in(patchFile);
- PatchList<int, int> patch;
- textformat::parsePatch(in, patchStringToInt(m_pkgid, vocabulary(), inserter(patch)));
- m_coll.setChanges(patch);
+ PatchList<string, string> patch;
+ textformat::parsePatch(in, inserter(patch));
+ applyChange(patch);
}
}
-tagcoll::PatchList<std::string, Tag> Debtags::changes() const
+tagcoll::PatchList<std::string, std::string> Debtags::changes() const
{
- tagcoll::PatchList<int, int> patches = m_coll.changes();
- tagcoll::PatchList<std::string, Tag> res;
-
- for (tagcoll::PatchList<int, int>::const_iterator i = patches.begin();
- i != patches.end(); ++i)
- {
- std::string pkg = packageByID(i->second.item);
- if (pkg.empty())
- continue;
-
- res.addPatch(tagcoll::Patch<std::string, Tag>(pkg,
- vocabulary().tagsByID(i->second.added),
- vocabulary().tagsByID(i->second.removed)));
- }
-
+ // Read original tag data
+ SourceDir mainSource(Path::debtagsSourceDir());
+ SourceDir userSource(Path::debtagsUserSourceDir());
+ coll::Simple<string, string> orig;
+ mainSource.readTags(inserter(orig));
+ userSource.readTags(inserter(orig));
+
+ tagcoll::PatchList<std::string, std::string> res;
+ res.addPatch(orig, *this);
return res;
}
@@ -136,7 +124,7 @@ bool Debtags::hasTagDatabase()
void Debtags::savePatch()
{
PatchList<std::string, std::string> spatch;
- m_coll.changes().output(patchIntToString(m_pkgid, vocabulary(), tagcoll::inserter(spatch)));
+ changes().output(tagcoll::inserter(spatch));
savePatch(spatch);
}
@@ -166,30 +154,16 @@ void Debtags::savePatch(const PatchList<std::string, std::string>& patch)
}
}
-void Debtags::savePatch(const PatchList<std::string, Tag>& patch)
-{
- PatchList<std::string, std::string> spatch;
- // patch.output(patchToString<C>(m_pkgs, m_pkgidx, m_tags, tagcoll::inserter(spatch)));
- savePatch(spatch);
-}
-
void Debtags::sendPatch()
{
PatchList<std::string, std::string> spatch;
- m_coll.changes().output(patchIntToString(m_pkgid, vocabulary(), tagcoll::inserter(spatch)));
+ changes().output(tagcoll::inserter(spatch));
if (!spatch.empty())
{
sendPatch(spatch);
}
}
-void Debtags::sendPatch(const PatchList<std::string, Tag>& patch)
-{
- PatchList<std::string, std::string> spatch;
- // patch.output(patchToString<C>(m_pkgs, m_pkgidx, m_tags, tagcoll::inserter(spatch)));
- sendPatch(spatch);
-}
-
void Debtags::sendPatch(const PatchList<std::string, std::string>& patch)
{
static const char* cmd = "/usr/sbin/sendmail -t";
@@ -226,24 +200,13 @@ void Debtags::sendPatch(const PatchList<std::string, std::string>& patch)
}
}
-
-template<typename OUT>
-void Debtags::outputSystem(const OUT& cons)
-{
- m_rocoll.output(intToPkg(m_pkgid, vocabulary(), cons));
-}
-
-template<typename OUT>
-void Debtags::outputPatched(const OUT& cons)
-{
- m_coll.output(intToPkg(m_pkgid, vocabulary(), cons));
-}
-
}
}
+#include <ept/debtags/maint/sourcedir.tcc>
#include <tagcoll/patch.tcc>
-#include <tagcoll/coll/patched.tcc>
+#include <tagcoll/coll/simple.tcc>
+#include <tagcoll/coll/fast.tcc>
#include <tagcoll/TextFormat.tcc>
//#include <tagcoll/stream/filters.tcc>
diff --git a/ept/debtags/debtags.h b/ept/debtags/debtags.h
index c46786e..619cb15 100644
--- a/ept/debtags/debtags.h
+++ b/ept/debtags/debtags.h
@@ -26,13 +26,10 @@
#ifndef EPT_DEBTAGS_DEBTAGS_H
#define EPT_DEBTAGS_DEBTAGS_H
-#include <ept/debtags/tag.h>
#include <ept/debtags/vocabulary.h>
-#include <ept/debtags/maint/pkgid.h>
#include <tagcoll/coll/base.h>
-#include <tagcoll/coll/intdiskindex.h>
-#include <tagcoll/coll/patched.h>
+#include <tagcoll/coll/fast.h>
namespace ept {
namespace debtags {
@@ -40,23 +37,6 @@ class Debtags;
}
}
-namespace tagcoll {
-template< typename _, typename _1 > class PatchList;
-
-namespace coll {
-
-template<>
-struct coll_traits< ept::debtags::Debtags >
-{
- typedef std::string item_type;
- typedef ept::debtags::Tag tag_type;
- typedef std::set< ept::debtags::Tag > tagset_type;
- typedef std::set< std::string > itemset_type;
-};
-
-}
-}
-
namespace ept {
namespace debtags {
@@ -65,26 +45,16 @@ namespace debtags {
*
* The database is normally found in /var/lib/debtags.
*
- * Tags and Facets are returned as Tag and Facet objects. The objects follow
+ * Tags and Facets are returned as std::strings. The objects follow
* the flyweight pattern and access the data contained in the Vocabulary
* instantiated inside Debtags.
*
* It is possible to get a reference to the Vocabulary object using the
* vocabulary() method.
*/
-class Debtags : public tagcoll::coll::Collection<Debtags>
+class Debtags : public tagcoll::coll::Fast<std::string, std::string>
{
protected:
- // Master mmap index container
- tagcoll::diskindex::MasterMMap mastermmap;
-
- // Debtags database
- tagcoll::coll::IntDiskIndex m_rocoll;
- tagcoll::coll::Patched< tagcoll::coll::IntDiskIndex > m_coll;
-
- // Package name to ID mapping
- PkgId m_pkgid;
-
// Tag vocabulary
Vocabulary m_voc;
@@ -94,93 +64,9 @@ protected:
// Last modification timestamp of the index
time_t m_timestamp;
- std::string packageByID(int id) const
- {
- return m_pkgid.byID(id);
- }
-
- template<typename IDS>
- std::set<std::string> packagesById(const IDS& ids) const
- {
- std::set<std::string> pkgs;
- for (typename IDS::const_iterator i = ids.begin();
- i != ids.end(); ++i)
- pkgs.insert(packageByID(*i));
- return pkgs;
- }
-
- int idByPackage(const std::string& pkg) const
- {
- return m_pkgid.byName(pkg);
- }
-
- template<typename PKGS>
- std::set<int> idsByPackages(const PKGS& pkgs) const
- {
- std::set<int> ids;
- for (typename PKGS::const_iterator i = pkgs.begin();
- i != pkgs.end(); ++i)
- ids.insert(idByPackage(*i));
- return ids;
- }
-
public:
- typedef tagcoll::coll::Patched< tagcoll::coll::IntDiskIndex > coll_type;
- typedef std::pair< std::string, std::set<Tag> > value_type;
-
- class const_iterator
- {
- const Debtags& coll;
- Debtags::coll_type::const_iterator ci;
- mutable const Debtags::value_type* cached_val;
-
- protected:
- const_iterator(const Debtags& coll,
- const Debtags::coll_type::const_iterator& ci)
- : coll(coll), ci(ci), cached_val(0) {}
-
- public:
- ~const_iterator()
- {
- if (cached_val)
- delete cached_val;
- }
- const Debtags::value_type operator*() const
- {
- if (cached_val)
- return *cached_val;
-
- return make_pair(coll.packageByID(ci->first), coll.vocabulary().tagsByID(ci->second));
- }
- const Debtags::value_type* operator->() const
- {
- if (cached_val)
- return cached_val;
- return cached_val = new Debtags::value_type(*(*this));
- }
- const_iterator& operator++()
- {
- ++ci;
- if (cached_val)
- {
- delete cached_val;
- cached_val = 0;
- }
- return *this;
- }
- bool operator==(const const_iterator& iter) const
- {
- return ci == iter.ci;
- }
- bool operator!=(const const_iterator& iter) const
- {
- return ci != iter.ci;
- }
-
- friend class Debtags;
- };
- const_iterator begin() const { return const_iterator(*this, m_coll.begin()); }
- const_iterator end() const { return const_iterator(*this, m_coll.end()); }
+ typedef tagcoll::coll::Fast<std::string, std::string> coll_type;
+ typedef std::pair< std::string, std::set<std::string> > value_type;
/**
* Create a new accessor for the on-disk Debtags database
@@ -190,8 +76,8 @@ public:
* is true, then the local state directory will be created when the object
* is instantiated.
*/
- Debtags(bool editable = false);
- ~Debtags() {}
+ Debtags(bool editable = false);
+ ~Debtags() {}
/// Get the timestamp of when the index was last updated
time_t timestamp() const { return m_timestamp; }
@@ -199,25 +85,11 @@ public:
/// Return true if this data source has data, false if it's empty
bool hasData() const { return m_timestamp != 0; }
- coll_type& tagdb() { return m_coll; }
- const coll_type& tagdb() const { return m_coll; }
- tagcoll::PatchList<std::string, Tag> changes() const;
+ coll_type& tagdb() { return *this; }
+ const coll_type& tagdb() const { return *this; }
+ tagcoll::PatchList<std::string, std::string> changes() const;
#if 0
- template<typename ITEMS, typename TAGS>
- void insert(const ITEMS& items, const TAGS& tags)
- {
- for (typename ITEMS::const_iterator i = items.begin();
- i != items.end(); ++i)
- m_changes.addPatch(Patch(*i, tags, TagSet()));
- }
-
- template<typename ITEMS>
- void insert(const ITEMS& items, const wibble::Empty<Tag>& tags)
- {
- // Nothing to do in this case
- }
-
/**
* Get the changes that have been applied to this collection
*/
@@ -239,84 +111,14 @@ public:
void addChanges(const Patches& changes);
#endif
- bool hasTag(const Tag& tag) const { return m_coll.hasTag(tag.id()); }
-
- std::set<Tag> getTagsOfItem(const std::string& item) const
- {
- int id = idByPackage(item);
- if (id == -1) return std::set<Tag>();
- return vocabulary().tagsByID(m_coll.getTagsOfItem(id));
- }
-
- template<typename ITEMS>
- std::set<Tag> getTagsOfItems(const ITEMS& items) const
- {
- return vocabulary().tagsByID(m_coll.getTagsOfItems(idsByPackages(items)));
- }
-
- std::set<std::string> getItemsHavingTag(const Tag& tag) const
- {
- return packagesById(m_coll.getItemsHavingTag(tag.id()));
- }
- template<typename TAGS>
- std::set<std::string> getItemsHavingTags(const TAGS& tags) const
- {
- std::set<int> itags;
- for (typename TAGS::const_iterator i = tags.begin();
- i != tags.end(); ++i)
- itags.insert(i->id());
- return packagesById(m_coll.getItemsHavingTags(itags));
- }
-
#if 0
ItemSet getTaggedItems() const;
#endif
- std::set<Tag> getAllTags() const
- {
- return vocabulary().tagsByID(m_coll.getAllTags());
- }
/// Access the vocabulary in use
- Vocabulary& vocabulary() { return m_voc; }
+ Vocabulary& vocabulary() { return m_voc; }
/// Access the vocabulary in use
- const Vocabulary& vocabulary() const { return m_voc; }
-
- /**
- * Access the PkgId in use.
- *
- * \note Future implementations may not rely on a PkgId
- */
- PkgId& pkgid() { return m_pkgid; }
- /**
- * Access the PkgId in use.
- *
- * \note Future implementations may not rely on a PkgId
- */
- const PkgId& pkgid() const { return m_pkgid; }
-
- int getCardinality(const Tag& tag) const
- {
- return m_coll.getCardinality(tag.id());
- }
-
- void applyChange(const tagcoll::PatchList<std::string, Tag>& change)
- {
- using namespace tagcoll;
- PatchList<int, int> intp;
- for (PatchList<std::string, Tag>::const_iterator i = change.begin();
- i != change.end(); ++i)
- {
- Patch<int, int> p(idByPackage(i->first));
- for (std::set<Tag>::const_iterator j = i->second.added.begin();
- j != i->second.added.end(); ++j)
- p.add(j->id());
- for (std::set<Tag>::const_iterator j = i->second.removed.begin();
- j != i->second.removed.end(); ++j)
- p.remove(j->id());
- intp.addPatch(p);
- }
- m_coll.applyChange(intp);
- }
+ const Vocabulary& vocabulary() const { return m_voc; }
#if 0
template<typename OUT>
@@ -352,12 +154,6 @@ public:
void savePatch(const tagcoll::PatchList<std::string, std::string>& patch);
/**
- * Save in the state storage directory a patch to turn the system database
- * into the collection given
- */
- void savePatch(const tagcoll::PatchList<std::string, Tag>& patch);
-
- /**
* Send to the central archive a patch that can be used to turn
* the system database into the collection given
*/
@@ -369,13 +165,7 @@ public:
void sendPatch(const tagcoll::PatchList<std::string, std::string>& patch);
/**
- * Send the given patch to the central archive
- */
- void sendPatch(const tagcoll::PatchList<std::string, Tag>& patch);
-
-
- /**
- * Output the current Debian tags database to a consumer of <std::string, Tag>
+ * Output the current Debian tags database to a consumer of <std::string, std::string>
*
* \note The collection is sent to 'cons' without merging repeated items
*/
@@ -383,7 +173,7 @@ public:
void outputSystem(const OUT& cons);
/**
- * Output the given tag file to a consumer of <std::string, Tag>
+ * Output the given tag file to a consumer of <std::string, std::string>
*
* \note The collection is sent to 'cons' without merging repeated items
*/
@@ -392,7 +182,7 @@ public:
/**
* Output the current Debian tags database, patched with local patch,
- * to a Consumer of <std::string, Tag>
+ * to a Consumer of <std::string, std::string>
*
* \note The collection is sent to 'cons' without merging repeated items
*/
@@ -401,7 +191,7 @@ public:
/**
* Output the given tag file, patched with local patch,
- * to a Consumer of <std::string, Tag>
+ * to a Consumer of <std::string, std::string>
*
* \note The collection is sent to 'cons' without merging repeated items
*/
diff --git a/ept/debtags/debtags.tcc b/ept/debtags/debtags.tcc
index 0963d09..48f80fb 100644
--- a/ept/debtags/debtags.tcc
+++ b/ept/debtags/debtags.tcc
@@ -27,8 +27,10 @@
#define EPT_DEBTAGS_DEBTAGS_TCC
#include <ept/debtags/debtags.h>
-#include <ept/debtags/maint/serializer.h>
+#include <ept/debtags/maint/path.h>
+#include <ept/debtags/maint/sourcedir.h>
+#include <tagcoll/coll/simple.h>
#include <tagcoll/input/stdio.h>
#include <tagcoll/stream/patcher.h>
#include <tagcoll/TextFormat.h>
@@ -39,50 +41,60 @@ namespace debtags {
template<typename OUT>
void Debtags::outputSystem(const OUT& cons)
{
- m_rocoll.output(intToPkg(m_pkgid, vocabulary(), cons));
+ // Read and merge tag data
+ SourceDir mainSource(Path::debtagsSourceDir());
+ SourceDir userSource(Path::debtagsUserSourceDir());
+ tagcoll::coll::Simple<string, string> merged;
+ mainSource.readTags(inserter(merged));
+ userSource.readTags(inserter(merged));
+ merged.output(cons);
}
+
template<typename OUT>
void Debtags::outputSystem(const std::string& filename, const OUT& out)
{
if (filename == "-")
{
tagcoll::input::Stdio input(stdin, "<stdin>");
- tagcoll::textformat::parse(input, ept::debtags::stringToPkg(m_pkgid, m_voc, out));
+ tagcoll::textformat::parse(input, out);
}
else
{
tagcoll::input::Stdio input(filename);
- tagcoll::textformat::parse(input, ept::debtags::stringToPkg(m_pkgid, m_voc, out));
+ tagcoll::textformat::parse(input, out);
}
}
template<typename OUT>
void Debtags::outputPatched(const OUT& cons)
{
- m_coll.output(intToPkg(m_pkgid, vocabulary(), cons));
+ output(cons);
}
template<typename OUT>
void Debtags::outputPatched(const std::string& filename, const OUT& out)
{
- const tagcoll::PatchList<string, Tag>& patch = m_coll.changes();
+ const tagcoll::PatchList<string, string>& patch = changes();
if (filename == "-")
{
tagcoll::input::Stdio input(stdin, "<stdin>");
- tagcoll::textformat::parse(input, ept::debtags::stringToPkg(m_pkgid, m_voc, patcher(patch, out)));
+ tagcoll::textformat::parse(input, patcher(patch, out));
}
else
{
tagcoll::input::Stdio input(filename);
- tagcoll::textformat::parse(input, ept::debtags::stringToPkg(m_pkgid, m_voc, patcher(patch, out)));
+ tagcoll::textformat::parse(input, patcher(patch, out));
}
}
}
}
-#include <tagcoll/coll/patched.tcc>
+#include <ept/debtags/maint/sourcedir.tcc>
+#include <tagcoll/coll/simple.tcc>
+#include <tagcoll/coll/fast.tcc>
+#include <tagcoll/patch.tcc>
#endif
diff --git a/ept/debtags/debtags.test.h b/ept/debtags/debtags.test.h
index f360cc6..9f99cd2 100644
--- a/ept/debtags/debtags.test.h
+++ b/ept/debtags/debtags.test.h
@@ -29,6 +29,7 @@
#include <tagcoll/coll/simple.h>
#include <tagcoll/stream/sink.h>
+#include <tagcoll/patch.h>
#include <wibble/operators.h>
@@ -73,8 +74,8 @@ struct TestDebtags : DebtagsTestEnvironment
Test _2()
{
- string p("debtags");
- std::set<Tag> tags = debtags.getTagsOfItem(p);
+ string p("debtags");
+ std::set<std::string> tags = debtags.getTagsOfItem(p);
assert( !tags.empty() );
#if 0
@@ -87,26 +88,26 @@ struct TestDebtags : DebtagsTestEnvironment
#endif
assert_eq( tags.size(), 8u );
- assert( voc().tagByName( "devel::buildtools" ) <= tags );
- assert( voc().tagByName( "implemented-in::c++" ) <= tags );
- assert( voc().tagByName( "interface::commandline" ) <= tags );
- assert( voc().tagByName( "role::program" ) <= tags );
- assert( voc().tagByName( "scope::application" ) <= tags );
- assert( voc().tagByName( "suite::debian" ) <= tags );
- assert( voc().tagByName( "use::searching" ) <= tags );
- assert( voc().tagByName( "works-with::software:package" ) <= tags );
+ assert( tags.find("devel::buildtools") != tags.end() );
+ assert( tags.find("implemented-in::c++") != tags.end() );
+ assert( tags.find("interface::commandline") != tags.end() );
+ assert( tags.find("role::program") != tags.end() );
+ assert( tags.find("scope::application") != tags.end() );
+ assert( tags.find("suite::debian") != tags.end() );
+ assert( tags.find("use::searching") != tags.end() );
+ assert( tags.find("works-with::software:package") != tags.end() );
}
Test _3()
{
using namespace std;
- /* Get the 'debtags' package */
- string p("debtags");
+ /* Get the 'debtags' package */
+ string p("debtags");
- /* Get its tags */
- std::set<Tag> tags = debtags.getTagsOfItem(p);
- assert(!tags.empty());
+ /* Get its tags */
+ std::set<std::string> tags = debtags.getTagsOfItem(p);
+ assert(!tags.empty());
/*
cerr << "Intersection size: " << endl;
@@ -162,15 +163,14 @@ struct TestDebtags : DebtagsTestEnvironment
assert( p <= packages );
/* Get one of the tags of 'debtags' */
- Tag tag = *tags.begin();
- assert(tag);
+ std::string tag = *tags.begin();
/* Get its items */
{
/* Need this workaround until I figure out how to tell the new GCC
* that TagDB is a TDBReadonlyDiskIndex and should behave as such
*/
- std::set<Tag> ts;
+ std::set<std::string> ts;
ts.insert(tag);
packages = debtags.getItemsHavingTags(ts);
}
@@ -190,20 +190,20 @@ struct TestDebtags : DebtagsTestEnvironment
string p("debtags");
/* Get its tags */
- std::set<Tag> tags = debtags.getTagsOfItem(p);
+ std::set<std::string> tags = debtags.getTagsOfItem(p);
assert(!tags.empty());
// Ensure that it's not tagged with gameplaying
- Tag t = voc().tagByName("use::gameplaying");
- assert(! (t <= tags) );
+ std::string t = "use::gameplaying";
+ assert(tags.find(t) == tags.end());
// Add the gameplaying tag
- PatchList<string, Tag> change;
- change.addPatch(Patch<string, Tag>(p, wibble::singleton(t), wibble::Empty<Tag>()));
+ PatchList<string, string> change;
+ change.addPatch(Patch<string, string>(p, wibble::singleton(t), wibble::Empty<string>()));
debtags.applyChange(change);
// See that the patch is non empty
- PatchList<string, Tag> tmp = debtags.changes();
+ PatchList<string, string> tmp = debtags.changes();
assert(tmp.size() > 0);
assert_eq(tmp.size(), 1u);
@@ -211,8 +211,8 @@ struct TestDebtags : DebtagsTestEnvironment
tags = debtags.getTagsOfItem(p);
assert(!tags.empty());
- t = voc().tagByName("use::gameplaying");
- assert( t <= tags );
+ t = "use::gameplaying";
+ assert(tags.find(t) != tags.end());
// Save the patch
debtags.savePatch();
@@ -252,18 +252,19 @@ struct TestDebtags : DebtagsTestEnvironment
assert_eq(empty.timestamp(), 0);
assert(!empty.hasData());
- tagcoll::PatchList<std::string, Tag> patches = empty.changes();
+ tagcoll::PatchList<std::string, std::string> patches = empty.changes();
assert(patches.empty());
- set<Tag> res = empty.getTagsOfItem("apt");
- assert(res.empty());
- res = empty.getTagsOfItems(wibble::singleton(string("apt")));
+ set<std::string> res = empty.getTagsOfItem("apt");
assert(res.empty());
+ // TODO: currently does not compile because of a bug in tagcoll
+ //res = empty.getTagsOfItems(wibble::singleton(string("apt")));
+ //assert(res.empty());
res = empty.getAllTags();
assert(res.empty());
- tagcoll::coll::Simple<string, Tag> coll;
+ tagcoll::coll::Simple<string, std::string> coll;
empty.outputSystem(tagcoll::coll::inserter(coll));
assert_eq(coll.itemCount(), 0u);
diff --git a/ept/debtags/expression.cc b/ept/debtags/expression.cc
deleted file mode 100644
index 4a7967c..0000000
--- a/ept/debtags/expression.cc
+++ /dev/null
@@ -1,51 +0,0 @@
-/** \file
- * Match tag expressions against sets of Debtags Tags
- */
-
-/*
- * Copyright (C) 2003,2004,2005,2006,2007 Enrico Zini <enrico@debian.org>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- */
-
-#include <ept/debtags/expression.h>
-#include <string>
-
-namespace tagcoll
-{
-
-template<>
-bool Expression::operator()(const std::set<ept::debtags::Tag>& tags) const
-{
- std::set<std::string> names;
- for (std::set<ept::debtags::Tag>::const_iterator i = tags.begin();
- i != tags.end(); ++i)
- names.insert(i->fullname());
- return this->m_impl->eval(names);
-}
-
-template<>
-bool Expression::operator()(const std::set<ept::debtags::Facet>& tags) const
-{
- std::set<std::string> names;
- for (std::set<ept::debtags::Facet>::const_iterator i = tags.begin();
- i != tags.end(); ++i)
- names.insert(i->name());
- return this->m_impl->eval(names);
-}
-
-};
-
-// vim:set ts=4 sw=4:
diff --git a/ept/debtags/expression.h b/ept/debtags/expression.h
deleted file mode 100644
index 45eb306..0000000
--- a/ept/debtags/expression.h
+++ /dev/null
@@ -1,42 +0,0 @@
-#ifndef EPT_DEBTAGS_EXPRESSION_H
-#define EPT_DEBTAGS_EXPRESSION_H
-
-/** \file
- * Match tag expressions against sets of Debtags Tags
- */
-
-/*
- * Copyright (C) 2003,2004,2005,2006,2007 Enrico Zini <enrico@debian.org>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- */
-
-#include <ept/debtags/tag.h>
-#include <tagcoll/expression.h>
-#include <set>
-
-namespace tagcoll
-{
-
-template<>
-bool Expression::operator()(const std::set<ept::debtags::Tag>& tags) const;
-
-template<>
-inline bool Expression::operator()(const std::set<ept::debtags::Facet>& tags) const;
-
-};
-
-#endif
-// vim:set ts=4 sw=4:
diff --git a/ept/debtags/expression.test.h b/ept/debtags/expression.test.h
index c96fd44..9f2ea08 100644
--- a/ept/debtags/expression.test.h
+++ b/ept/debtags/expression.test.h
@@ -20,7 +20,7 @@
#include <wibble/test.h>
#include <ept/debtags/maint/path.h>
-#include <ept/debtags/expression.h>
+#include <tagcoll/expression.h>
#include <ept/debtags/vocabulary.h>
#include "debtags.test.h"
@@ -34,10 +34,10 @@ struct TestExpression : DebtagsTestEnvironment {
Test _1()
{
- set<Tag> test;
- test.insert(voc.tagByName("use::editing"));
- test.insert(voc.tagByName("use::viewing"));
- test.insert(voc.tagByName("works-with::text"));
+ set<std::string> test;
+ test.insert("use::editing");
+ test.insert("use::viewing");
+ test.insert("works-with::text");
assert_eq(test.size(), 3u);
diff --git a/ept/debtags/maint/debtagsindexer.cc b/ept/debtags/maint/debtagsindexer.cc
deleted file mode 100644
index 6c8d6bc..0000000
--- a/ept/debtags/maint/debtagsindexer.cc
+++ /dev/null
@@ -1,265 +0,0 @@
-#include <ept/debtags/maint/debtagsindexer.h>
-#include <ept/debtags/maint/path.h>
-#include <ept/debtags/maint/pkgid.h>
-#include <ept/debtags/maint/serializer.h>
-#include <ept/debtags/vocabulary.h>
-
-#include <tagcoll/coll/intdiskindex.h>
-#include <tagcoll/coll/simple.h>
-#include <tagcoll/TextFormat.h>
-#include <tagcoll/stream/filters.h>
-
-#include <wibble/exception.h>
-
-#include <cstring>
-
-using namespace std;
-
-namespace ept {
-namespace debtags {
-
-/// MMapIndexer that indexes the package names
-struct PkgIdGenerator : public tagcoll::diskindex::MMapIndexer
-{
- // Sorted set of all available package names
- std::set<std::string> pkgs;
-
- int encodedSize() const
- {
- int size = pkgs.size() * sizeof(int);
- for (std::set<std::string>::const_iterator i = pkgs.begin();
- i != pkgs.end(); ++i)
- size += i->size() + 1;
- return tagcoll::diskindex::MMap::align(size);
- }
-
- void encode(char* buf) const
- {
- int pos = pkgs.size() * sizeof(int);
- int idx = 0;
- for (std::set<std::string>::const_iterator i = pkgs.begin();
- i != pkgs.end(); ++i)
- {
- ((int*)buf)[idx++] = pos;
- memcpy(buf + pos, i->c_str(), i->size() + 1);
- pos += i->size() + 1;
- }
- }
-};
-
-
-DebtagsIndexer::DebtagsIndexer(Vocabulary& voc)
- : voc(voc),
- mainSource(Path::debtagsSourceDir()),
- userSource(Path::debtagsUserSourceDir())
-{
- rescan();
-}
-
-void DebtagsIndexer::rescan()
-{
- ts_main_src = mainSource.timestamp();
- ts_user_src = userSource.timestamp();
- ts_main_tag = Path::timestamp(Path::tagdb());
- ts_main_idx = Path::timestamp(Path::tagdbIndex());
- ts_user_tag = Path::timestamp(Path::userTagdb());
- ts_user_idx = Path::timestamp(Path::userTagdbIndex());
-}
-
-bool DebtagsIndexer::needsRebuild() const
-{
- // If there are no indexes of any kind, then we need rebuilding
- if (ts_user_tag == 0 && ts_user_idx == 0 && ts_main_tag == 0 && ts_main_idx == 0)
- return true;
-
- // If the user index is ok, then we are fine
- if (ts_user_tag >= sourceTimestamp() && ts_user_idx >= sourceTimestamp())
- return false;
-
- // If there are user sources, then we cannot use the system index
- if (ts_user_src > 0)
- return true;
-
- // If there are no user sources, then we can fallback on the system
- // indexes in case the user indexes are not up to date
- if (ts_main_tag >= sourceTimestamp() && ts_main_idx >= sourceTimestamp())
- return false;
-
- return true;
-}
-
-bool DebtagsIndexer::userIndexIsRedundant() const
-{
- // If there is no user index, then it is not redundant
- if (ts_user_tag == 0 && ts_user_idx == 0)
- return false;
-
- // If we have user sources, then the user index is never redundant
- if (ts_user_src > 0)
- return false;
-
- // If the system index is not up to date, then the user index is not
- // redundant
- if (ts_main_tag < sourceTimestamp() || ts_main_idx < sourceTimestamp())
- return false;
-
- return true;
-}
-
-bool DebtagsIndexer::rebuild(const std::string& tagfname, const std::string& idxfname)
-{
- using namespace tagcoll;
-
- diskindex::MasterMMapIndexer master(idxfname);
-
- // Read and merge tag data
- coll::Simple<string, string> merged;
- mainSource.readTags(inserter(merged));
- userSource.readTags(inserter(merged));
-
- if (merged.empty())
- //throw wibble::exception::Consistency("Reading debtags sources from " + Path::debtagsSourceDir() + " and " + Path::debtagsUserSourceDir(), "Unable to find any tag data");
- return false;
-
- // Create the pkgid index
- PkgIdGenerator pkgidGen;
- for (coll::Simple<string, string>::const_iterator i = merged.begin();
- i != merged.end(); ++i)
- pkgidGen.pkgs.insert(i->first);
-
- // Temporary in-memory index to use for converting packages to ints while
- // creating the debtags index
- char buf[pkgidGen.encodedSize()];
- pkgidGen.encode(buf);
- PkgId pkgid(buf, pkgidGen.encodedSize());
-
- // Create the Debtags index
- coll::IntDiskIndexer tagindexer;
- merged.output(stringToInt(pkgid, voc, inserter(tagindexer)));
-
- // MMap 0: pkgid
- master.append(pkgidGen);
- // MMap 1: pkg->tag
- master.append(tagindexer.pkgIndexer());
- // MMap 2: tag->pkg
- master.append(tagindexer.tagIndexer());
-
- // Write the tag database in text format
- std::string tmpdb = tagfname + ".tmp";
- FILE* out = fopen(tmpdb.c_str(), "wt");
- if (!out) throw wibble::exception::File(tmpdb, "creating temporary copy of tag index");
- merged.output(textformat::StdioWriter(out));
- fclose(out);
-
- // Perform "atomic" update of the tag database
- // FIXME: cannot be atomic because race conditions happening between file
- // renames
- if (rename(tmpdb.c_str(), tagfname.c_str()) == -1)
- throw wibble::exception::System("Renaming " + tmpdb + " to " + tagfname);
-
- master.commit();
- return true;
-}
-
-bool DebtagsIndexer::rebuildIfNeeded()
-{
- if (needsRebuild())
- {
- // Decide if we rebuild the user index or the system index
-
- if (ts_user_src == 0 && Path::access(Path::debtagsIndexDir(), W_OK) == 0)
- {
- // There are no user sources and we can write to the system index
- // directory: rebuild the system index
- if (!rebuild(Path::tagdb(), Path::tagdbIndex()))
- return false;
- ts_main_tag = Path::timestamp(Path::tagdb());
- ts_main_idx = Path::timestamp(Path::tagdbIndex());
- if (Path::tagdb() == Path::userTagdb())
- ts_user_tag = ts_main_tag;
- if (Path::tagdbIndex() == Path::userTagdbIndex())
- ts_user_idx = ts_main_idx;
- } else {
- wibble::sys::fs::mkFilePath(Path::userTagdb());
- wibble::sys::fs::mkFilePath(Path::userTagdbIndex());
- if (!rebuild(Path::userTagdb(), Path::userTagdbIndex()))
- return false;
- ts_user_tag = Path::timestamp(Path::userTagdb());
- ts_user_idx = Path::timestamp(Path::userTagdbIndex());
- }
- return true;
- }
- return false;
-}
-
-bool DebtagsIndexer::deleteRedundantUserIndex()
-{
- if (userIndexIsRedundant())
- {
- // Delete the user indexes if they exist
- if (Path::tagdb() != Path::userTagdb())
- {
- unlink(Path::userTagdb().c_str());
- ts_user_tag = 0;
- }
- if (Path::tagdbIndex() != Path::userTagdbIndex())
- {
- unlink(Path::userTagdbIndex().c_str());
- ts_user_idx = 0;
- }
- return true;
- }
- return false;
-}
-
-bool DebtagsIndexer::getUpToDateTagdb(std::string& tagfname, std::string& idxfname)
-{
- // If there are no indexes of any kind, then we have nothing to return
- if (ts_user_tag == 0 && ts_user_idx == 0 && ts_main_tag == 0 && ts_main_idx == 0)
- return false;
-
- // If the user index is up to date, use it
- if (ts_user_tag >= sourceTimestamp() &&
- ts_user_idx >= sourceTimestamp())
- {
- tagfname = Path::userTagdb();
- idxfname = Path::userTagdbIndex();
- return true;
- }
-
- // If the user index is not up to date and we have user sources, we cannot
- // fall back to the system index
- if (ts_user_src != 0)
- return false;
-
- // Fallback to the system index
- if (ts_main_tag >= sourceTimestamp() &&
- ts_main_idx >= sourceTimestamp())
- {
- tagfname = Path::tagdb();
- idxfname = Path::tagdbIndex();
- return true;
- }
-
- return false;
-}
-
-
-
-bool DebtagsIndexer::obtainWorkingDebtags(Vocabulary& voc, std::string& tagfname, std::string& idxfname)
-{
- DebtagsIndexer t(voc);
-
- t.rebuildIfNeeded();
- t.deleteRedundantUserIndex();
- return t.getUpToDateTagdb(tagfname, idxfname);
-}
-
-}
-}
-
-#include <ept/debtags/maint/sourcedir.tcc>
-#include <tagcoll/coll/simple.tcc>
-
-// vim:set ts=4 sw=4:
-// -*- C++ -*-
diff --git a/ept/debtags/maint/debtagsindexer.h b/ept/debtags/maint/debtagsindexer.h
deleted file mode 100644
index b702c88..0000000
--- a/ept/debtags/maint/debtagsindexer.h
+++ /dev/null
@@ -1,51 +0,0 @@
-#ifndef EPT_DEBTAGS_DEBTAGSINDEXER_H
-#define EPT_DEBTAGS_DEBTAGSINDEXER_H
-
-#include <ept/debtags/maint/sourcedir.h>
-#include <string>
-
-namespace ept {
-namespace debtags {
-
-class Vocabulary;
-
-struct DebtagsIndexer
-{
- Vocabulary& voc;
-
- SourceDir mainSource;
- SourceDir userSource;
- time_t ts_main_src;
- time_t ts_user_src;
- time_t ts_main_tag;
- time_t ts_main_idx;
- time_t ts_user_tag;
- time_t ts_user_idx;
-
- time_t sourceTimestamp() const
- {
- time_t res = ts_main_src;
- if (ts_user_src > res) res = ts_user_src;
- return res;
- }
- bool needsRebuild() const;
- bool rebuild(const std::string& tagfname, const std::string& idxfname);
- bool rebuildIfNeeded();
- bool getUpToDateTagdb(std::string& tagfname, std::string& idxfname);
-
- bool userIndexIsRedundant() const;
- bool deleteRedundantUserIndex();
-
- void rescan();
-
- DebtagsIndexer(Vocabulary& voc);
-
- static bool obtainWorkingDebtags(Vocabulary& voc, std::string& tagfname, std::string& idxfname);
-};
-
-
-}
-}
-
-// vim:set ts=4 sw=4:
-#endif
diff --git a/ept/debtags/maint/pkgid.cc b/ept/debtags/maint/pkgid.cc
deleted file mode 100644
index c78d7c1..0000000
--- a/ept/debtags/maint/pkgid.cc
+++ /dev/null
@@ -1,66 +0,0 @@
-// -*- mode: c++; tab-width: 4; indent-tabs-mode: t -*-
-
-/** @file
- * @author Enrico Zini <enrico@enricozini.org>
- * Quick map from package IDs to package names
- */
-
-/*
- * Copyright (C) 2003-2007 Enrico Zini <enrico@debian.org>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- */
-
-#include <ept/debtags/maint/pkgid.h>
-#include <ept/debtags/maint/path.h>
-
-namespace ept {
-namespace debtags {
-
-PkgId::PkgId() {}
-
-PkgId::PkgId(const char* buf, int size)
- : MMap(buf, size) {}
-
-PkgId::PkgId(const tagcoll::diskindex::MasterMMap& master, size_t idx)
- : MMap(master, idx) {}
-
-int PkgId::byName(const std::string& name) const
-{
- // Binary search the index to find the package ID
- int begin, end;
-
- /* Binary search */
- begin = -1, end = size();
- while (end - begin > 1)
- {
- int cur = (end + begin) / 2;
- if (byID(cur) > name)
- end = cur;
- else
- begin = cur;
- }
-
- if (begin == -1 || byID(begin) != name)
- //throw NotFoundException(string("looking for the ID of string ") + str);
- return -1;
- else
- return begin;
-}
-
-}
-}
-
-// vim:set ts=4 sw=4:
diff --git a/ept/debtags/maint/pkgid.h b/ept/debtags/maint/pkgid.h
deleted file mode 100644
index e193f8c..0000000
--- a/ept/debtags/maint/pkgid.h
+++ /dev/null
@@ -1,91 +0,0 @@
-// -*- mode: c++; tab-width: 4; indent-tabs-mode: t -*-
-#ifndef EPT_DEBTAGS_PKGID_H
-#define EPT_DEBTAGS_PKGID_H
-
-/** @file
- * @author Enrico Zini <enrico@enricozini.org>
- * Quick map from package IDs to package names
- */
-
-/*
- * Copyright (C) 2003-2007 Enrico Zini <enrico@debian.org>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- */
-
-#include <tagcoll/diskindex/mmap.h>
-#include <string>
-
-namespace ept {
-namespace debtags {
-
-/**
- * Maps Packages to IDs and vice-versa.
- *
- * This is used in building the Debtags fast index, which works representing
- * tags and packages as int IDs
- */
-class PkgId : public tagcoll::diskindex::MMap
-{
- tagcoll::diskindex::MasterMMap mastermmap;
- time_t m_timestamp;
-
-public:
- PkgId();
- PkgId(const tagcoll::diskindex::MasterMMap& master, size_t idx);
- PkgId(const char* buf, int size);
-
- /// Get the timestamp of when the index was last updated
- time_t timestamp() const { return m_timestamp; }
-
- /// Get the number of packages in the index
- size_t size() const { return m_buf ? *(int*)m_buf / sizeof(int) : 0; }
-
- /**
- * Get the ID of a package given its name.
- *
- * If not found, returns -1.
- */
- int byName(const std::string& name) const;
-
- /**
- * Get a package name given its ID.
- *
- * If not found, returns the empty string.
- */
- std::string byID(int id) const
- {
- if (id >= 0 || static_cast<unsigned>(id) < size())
- return std::string(m_buf + ((int*)m_buf)[id]);
- return std::string();
- }
-
- /// Get the number of packages in the index
- int size(int id) const
- {
- if (id < 0 || (unsigned)id >= size())
- return 0;
- if ((unsigned)id == size() - 1)
- return m_size - ((int*)m_buf)[id] - 1;
- else
- return ((int*)m_buf)[id + 1] - ((int*)m_buf)[id] - 1;
- }
-};
-
-}
-}
-
-// vim:set ts=4 sw=4:
-#endif
diff --git a/ept/debtags/maint/pkgid.test.h b/ept/debtags/maint/pkgid.test.h
deleted file mode 100644
index d49b72c..0000000
--- a/ept/debtags/maint/pkgid.test.h
+++ /dev/null
@@ -1,75 +0,0 @@
-// -*- mode: c++; tab-width: 4; indent-tabs-mode: t -*-
-/*
- * id->package mapping
- *
- * Copyright (C) 2006 Enrico Zini <enrico@debian.org>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- */
-
-#include <ept/debtags/maint/pkgid.h>
-#include <ept/debtags/maint/path.h>
-#include <ept/debtags/debtags.h>
-#include <set>
-
-#include <ept/test.h>
-
-using namespace std;
-using namespace ept;
-using namespace ept::debtags;
-
-struct TestPkgid : DebtagsTestEnvironment
-{
- Debtags debtags;
- PkgId& pkgid;
-
- TestPkgid()
- : pkgid(debtags.pkgid())
- {
- }
-
-// Check that we can go from name to ID and back
- Test _1()
-{
- //int x = 0;
- for (Debtags::const_iterator i = debtags.begin();
- i != debtags.end(); ++i)
- {
- int id = pkgid.byName(i->first);
- std::string pkg = pkgid.byID(id);
- assert(i->first == pkg);
-
- /* std::cerr << x << ": " << i->id() << ": "
- << i->name() << ", " << pkgidx().name( i->id() ) <<
- std::endl; */
- //++ x;
- }
-}
-
-// Check that IDs are distinct
- Test _2()
-{
- using namespace std;
-
- size_t count = 0;
- set<int> ids;
- for (Debtags::const_iterator i = debtags.begin(); i != debtags.end(); ++i, ++count)
- ids.insert(pkgid.byName(i->first));
- assert_eq(ids.size(), count);
-}
-
-};
-
-// vim:set ts=4 sw=4:
diff --git a/ept/debtags/maint/serializer.h b/ept/debtags/maint/serializer.h
deleted file mode 100644
index 57c4c81..0000000
--- a/ept/debtags/maint/serializer.h
+++ /dev/null
@@ -1,949 +0,0 @@
-// -*- mode: c++; tab-width: 4; indent-tabs-mode: t -*-
-/**
- * @file cache/component/debtags/serializer.h
- * @author Enrico Zini (enrico) <enrico@enricozini.org>
- */
-
-#ifndef EPT_DEBTAGS_SERIALIZER_H
-#define EPT_DEBTAGS_SERIALIZER_H
-
-#include <ept/debtags/vocabulary.h>
-#include <ept/debtags/maint/pkgid.h>
-#include <tagcoll/patch.h>
-#include <wibble/mixin.h>
-#include <string>
-
-namespace ept {
-namespace debtags {
-
-template<typename OUT>
-class IntToPkg : public wibble::mixin::OutputIterator< IntToPkg<OUT> >
-{
- PkgId& pkgid;
- Vocabulary& voc;
- OUT out;
-
-public:
- IntToPkg(PkgId& pkgid, Vocabulary& voc, const OUT& out)
- : pkgid(pkgid), voc(voc), out(out) {}
-
- template<typename ITEMS, typename TAGS>
- IntToPkg<OUT>& operator=(const std::pair<ITEMS, TAGS>& data)
- {
- std::set<std::string> ritems;
- std::set<Tag> rtags;
-
- for (typename ITEMS::const_iterator i = data.first.begin();
- i != data.first.end(); ++i)
- {
- std::string pkg = pkgid.byID(*i);
- if (!pkg.empty())
- ritems.insert(pkg);
- }
-
- for (typename TAGS::const_iterator i = data.second.begin();
- i != data.second.end(); ++i)
- {
- Tag t = voc.tagByID(*i);
- if (t.valid())
- rtags.insert(t);
- }
-
- if (!ritems.empty() && !rtags.empty())
- {
- *out = make_pair(ritems, rtags);
- ++out;
- }
- return *this;
- }
-};
-
-template<typename OUT>
-IntToPkg<OUT> intToPkg(PkgId& pkgid, Vocabulary& voc, const OUT& out)
-{
- return IntToPkg<OUT>(pkgid, voc, out);
-}
-
-template<typename OUT>
-class StringToInt : public wibble::mixin::OutputIterator< StringToInt<OUT> >
-{
- PkgId& pkgid;
- Vocabulary& voc;
- OUT out;
-
-public:
- StringToInt(PkgId& pkgid, Vocabulary& voc, const OUT& out)
- : pkgid(pkgid), voc(voc), out(out) {}
-
- template<typename ITEMS, typename TAGS>
- StringToInt<OUT>& operator=(const std::pair<ITEMS, TAGS>& data)
- {
- std::set<int> ritems;
- std::set<int> rtags;
-
- for (typename ITEMS::const_iterator i = data.first.begin();
- i != data.first.end(); ++i)
- {
- int id = pkgid.byName(*i);
- if (id != -1)
- ritems.insert(id);
- }
-
- for (typename TAGS::const_iterator i = data.second.begin();
- i != data.second.end(); ++i)
- {
- Tag t = voc.tagByName(*i);
- if (t.valid())
- rtags.insert(t.id());
- }
-
- if (!ritems.empty() && !rtags.empty())
- {
- *out = make_pair(ritems, rtags);
- ++out;
- }
- return *this;
- }
-
-};
-
-template<typename OUT>
-StringToInt<OUT> stringToInt(PkgId& pkgid, Vocabulary& voc, const OUT& out)
-{
- return StringToInt<OUT>(pkgid, voc, out);
-}
-
-template<typename OUT>
-class StringToPkg : public wibble::mixin::OutputIterator< StringToPkg<OUT> >
-{
- PkgId& pkgid;
- Vocabulary& voc;
- OUT out;
-
-public:
- StringToPkg(PkgId& pkgid, Vocabulary& voc, const OUT& out)
- : pkgid(pkgid), voc(voc), out(out) {}
-
- template<typename ITEMS, typename TAGS>
- StringToPkg<OUT>& operator=(const std::pair<ITEMS, TAGS>& data)
- {
- std::set<std::string> ritems;
- std::set<Tag> rtags;
-
- for (typename ITEMS::const_iterator i = data.first.begin();
- i != data.first.end(); ++i)
- {
- // Ensure that the package exists in the pkgid database
- if (pkgid.byName(*i) == -1)
- continue;
- ritems.insert(*i);
- }
-
- for (typename TAGS::const_iterator i = data.second.begin();
- i != data.second.end(); ++i)
- {
- Tag t = voc.tagByName(*i);
- if (t.valid())
- rtags.insert(t);
- }
-
- if (!ritems.empty() && !rtags.empty())
- {
- *out = make_pair(ritems, rtags);
- ++out;
- }
- return *this;
- }
-
-};
-
-template<typename OUT>
-StringToPkg<OUT> stringToPkg(PkgId& pkgid, Vocabulary& voc, const OUT& out)
-{
- return StringToPkg<OUT>(pkgid, voc, out);
-}
-
-template<typename OUT>
-class PkgToString : public wibble::mixin::OutputIterator< PkgToString<OUT> >
-{
- OUT out;
-public:
- PkgToString(const OUT& out) : out(out) {}
-
- template<typename ITEMS, typename TAGS>
- PkgToString<OUT>& operator=(const std::pair<ITEMS, TAGS>& data)
- {
- std::set<std::string> stags;
- for (typename TAGS::const_iterator i = data.second.begin();
- i != data.second.end(); ++i)
- if (i->valid())
- stags.insert(i->fullname());
- *out = make_pair(data.first, stags);
- ++out;
- return *this;
- }
-};
-
-template<typename OUT>
-PkgToString<OUT> pkgToString(const OUT& out)
-{
- return PkgToString<OUT>(out);
-}
-
-template<typename OUT>
-class PatchStringToInt : public wibble::mixin::OutputIterator< PatchStringToInt<OUT> >
-{
- PkgId& pkgid;
- Vocabulary& voc;
- OUT out;
-
-public:
- PatchStringToInt(PkgId& pkgid, Vocabulary& voc, const OUT& out)
- : pkgid(pkgid), voc(voc), out(out) {}
-
- PatchStringToInt<OUT>& operator=(const tagcoll::Patch<std::string, std::string>& patch)
- {
- int id = pkgid.byName(patch.item);
- if (id == -1)
- return *this;
-
- tagcoll::Patch<int, int> res(id);
- for (std::set<std::string>::const_iterator i = patch.added.begin();
- i != patch.added.end(); ++i)
- {
- Tag tag = voc.tagByName(*i);
- if (tag.valid())
- res.add(tag.id());
- }
- for (std::set<std::string>::const_iterator i = patch.removed.begin();
- i != patch.removed.end(); ++i)
- {
- Tag tag = voc.tagByName(*i);
- if (tag.valid())
- res.remove(tag.id());
- }
- *out = res;
- ++out;
- return *this;
- }
-};
-
-template<typename OUT>
-PatchStringToInt<OUT> patchStringToInt(PkgId& pkgid, Vocabulary& voc, const OUT& out)
-{
- return PatchStringToInt<OUT>(pkgid, voc, out);
-}
-
-template<typename OUT>
-class PatchIntToString : public wibble::mixin::OutputIterator< PatchIntToString<OUT> >
-{
- PkgId& pkgid;
- Vocabulary& voc;
- OUT out;
-
-public:
- PatchIntToString(PkgId& pkgid, Vocabulary& voc, const OUT& out)
- : pkgid(pkgid), voc(voc), out(out) {}
-
- PatchIntToString<OUT>& operator=(const tagcoll::Patch<int, int>& patch)
- {
- std::string name = pkgid.byID(patch.item);
- if (name.empty())
- return *this;
-
- tagcoll::Patch<std::string, std::string> res(name);
- for (std::set<int>::const_iterator i = patch.added.begin();
- i != patch.added.end(); ++i)
- {
- Tag tag = voc.tagByID(*i);
- if (tag.valid())
- res.add(tag.fullname());
- }
- for (std::set<int>::const_iterator i = patch.removed.begin();
- i != patch.removed.end(); ++i)
- {
- Tag tag = voc.tagByID(*i);
- if (tag.valid())
- res.remove(tag.fullname());
- }
- *out = res;
- ++out;
- return *this;
- }
-};
-
-template<typename OUT>
-PatchIntToString<OUT> patchIntToString(PkgId& pkgid, Vocabulary& voc, const OUT& out)
-{
- return PatchIntToString<OUT>(pkgid, voc, out);
-}
-
-#if 0
- GOOD STUFF
-
-template<typename OUT>
-class ToInt : public wibble::mixin::OutputIterator< ToInt<OUT> >
-{
- OUT out;
-public:
- ToInt(const OUT& out) : out(out) {}
-
- template<typename ITEMS, typename TAGS>
- ToInt<OUT>& operator=(const std::pair<ITEMS, TAGS>& data)
- {
- std::set<int> iitems;
- std::set<int> itags;
- for (typename ITEMS::const_iterator i = data.first.begin();
- i != data.first.end(); ++i)
- if (i->valid())
- iitems.insert(i->ondiskId());
- for (typename TAGS::const_iterator i = data.second.begin();
- i != data.second.end(); ++i)
- if (i->valid())
- itags.insert(i->id());
- *out = make_pair(iitems, itags);
- ++out;
- return *this;
- }
-};
-
-template<typename OUT>
-ToInt<OUT> toInt(const OUT& out)
-{
- return ToInt<OUT>(out);
-}
-
-template<typename ITEMCONV, typename TAGCONV, typename OUT>
-class Converter : public wibble::mixin::OutputIterator< Converter<ITEMCONV, TAGCONV, OUT> >
-{
- ITEMCONV itemconv;
- TAGCONV tagconv;
- OUT out;
-
-public:
- Converter(const ITEMCONV& itemconv, const TAGCONV& tagconv, const OUT& out)
- : itemconv(itemconv), tagconv(tagconv), out(out) {}
-
- template<typename ITEMS, typename TAGS>
- Converter<ITEMCONV, TAGCONV, OUT>& operator=(const std::pair<ITEMS, TAGS>& data)
- {
- *out = make_pair(itemconv(data.first), tagconv(data.second));
- ++out;
- return *this;
- }
-};
-
-template<typename ITEMCONV, typename TAGCONV, typename OUT>
-Converter<ITEMCONV, TAGCONV, OUT> converter(const ITEMCONV& itemconv, const TAGCONV& tagconv, const OUT& out)
-{
- return Converter<ITEMCONV, TAGCONV, OUT>(itemconv, tagconv, out);
-}
-
-
-template<typename OUT>
-class PatchToString : public wibble::mixin::OutputIterator< PatchToString<OUT> >
-{
- OUT out;
-
-public:
- PatchToString(const OUT& out) : out(out) {}
-
- template<typename PKG, typename TAG>
- PatchToString<OUT>& operator=(const tagcoll::Patch<PKG, TAG>& patch)
- {
- if (!patch.item.valid())
- return *this;
-
- tagcoll::Patch<std::string, std::string> res(patch.item.name());
- for (typename std::set<TAG>::const_iterator i = patch.added.begin();
- i != patch.added.end(); ++i)
- if (i->valid())
- res.add(i->fullname());
- for (typename std::set<TAG>::const_iterator i = patch.removed.begin();
- i != patch.removed.end(); ++i)
- if (i->valid())
- res.remove(i->fullname());
- *out = res;
- ++out;
- return *this;
- }
-};
-
-template<typename OUT>
-PatchToString<OUT> patchToString(const OUT& out)
-{
- return PatchToString<OUT>(out);
-}
-
-#endif
-
-}
-}
-
-#if 0
-
-namespace tagcoll {
-namespace coll {
-
-template<>
-struct coll_traits< ept::cache::debtags::DebtagsIndex >
-{
- typedef ept::cache::Package<> item_type;
- typedef ept::cache::debtags::Tag tag_type;
- typedef std::set< ept::cache::Package<> > itemset_type;
- typedef std::set<ept::cache::debtags::Tag> tagset_type;
-};
-
-}
-}
-
-namespace ept {
-namespace cache {
-namespace debtags {
-
-#if 0
-/**
- * Convert Facets to ints
- */
-class FacetIntConverter : public Implementation<FacetIntConverter>,
- public Tagcoll::Converter<aptFront::cache::entity::Facet, int>,
- public Tagcoll::Converter<int, aptFront::cache::entity::Facet>
-{
- typedef aptFront::cache::entity::Facet Facet;
- typedef Tagcoll::OpSet<aptFront::cache::entity::Facet> FacetSet;
- typedef Tagcoll::OpSet<int> IntSet;
-public:
- virtual int operator()(const aptFront::cache::entity::Facet& item) const;
- virtual aptFront::cache::entity::Facet operator()(const int& item) const;
-
- virtual IntSet operator()(const FacetSet& item) const
- { return Tagcoll::Converter<Facet, int>::operator()(item); }
- virtual FacetSet operator()(const IntSet& item) const
- { return Tagcoll::Converter<int, Facet>::operator()(item); }
-
- static std::string componentName();
-};
-
-/**
- * Convert Facets to strings
- */
-class FacetStringConverter : public Implementation<FacetStringConverter>,
- public Tagcoll::Converter<aptFront::cache::entity::Facet, std::string>,
- public Tagcoll::Converter<std::string, aptFront::cache::entity::Facet>
-{
- typedef aptFront::cache::entity::Facet Facet;
- typedef Tagcoll::OpSet<aptFront::cache::entity::Facet> FacetSet;
- typedef Tagcoll::OpSet<std::string> StringSet;
-public:
- virtual std::string operator()(const aptFront::cache::entity::Facet& item) const;
- virtual aptFront::cache::entity::Facet operator()(const std::string& item) const;
-
- virtual StringSet operator()(const FacetSet& item) const
- { return Tagcoll::Converter<Facet, std::string>::operator()(item); }
- virtual FacetSet operator()(const StringSet& item) const
- { return Tagcoll::Converter<std::string, Facet>::operator()(item); }
-
- static std::string componentName();
-};
-
-/**
- * Convert Vocabulary to ints
- */
-class TagIntConverter : public Implementation<TagIntConverter>,
- public Tagcoll::Converter<aptFront::cache::entity::Tag, int>,
- public Tagcoll::Converter<int, aptFront::cache::entity::Tag>
-{
- typedef aptFront::cache::entity::Tag Tag;
- typedef Tagcoll::OpSet<aptFront::cache::entity::Tag> TagSet;
- typedef Tagcoll::OpSet<int> IntSet;
-public:
- virtual int operator()(const aptFront::cache::entity::Tag& item) const;
- virtual aptFront::cache::entity::Tag operator()(const int& item) const;
-
- virtual IntSet operator()(const TagSet& item) const
- { return Tagcoll::Converter<Tag, int>::operator()(item); }
- virtual TagSet operator()(const IntSet& item) const
- { return Tagcoll::Converter<int, Tag>::operator()(item); }
-
- static std::string componentName();
-};
-
-/**
- * Convert Vocabulary to strings
- */
-class TagStringConverter : public Implementation<TagStringConverter>,
- public Tagcoll::Converter<aptFront::cache::entity::Tag, std::string>,
- public Tagcoll::Converter<std::string, aptFront::cache::entity::Tag>
-{
- typedef aptFront::cache::entity::Tag Tag;
- typedef Tagcoll::OpSet<aptFront::cache::entity::Tag> TagSet;
- typedef Tagcoll::OpSet<std::string> StringSet;
-public:
- virtual std::string operator()(const Tag& item) const;
- virtual Tag operator()(const std::string& item) const;
-
- virtual StringSet operator()(const TagSet& item) const
- { return Tagcoll::Converter<Tag, std::string>::operator()(item); }
- virtual TagSet operator()(const StringSet& item) const
- { return Tagcoll::Converter<std::string, Tag>::operator()(item); }
-
- TagSet parseTagList(const std::string& str) const;
-
- static std::string componentName();
-};
-
-/**
- * Convert Aggregator to ints
- */
-class PackageIntConverter : public Implementation<PackageIntConverter>,
- public Tagcoll::Converter<aptFront::cache::entity::Package, int>,
- public Tagcoll::Converter<int, aptFront::cache::entity::Package>
-{
- typedef aptFront::cache::entity::Package Package;
- typedef Tagcoll::OpSet<aptFront::cache::entity::Package> PackageSet;
- typedef Tagcoll::OpSet<int> IntSet;
-public:
- virtual int operator()(const Package& item) const;
- virtual Package operator()(const int& item) const;
-
- virtual IntSet operator()(const PackageSet& item) const
- { return Tagcoll::Converter<Package, int>::operator()(item); }
- virtual PackageSet operator()(const IntSet& item) const
- { return Tagcoll::Converter<int, Package>::operator()(item); }
-
- static std::string componentName();
-};
-
-/**
- * Convert Aggregator to strings
- */
-class PackageStringConverter : public Implementation<PackageStringConverter>,
- public Tagcoll::Converter<aptFront::cache::entity::Package, std::string>,
- public Tagcoll::Converter<std::string, aptFront::cache::entity::Package>
-{
- typedef aptFront::cache::entity::Package Package;
- typedef Tagcoll::OpSet<aptFront::cache::entity::Package> PackageSet;
- typedef Tagcoll::OpSet<std::string> StringSet;
-public:
- virtual std::string operator()(const Package& item) const;
- virtual Package operator()(const std::string& item) const;
-
- virtual StringSet operator()(const PackageSet& item) const
- { return Tagcoll::Converter<Package, std::string>::operator()(item); }
- virtual PackageSet operator()(const StringSet& item) const
- { return Tagcoll::Converter<std::string, Package>::operator()(item); }
-
- static std::string componentName();
-};
-
-#endif
-
-}
-}
-}
-
-#endif
-
-#endif
-// -*- mode: c++; tab-width: 4; indent-tabs-mode: t -*-
-
-#if 0
-/**
- * @file cache/debtags/serializer.h
- * @author Enrico Zini (enrico) <enrico@enricozini.org>
- */
-
-#ifndef EPT_CACHE_DEBTAGS_SERIALIZER_TCC
-#define EPT_CACHE_DEBTAGS_SERIALIZER_TCC
-
-#include <ept/cache/debtags/serializer.h>
-#if 0
-#include <ept/cache/debtags/pkgidx.h>
-#include <ept/cache/debtags/vocabulary.h>
-#include <ept/cache/package.h>
-//#include <ept/cache/cache.h>
-#endif
-
-namespace ept {
-namespace t {
-namespace cache {
-namespace debtags {
-
-
-
-#if 0
-string FacetIntConverter::componentName() { return "FacetIntConverter"; }
-
-int FacetIntConverter::operator()(const aptFront::cache::entity::Facet& item) const
-{
- if (!item.valid()) return -1;
- return item.id();
-}
-aptFront::cache::entity::Facet FacetIntConverter::operator()(const int& item) const
-{
- return cache().tags().facetByID(item);
-}
-
-string FacetStringConverter::componentName() { return "FacetStringConverter"; }
-
-std::string FacetStringConverter::operator()(const aptFront::cache::entity::Facet& item) const
-{
- if (!item.valid()) return string();
- return item.name();
-}
-aptFront::cache::entity::Facet FacetStringConverter::operator()(const std::string& item) const
-{
- return cache().tags().facetByName(item);
-}
-
-string TagIntConverter::componentName() { return "TagIntConverter"; }
-
-int TagIntConverter::operator()(const aptFront::cache::entity::Tag& item) const
-{
- if (!item.valid()) return -1;
- return item.id();
-}
-aptFront::cache::entity::Tag TagIntConverter::operator()(const int& item) const
-{
- return cache().tags().tagByID(item);
-}
-
-string TagStringConverter::componentName() { return "TagStringConverter"; }
-
-std::string TagStringConverter::operator()(const aptFront::cache::entity::Tag& item) const
-{
- if (!item.valid()) return string();
- return item.fullname();
-}
-aptFront::cache::entity::Tag TagStringConverter::operator()(const std::string& item) const
-{
- return cache().tags().tagByName(item);
-}
-
-Tagcoll::OpSet<entity::Tag> TagStringConverter::parseTagList(const std::string& str) const
-{
- if (str.empty())
- return Tagcoll::OpSet<entity::Tag>();
-
- size_t i = str.find(", ");
- if (i == string::npos)
- {
- // Check if we need curly brace expansion
- if (str[str.size() - 1] == '}')
- {
- using namespace std;
- Tagcoll::OpSet<entity::Tag> res;
- size_t begin = str.find('{');
- if (begin == string::npos)
- return res;
- string prefix(str, 0, begin);
- ++begin;
- size_t end;
- while ((end = str.find(',', begin)) != string::npos)
- {
- res += (*this)(prefix + str.substr(begin, end-begin));
- begin = end + 1;
- }
- res += (*this)(prefix + str.substr(begin, str.size() - 1 - begin));
- return res;
- } else {
- entity::Tag t = (*this)(str);
- if (t.valid())
- return Tagcoll::OpSet<entity::Tag>() + t;
- else
- return Tagcoll::OpSet<entity::Tag>();
- }
- } else {
- return parseTagList(string(str, 0, i)) + parseTagList(string(str, i+2));
- }
-}
-
-string PackageIntConverter::componentName() { return "PackageIntConverter"; }
-
-int PackageIntConverter::operator()(const aptFront::cache::entity::Package& item) const
-{
- if (!item.valid()) return -1;
- return item.id();
-}
-aptFront::cache::entity::Package PackageIntConverter::operator()(const int& item) const
-{
- PkgIdx& p = cache().pkgidx();
- return cache().packages().packageByName(string(p.name(item), p.size(item)));
-}
-
-string PackageStringConverter::componentName() { return "PackageStringConverter"; }
-
-std::string PackageStringConverter::operator()(const aptFront::cache::entity::Package& item) const
-{
- if (!item.valid()) return string();
- return item.name();
-}
-aptFront::cache::entity::Package PackageStringConverter::operator()(const std::string& item) const
-{
- return cache().packages().packageByName(item);
-}
-#endif
-
-}
-}
-
-#endif
-
-#if 0
-#ifdef COMPILE_TESTSUITE
-//#include <apt-front/cache/component/debtags/update.h>
-#include <iostream>
-#include "test-utils.h"
-
-namespace tut {
-using namespace aptFront::cache;
-using namespace component;
-using namespace debtags;
-using namespace std;
-
-struct cache_component_debtags_serializer_shar {
- cache_component_debtags_serializer_shar () {
- aptInit ();
- ok = true;
- debtags::fetchNewData();
- c.open( Cache::OpenDefault |
- Cache::OpenReadOnly | Cache::OpenDebtags );
- }
- void check() {
- if (ok) return;
- ok = true;
- throw warning( "debtags init failed, cancelling" );
- }
- ~cache_component_debtags_serializer_shar() {
- check();
- }
- Cache c;
- bool ok;
-};
-
-TESTGRP( cache_component_debtags_serializer );
-
-using namespace Tagcoll;
-
-template<> template<>
-void to::test<1> ()
-{
- check();
-
- PackageStringConverter& psc = c.packagestringconverter();
-
- ensure(psc("Slartibartsfart") == entity::Package());
-
- /* Get the 'debtags' package */
- entity::Package p = c.packages().packageByName( "debtags" );
- ensure(p.valid());
-
- /* Get the 'debtags' package using the serializer */
- entity::Package p1 = psc("debtags");
- ensure(p1.valid());
-
- /* They must be the same */
- ensure(p == p1);
-
- ensure_equals(psc(p), "debtags");
- ensure_equals(psc(p1), "debtags");
- ensure_equals(psc(p), psc(p1));
-
- /* If there is an invalid package to serialize, it should be discarded */
- {
- Tagcoll::OpSet<entity::Package> pkgs;
- pkgs += c.packages().packageByName( "debtags" );
- pkgs += c.packages().packageByName( "tagcoll" );
- pkgs += entity::Package();
-
- ensure_equals (pkgs.size(), 3u);
- ensure_equals (psc(pkgs).size(), 2u);
- ensure (psc(pkgs).contains("debtags"));
- ensure (psc(pkgs).contains("tagcoll"));
- }
-
- /* If there is an invalid package to serialize, it should be discarded */
- {
- Tagcoll::OpSet<std::string> pkgs;
- pkgs += "debtags";
- pkgs += "tagcoll";
- pkgs += "Slartibartsfart";
-
- ensure_equals (pkgs.size(), 3u);
- ensure_equals (psc(pkgs).size(), 2u);
- ensure (psc(pkgs).contains(psc("debtags")));
- ensure (psc(pkgs).contains(psc("tagcoll")));
- ensure (!psc(pkgs).contains(entity::Package()));
- }
-}
-
-ostream& operator<<(ostream& out, const entity::Package& pkg)
-{
- if (pkg.valid())
- return out << pkg.name();
- else
- return out << "(invalid package)";
-}
-
-// Check that package conversions work two-way
-template<> template<>
-void to::test<2> ()
-{
- PackageStringConverter& psc = c.packagestringconverter();
- for (component::Aggregator::iterator i = c.packages().packagesBegin();
- i != c.packages().packagesEnd(); ++i)
- {
- try {
- ensure_equals(*i, psc(psc(*i)));
- } catch (...) {
- cerr << "Note: exception thrown during processing[string] of package " << i->name(string("(invalid package)")) << endl;
- throw;
- }
- }
-
- PackageIntConverter& pic = c.packageintconverter();
- for (component::Aggregator::iterator i = c.packages().packagesBegin();
- i != c.packages().packagesEnd(); ++i)
- {
- try {
- ensure_equals(*i, pic(pic(*i)));
- } catch (...) {
- cerr << "Note: exception thrown during processing[int] of package " << i->name(string("(invalid package)")) << endl;
- throw;
- }
- }
-}
-
-// Check that facet conversions work two-way
-template<> template<>
-void to::test<3> ()
-{
- typedef Tagcoll::OpSet<entity::Facet> FacetSet;
-
- FacetStringConverter& fsc = c.facetstringconverter();
- FacetSet allFacets(c.tags().facets());
- for (FacetSet::const_iterator i = allFacets.begin(); i != allFacets.end(); i++)
- {
- try {
- ensure_equals(*i, fsc(fsc(*i)));
- } catch (...) {
- cerr << "Note: exception thrown during processing[string] of facet " << i->name() << endl;
- throw;
- }
- }
-
- FacetIntConverter& fic = c.facetintconverter();
- for (FacetSet::const_iterator i = allFacets.begin(); i != allFacets.end(); i++)
- {
- try {
- ensure_equals(*i, fic(fic(*i)));
- } catch (...) {
- cerr << "Note: exception thrown during processing[int] of facet " << i->name() << endl;
- throw;
- }
- }
-}
-
-// Check that tag conversions work two-way
-template<> template<>
-void to::test<4> ()
-{
- typedef Tagcoll::OpSet<entity::Tag> TagSet;
-
- TagStringConverter& tsc = c.tagstringconverter();
- TagSet allTags(c.tags().tags());
- for (TagSet::const_iterator i = allTags.begin(); i != allTags.end(); i++)
- {
- try {
- ensure_equals(*i, tsc(tsc(*i)));
- } catch (...) {
- cerr << "Note: exception thrown during processing[string] of tag " << i->fullname() << endl;
- throw;
- }
- }
-
- TagIntConverter& tic = c.tagintconverter();
- for (TagSet::const_iterator i = allTags.begin(); i != allTags.end(); i++)
- {
- try {
- ensure_equals(*i, tic(tic(*i)));
- } catch (...) {
- cerr << "Note: exception thrown during processing[int] of tag " << i->fullname() << endl;
- throw;
- }
- }
-}
-
-// Check TagStringConverter::parseTagList
-template<> template<>
-void to::test<5> ()
-{
- TagStringConverter& tsc = c.tagstringconverter();
- OpSet<entity::Tag> ts;
-
- // First ensure that we're using existing tags as samples
- ensure(tsc("accessibility::TODO") != entity::Tag());
- ensure(tsc("role::sw:devel-lib") != entity::Tag());
- ensure(tsc("x11::xserver") != entity::Tag());
- ensure(tsc("antani") == entity::Tag());
- ensure(tsc("blinda") == entity::Tag());
- ensure(tsc("supercazzola") == entity::Tag());
-
- ts = tsc.parseTagList("role::sw:devel-lib");
- ensure_equals(ts.size(), 1u);
- ensure(ts.contains(tsc("role::sw:devel-lib")));
-
- ts = tsc.parseTagList("accessibility::TODO, x11::xserver, role::sw:devel-lib");
- ensure_equals(ts.size(), 3u);
- ensure(ts.contains(tsc("accessibility::TODO")));
- ensure(ts.contains(tsc("role::sw:devel-lib")));
- ensure(ts.contains(tsc("x11::xserver")));
-
- ts = tsc.parseTagList("antani");
- ensure_equals(ts.size(), 0u);
-
- ts = tsc.parseTagList("antani, blinda, supercazzola");
- ensure_equals(ts.size(), 0u);
-
- ts = tsc.parseTagList("antani, x11::xserver, blinda");
- ensure_equals(ts.size(), 1u);
- ensure(ts.contains(tsc("x11::xserver")));
-}
-
-// Check TagStringConverter::parseTagList's handling of curly brace expansion
-template<> template<>
-void to::test<6> ()
-{
- TagStringConverter& tsc = c.tagstringconverter();
- OpSet<entity::Tag> ts;
-
- // First ensure that we're using existing tags as samples
- ensure(tsc("role::TODO") != entity::Tag());
- ensure(tsc("role::sw:server") != entity::Tag());
- ensure(tsc("role::aux:dummy") != entity::Tag());
- ensure(tsc("role::sw:amusement") != entity::Tag());
- ensure(tsc("role::sw:server{}") == entity::Tag());
- ensure(tsc("role::{}") == entity::Tag());
- ensure(tsc("role::{") == entity::Tag());
- ensure(tsc("role::}") == entity::Tag());
-
- ts = tsc.parseTagList("role::{TODO,sw:server,aux:dummy,sw:amusement}");
- ensure_equals(ts.size(), 4u);
- ensure(ts.contains(tsc("role::TODO")));
- ensure(ts.contains(tsc("role::sw:server")));
- ensure(ts.contains(tsc("role::aux:dummy")));
- ensure(ts.contains(tsc("role::sw:amusement")));
-
- ts = tsc.parseTagList("role::{TODO,aux:dummy}, role::sw:{server,amusement}");
- ensure_equals(ts.size(), 4u);
- ensure(ts.contains(tsc("role::TODO")));
- ensure(ts.contains(tsc("role::sw:server")));
- ensure(ts.contains(tsc("role::aux:dummy")));
- ensure(ts.contains(tsc("role::sw:amusement")));
-}
-
-}
-#endif
-#endif
-#endif
-// vim:set ts=4 sw=4:
diff --git a/ept/debtags/maint/serializer.test.h b/ept/debtags/maint/serializer.test.h
deleted file mode 100644
index 6a4f3a6..0000000
--- a/ept/debtags/maint/serializer.test.h
+++ /dev/null
@@ -1,133 +0,0 @@
-// -*- mode: c++; tab-width: 4; indent-tabs-mode: t -*-
-/**
- * @file
- * @author Enrico Zini (enrico) <enrico@enricozini.org>
- */
-
-/*
- * Tests for Debtags serialization filters
- *
- * Copyright (C) 2003-2007 Enrico Zini <enrico@debian.org>
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- */
-
-#include <ept/debtags/maint/serializer.h>
-#include <ept/debtags/maint/pkgid.h>
-#include <ept/debtags/maint/path.h>
-#include <ept/debtags/vocabulary.h>
-#include <ept/debtags/debtags.h>
-
-#include <tagcoll/coll/simple.h>
-
-#include <wibble/singleton.h>
-
-#include <ept/test.h>
-
-using namespace std;
-using namespace tagcoll;
-using namespace ept;
-using namespace ept::debtags;
-
-struct TestSerializer : DebtagsTestEnvironment
-{
- Debtags debtags;
- Vocabulary& voc;
- PkgId& pkgid;
-
- TestSerializer()
- : voc(debtags.vocabulary()), pkgid(debtags.pkgid()) {}
-
-/* Test going from a stream of tag data <string, string> to a stream of tag
- * data <int, int> to a stream of tag data <Package, Tag> and finally back to a
- * stream of tag data <string, string>
- */
- Test _1()
-{
- // Source data <string, string>
- coll::Simple<string, string> source;
- source.insert(wibble::singleton(string("debtags")), wibble::singleton(string("use::editing")));
- source.insert(wibble::singleton(string("debtags")), wibble::singleton(string("role::program")));
-
- // <string, string> -> <int, int>
- coll::Simple<int, int> dest;
- source.output(stringToInt(pkgid, voc, inserter(dest)));
-
- assert_eq(dest.itemCount(), 1u);
- assert_eq(dest.tagCount(), 2u);
-
- // <int, int> -> <Package, Tag>
- coll::Simple<string, Tag> dest1;
- dest.output(intToPkg(pkgid, voc, inserter(dest1)));
-
- assert_eq(dest1.itemCount(), 1u);
- assert_eq(dest1.tagCount(), 2u);
-
- std::set<Tag> tags = dest1.getTagsOfItem("debtags");
- assert_eq(tags.size(), 2u);
-
- Tag useEditing = voc.tagByName("use::editing");
- Tag roleProgram = voc.tagByName("role::program");
-
- assert(tags.find(useEditing) != tags.end());
- assert(tags.find(roleProgram) != tags.end());
-
- // <Package, Tag> -> <string, string>
- coll::Simple<string, string> dest2;
- dest1.output(pkgToString(inserter(dest2)));
-
- assert_eq(dest2.itemCount(), 1u);
- assert_eq(dest2.tagCount(), 2u);
-
- std::set<std::string> tags1 = dest2.getTagsOfItem("debtags");
- assert_eq(tags1.size(), 2u);
-
- assert(tags1.find("use::editing") != tags1.end());
- assert(tags1.find("role::program") != tags1.end());
-}
-
-/* Test going from patch with strings to patch with ints and vice versa */
- Test _2()
-{
- PatchList<string, string> change;
- change.addPatch(Patch<string, string>("debtags",
- wibble::singleton(string("use::gameplaying")),
- wibble::singleton(string("use::editing"))));
-
- // Deserialise to ints
- PatchList<int, int> intChange;
- change.output(patchStringToInt(pkgid, voc, tagcoll::inserter(intChange)));
- assert_eq(intChange.size(), 1u);
- assert_eq(intChange.begin()->second.added.size(), 1u);
- assert_eq(intChange.begin()->second.removed.size(), 1u);
-
- // Serialise back to strings
- PatchList<string, string> change1;
- intChange.output(patchIntToString(pkgid, voc, tagcoll::inserter(change1)));
- assert_eq(change1.size(), 1u);
- assert_eq(change1.begin()->first, string("debtags"));
- assert_eq(change1.begin()->second.item, string("debtags"));
- assert_eq(change1.begin()->second.added.size(), 1u);
- assert_eq(*change1.begin()->second.added.begin(), string("use::gameplaying"));
- assert_eq(change1.begin()->second.removed.size(), 1u);
- assert_eq(*change1.begin()->second.removed.begin(), string("use::editing"));
-}
-
-};
-
-#include <tagcoll/coll/simple.tcc>
-#include <tagcoll/patch.tcc>
-
-// vim:set ts=4 sw=4:
diff --git a/ept/debtags/maint/sourcedir.cc b/ept/debtags/maint/sourcedir.cc
index 79f0477..9b008fb 100644
--- a/ept/debtags/maint/sourcedir.cc
+++ b/ept/debtags/maint/sourcedir.cc
@@ -1,5 +1,5 @@
#include <ept/debtags/maint/sourcedir.h>
-#include <ept/debtags/maint/vocabularymerger.h>
+#include <ept/debtags/vocabulary.h>
#include <ept/debtags/maint/path.h>
#include <wibble/string.h>
@@ -97,6 +97,7 @@ void SourceDir::readVocabularies(Vocabulary& out)
for (const_iterator d = begin(); d != end(); ++d)
{
+ if (d->d_name[0] == '.') continue;
FileType type = fileType(d->d_name);
if (type == VOC)
{
diff --git a/ept/debtags/maint/sourcedir.h b/ept/debtags/maint/sourcedir.h
index f970155..988ae24 100644
--- a/ept/debtags/maint/sourcedir.h
+++ b/ept/debtags/maint/sourcedir.h
@@ -30,7 +30,7 @@
namespace ept {
namespace debtags {
-class VocabularyMerger;
+class Vocabulary;
/**
* Access a directory containing Debtags data files
diff --git a/ept/debtags/maint/vocabularymerger.test.h b/ept/debtags/maint/vocabularymerger.test.h
deleted file mode 100644
index 4443a22..0000000
--- a/ept/debtags/maint/vocabularymerger.test.h
+++ /dev/null
@@ -1,144 +0,0 @@
-/*
- * Merge different vocabularies together and create the tag and facet indexes
- *
- * Copyright (C) 2003-2007 Enrico Zini <enrico@debian.org>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- */
-
-#include <wibble/test.h>
-#include <ept/debtags/maint/vocabularymerger.h>
-#include <tagcoll/input/string.h>
-
-using namespace std;
-using namespace tagcoll;
-
-struct TestVocabularyMerger {
-
- inline static const char* indexref(const char* index, int id)
- {
- return index + ((int*)index)[id];
- }
-
-
- Test _1()
-{
- string voc1 =
- "Facet: taste\n"
- "Description: Taste\n\n"
- "Tag: taste::sweet\n"
- "Description: Sweet\n\n"
- "Tag: taste::salty\n"
- "Description: Salty\n\n";
- string voc2 =
- "Facet: smell\n"
- "Description: Smell\n\n"
- "Tag: smell::fresh\n"
- "Description: Fresh\n\n"
- "Tag: smell::mold\n"
- "Description: Mold\n\n";
- tagcoll::input::String in1(voc1);
- tagcoll::input::String in2(voc2);
-
- ept::debtags::VocabularyMerger vm;
-
- // Read and merge the two vocabulary samples
- vm.read(in1);
- vm.read(in2);
-
- // Write the merged vocabulary to /dev/null (but generate offsets and indexes in the meantime)
- vm.write("/dev/null");
-
- // Create the facet index
- char facetIndex[vm.facetIndexer().encodedSize()];
- vm.facetIndexer().encode(facetIndex);
-
- // Create the tag index
- char tagIndex[vm.tagIndexer().encodedSize()];
- vm.tagIndexer().encode(tagIndex);
-
- // Check that the facet names have been encoded correctly and in order
- assert_eq(string(indexref(facetIndex, 0) + 4*sizeof(int)), "smell");
- assert_eq(string(indexref(facetIndex, 1) + 4*sizeof(int)), "taste");
-
- // Check the first and last tag indexes for the facets
- assert_eq(((int*)indexref(facetIndex, 0))[2], 0);
- assert_eq(((int*)indexref(facetIndex, 0))[3], 1);
- assert_eq(((int*)indexref(facetIndex, 1))[2], 2);
- assert_eq(((int*)indexref(facetIndex, 1))[3], 3);
-
- // Check that the tag names have been encoded correctly and in order
- assert_eq(string(indexref(tagIndex, 0) + 3*sizeof(int)), "smell::fresh");
- assert_eq(string(indexref(tagIndex, 1) + 3*sizeof(int)), "smell::mold");
- assert_eq(string(indexref(tagIndex, 2) + 3*sizeof(int)), "taste::salty");
- assert_eq(string(indexref(tagIndex, 3) + 3*sizeof(int)), "taste::sweet");
-
- // Check the facet indexes for the tags
- assert_eq(((int*)indexref(tagIndex, 0))[2], 0);
- assert_eq(((int*)indexref(tagIndex, 1))[2], 0);
- assert_eq(((int*)indexref(tagIndex, 2))[2], 1);
- assert_eq(((int*)indexref(tagIndex, 3))[2], 1);
-}
-
-// Test parsing a vocabulary with a tag without a defined facet
- Test _2()
-{
- string voc =
- "Tag: foo::bar\n"
- "Description: Tag without facet\n"
- " VocabularyMerged should behave fine in this case.\n\n";
- tagcoll::input::String in(voc);
-
- ept::debtags::VocabularyMerger vm;
- vm.read(in);
-
- // Write the merged vocabulary to /dev/null (but generate offsets and indexes in the meantime)
- vm.write("/dev/null");
-
- // Create the facet index
- char facetIndex[vm.facetIndexer().encodedSize()];
- vm.facetIndexer().encode(facetIndex);
-
- // Create the tag index
- char tagIndex[vm.tagIndexer().encodedSize()];
- vm.tagIndexer().encode(tagIndex);
-}
-
-// Test parsing a vocabulary with a facet without tags
- Test _3()
-{
- string voc =
- "Facet: empty\n"
- "Description: Facet without tags\n"
- " VocabularyMerged used to segfault in this case.\n\n";
- tagcoll::input::String in(voc);
-
- ept::debtags::VocabularyMerger vm;
- vm.read(in);
-
- // Write the merged vocabulary to /dev/null (but generate offsets and indexes in the meantime)
- vm.write("/dev/null");
-
- // Create the facet index
- char facetIndex[vm.facetIndexer().encodedSize()];
- vm.facetIndexer().encode(facetIndex);
-
- // Create the tag index
- char tagIndex[vm.tagIndexer().encodedSize()];
- vm.tagIndexer().encode(tagIndex);
-}
-
-};
-// vim:set ts=4 sw=4:
diff --git a/ept/debtags/tag.cc b/ept/debtags/tag.cc
deleted file mode 100644
index 09392e9..0000000
--- a/ept/debtags/tag.cc
+++ /dev/null
@@ -1,138 +0,0 @@
-/* -*- C++ -*-
- * Copyright (C) 2005,2006 Enrico Zini <enrico@debian.org>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- */
-
-#include <ept/debtags/tag.h>
-#include <ept/debtags/vocabulary.h>
-#include <stdexcept>
-
-namespace ept {
-namespace debtags {
-
-static inline std::string constget(const std::map<std::string, std::string>& m,
- const std::string& key)
-{
- std::map<std::string, std::string>::const_iterator i = m.find(key);
- if (i == m.end())
- return std::string();
- else
- return i->second;
-}
-
-std::string Facet::name() const
-{
- if (valid())
- return m_tags->facetName(m_id);
- throw std::out_of_range( "No name for this facet" );
-}
-std::string Facet::name(const std::string& d) const
-{
- return valid() ? m_tags->facetName(m_id) : d;
-}
-
-std::string Facet::shortDescription() const
-{
- if (valid())
- return constget(m_tags->facetData(m_id), "_SD_");
- throw std::out_of_range( "No short description for this facet" );
-}
-std::string Facet::shortDescription(const std::string& d) const
-{
- return valid() ? constget(m_tags->facetData(m_id), "_SD_") : d;
-}
-
-std::string Facet::longDescription() const
-{
- if (valid())
- return constget(m_tags->facetData(m_id), "Description");
- throw std::out_of_range( "No long description for this facet" );
-}
-std::string Facet::longDescription(const std::string& d) const
-{
- return valid() ? constget(m_tags->facetData(m_id), "Description") : d;
-}
-
-bool Facet::hasTag(const std::string& name) const
-{
- if (!valid())
- throw std::out_of_range( "hasTag() called on an invalid facet" );
- return m_tags->hasTag(this->name() + "::" + name);
-}
-
-std::set< Tag > Facet::tags() const
-{
- if (!valid())
- throw std::out_of_range( "tags() called on an invalid facet" );
- return m_tags->tags(m_id);
-}
-
-
-Facet Tag::facet() const
-{
- if (valid())
- return m_tags->facetByTag(m_id);
- throw std::out_of_range( "No facet for this tag" );
-}
-
-std::string Tag::name() const
-{
- if (valid())
- return m_tags->tagShortName(m_id);
- throw std::out_of_range( "No name for this tag" );
-}
-std::string Tag::name(const std::string& d) const
-{
- return valid() ? m_tags->tagShortName(m_id) : d;
-}
-
-std::string Tag::fullname() const
-{
- if (valid())
- return m_tags->tagName(m_id);
- throw std::out_of_range( "No full name for this tag" );
-}
-std::string Tag::fullname(const std::string& d) const
-{
- return valid() ? m_tags->tagName(m_id) : d;
-}
-
-std::string Tag::shortDescription() const
-{
- if (valid())
- return constget(m_tags->tagData(m_id), "_SD_");
- throw std::out_of_range( "No short description for this tag" );
-}
-std::string Tag::shortDescription(const std::string& d) const
-{
- return valid() ? constget(m_tags->tagData(m_id), "_SD_") : d;
-}
-
-std::string Tag::longDescription() const
-{
- if (valid())
- return constget(m_tags->tagData(m_id), "Description");
- throw std::out_of_range( "No long description for this tag" );
-}
-std::string Tag::longDescription(const std::string& d) const
-{
- return valid() ? constget(m_tags->tagData(m_id), "Description") : d;
-}
-
-}
-}
-
-// vim:set ts=3 sw=3:
diff --git a/ept/debtags/tag.h b/ept/debtags/tag.h
deleted file mode 100644
index bb7488f..0000000
--- a/ept/debtags/tag.h
+++ /dev/null
@@ -1,251 +0,0 @@
-// -*- C++ -*-
-#ifndef EPT_DEBTAGS_TAG_H
-#define EPT_DEBTAGS_TAG_H
-
-/** \file
- * Debtags facets and tags
- */
-
-/*
- * Copyright (C) 2005,2006,2007 Enrico Zini <enrico@debian.org>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- */
-
-#include <set>
-#include <string>
-
-namespace ept {
-namespace debtags {
-
-class Vocabulary;
-
-class Tag;
-
-/**
- * Representation of a facet.
- *
- * ept::debtags::Facet represents a Facet with all its informations.
- * It is guaranteed to have fast value-copy semantics, so it can be passed
- * around freely and efficiently without worrying about memory management
- * issues.
- *
- * The class is normally instantiated using a Vocabulary:
- * \code
- * Facet facet = vocabulary.faceByName("made-of");
- * \endcode
- *
- * Facets can contain an "invalid" value, in which case using any of their
- * methods will likely produce segfault. The "invalid" facets are useful as
- * "none" return values:
- *
- * \code
- * Facet facet = vocabulary.facetByName("made-of");
- * if (!facet)
- * throw SomeException("facet \"made-of\" has not been defined");
- * \endcode
- */
-class Facet
-{
-protected:
- const Vocabulary* m_tags;
- int m_id;
-
- Facet(const Vocabulary* tags, int id) : m_tags(tags), m_id(id) {}
-
-public:
- Facet() : m_tags(0), m_id(-1) {}
- ~Facet() {}
-
- bool operator==(const Facet& f) const { return m_id == f.m_id; }
- bool operator!=(const Facet& f) const { return m_id != f.m_id; }
- bool operator<(const Facet& f) const { return m_id < f.m_id; }
-
- /**
- * Return true if the facet is valid
- */
- operator bool() const { return m_id != -1; }
- bool valid() const { return m_id != -1; }
-
- /**
- * Return the name of the facet
- * @throws std::out_of_range if the facet is not valid
- */
- std::string name() const;
- /**
- * Return the name of the facet
- *
- * Returns d if the facet is not valid.
- */
- std::string name(const std::string& d) const;
-
- /**
- * Return the short description of the facet
- * @throws std::out_of_range if the facet is not valid
- */
- std::string shortDescription() const;
- /**
- * Return the short description of the facet
- *
- * Returns d if the facet is not valid.
- */
- std::string shortDescription(const std::string& d) const;
-
- /**
- * Return the long description of the facet
- * @throws std::out_of_range if the facet is not valid
- */
- std::string longDescription() const;
- /**
- * Return the long description of the facet
- *
- * Returns d if the facet is not valid.
- */
- std::string longDescription(const std::string& d) const;
-
- /**
- * Return true if the facet has a tag with the given name (name, not fullname)
- */
- bool hasTag(const std::string& name) const;
-
- /**
- * Return the list of tags in this facet
- */
- std::set<Tag> tags() const;
-
- /**
- * Return the ID of this facet
- *
- * @warning This method is exported to help in writing tests, but it is not
- * part of the normal API: do not use it, because future implementations may
- * not be based on IDs and therefore not have this method.
- */
- int id() const { return m_id; }
-
- friend class Vocabulary;
-};
-
-/**
- * Representation of a tag.
- *
- * ept::debtags::Tag represents a Tag with all its informations.
- * It is guaranteed to have fast value-copy semantics, so it can be passed
- * around freely and efficiently without worrying about memory management
- * issues.
- *
- * The class is normally instantiated using a Vocabulary:
- * \code
- * Tag tag = vocabulary.tagByName("made-of::lang:c++");
- * \endcode
- *
- * Tags can contain an "invalid" value, in which case using any of their
- * methods will likely produce segfault. The "invalid" facets are useful as
- * "none" return values:
- *
- * \code
- * Tag tag = vocabulary.tagByName("made-of");
- * if (!tag)
- * throw SomeException("tag \"mytag\" has not been defined");
- * \endcode
- */
-class Tag
-{
-protected:
- const Vocabulary* m_tags;
- int m_id;
-
- Tag(const Vocabulary* tags, int id) : m_tags(tags), m_id(id) {}
-
-public:
- typedef std::set< Tag > Set;
-
- Tag() : m_tags(0), m_id(-1) {}
- ~Tag() {}
-
- bool operator==(const Tag& f) const { return m_id == f.m_id; }
- bool operator!=(const Tag& f) const { return m_id != f.m_id; }
- bool operator<(const Tag& f) const { return m_id < f.m_id; }
-
- operator bool() const { return m_id != -1; }
- bool valid() const { return m_id != -1; }
-
- Facet facet() const;
-
- /**
- * Return the name of the tag, without the facet:: prefix
- * @throws std::out_of_range if the tag is not valid
- */
- std::string name() const;
- /**
- * Return the short description of the tag
- *
- * Returns d if the tag is not valid.
- */
- std::string name(const std::string& d) const;
-
- /**
- * Return the name of the tag, with the facet:: prefix
- * @throws std::out_of_range if the tag is not valid
- */
- std::string fullname() const;
- /**
- * Return the short description of the tag
- *
- * Returns d if the tag is not valid.
- */
- std::string fullname(const std::string& d) const;
-
- /**
- * Return the short description of the tag
- * @throws std::out_of_range if the tag is not valid
- */
- std::string shortDescription() const;
- /**
- * Return the short description of the tag
- *
- * Returns d if the tag is not valid.
- */
- std::string shortDescription(const std::string& d) const;
-
- /**
- * Return the long description of the tag
- *
- * @throws std::out_of_range if the tag is not valid
- */
- std::string longDescription() const;
- /**
- * Return the long description of the tag
- *
- * Returns d if the tag is not valid.
- */
- std::string longDescription(const std::string& d) const;
-
- /**
- * Return the ID of this tag
- *
- * @warning This method is exported to help in writing tests, but it is not
- * part of the normal API: do not use it, because future implementations may
- * not be based on IDs and therefore not have this method.
- */
- int id() const { return m_id; }
-
- friend class Vocabulary;
-};
-
-}
-}
-
-// vim:set ts=3 sw=3:
-#endif
diff --git a/ept/debtags/tag.test.h b/ept/debtags/tag.test.h
deleted file mode 100644
index 998147d..0000000
--- a/ept/debtags/tag.test.h
+++ /dev/null
@@ -1,107 +0,0 @@
-/*
- * Copyright (C) 2005,2007 Enrico Zini <enrico@debian.org>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- */
-
-#if 0
-#include <ept/tests/test-utils.h>
-#include <ept/debtags/tag.h>
-#include <ept/debtags/vocabulary.h>
-#include <ept/debtags/maint/path.h>
-
-#include <tagcoll/utils/set.h>
-
-using namespace std;
-using namespace ept::debtags;
-
-namespace tut {
-
-struct ept_debtags_tag_shar
-{
- Path::OverrideDebtagsSourceDir odsd;
- Path::OverrideDebtagsIndexDir odid;
- Path::OverrideDebtagsUserSourceDir odusd;
- Path::OverrideDebtagsUserIndexDir oduid;
- Vocabulary voc;
-
- ept_debtags_tag_shar()
- : odsd("./"), odid("./"), odusd("./"), oduid("./") {}
-};
-
-TESTGRP( ept_debtags_tag );
-
-template<> template<>
-void to::test<1>()
-{
- Tag a, b;
- ensure( a == b );
- ensure( !a.valid() );
- ensure( !b.valid() );
-}
-
-template<> template<>
-void to::test<2>()
-{
- Tag a;
- int x = 1;
- try {
- a.shortDescription();
- x = 2;
- } catch (...) {
- x = 3;
- }
- ensure_equals( x, 3 );
-}
-
-template<> template<>
-void to::test< 3 >()
-{
- Facet f = voc.facetByName( "works-with" );
- Tag t = voc.tagByName( "works-with::people" );
- ensure( t.valid() );
- ensure( f.valid() );
- ensure( t.facet() == f );
- ensure( tagcoll::utils::set_contains(f.tags(), t) );
-}
-
-template<> template<>
-void to::test< 4 >()
-{
- Facet f = voc.facetByName( "works-with" );
- Tag t = voc.tagByName( "works-with::people" );
- ensure( t.valid() );
- ensure( f.valid() );
- ensure( f.hasTag( t.name() ) );
-}
-
-template<> template<>
-void to::test< 5 >()
-{
- Tag t = voc.tagByName( "works-with::people" );
- ensure( t.valid() );
- ensure( t.facet().hasTag( t.name() ) );
- ensure( tagcoll::utils::set_contains(t.facet().tags(), t) );
-}
-
-}
-
-/*
-#include <ept/cache/tag.tcc>
-#include <ept/cache/debtags/vocabulary.tcc>
-*/
-
-// vim:set ts=3 sw=3:
-#endif
diff --git a/ept/debtags/vocabulary.cc b/ept/debtags/vocabulary.cc
index 7f3a6b7..25887fa 100644
--- a/ept/debtags/vocabulary.cc
+++ b/ept/debtags/vocabulary.cc
@@ -39,6 +39,52 @@ using namespace tagcoll;
namespace ept {
namespace debtags {
+namespace voc {
+std::string Data::shortDescription() const
+{
+ if (m_desc.empty())
+ {
+ string d = longDescription();
+ if (d.empty()) return d;
+ size_t pos = d.find('\n');
+ if (pos == std::string::npos)
+ m_desc = d;
+ else
+ m_desc = d.substr(0, pos);
+ }
+ return m_desc;
+}
+
+std::string Data::longDescription() const
+{
+ const_iterator i = find("Description");
+ if (i == end()) return std::string();
+ return i->second;
+}
+
+bool FacetData::hasTag(const std::string& name) const
+{
+ return m_tags.find(name) != m_tags.end();
+}
+
+const TagData* FacetData::tagData(const std::string& name) const
+{
+ std::map<std::string, voc::TagData>::const_iterator i = m_tags.find(name);
+ if (i == m_tags.end()) return 0;
+ return &i->second;
+}
+
+std::set<std::string> FacetData::tags() const
+{
+ std::set<std::string> res;
+ for (std::map<std::string, voc::TagData>::const_iterator i = m_tags.begin();
+ i != m_tags.end(); ++i)
+ res.insert(i->first);
+ return res;
+}
+
+}
+
static inline std::string getfacet(const std::string& tagname)
{
size_t p = tagname.find("::");
@@ -67,11 +113,11 @@ Vocabulary::~Vocabulary()
voc::TagData& voc::FacetData::obtainTag(const std::string& name)
{
- std::map<std::string, voc::TagData>::iterator i = tags.find(name);
- if (i == tags.end())
+ std::map<std::string, voc::TagData>::iterator i = m_tags.find(name);
+ if (i == m_tags.end())
{
// Create the tag if it's missing
- pair<std::map<std::string, TagData>::iterator, bool> res = tags.insert(make_pair<std::string, TagData>(name, TagData()));
+ pair<std::map<std::string, TagData>::iterator, bool> res = m_tags.insert(make_pair<std::string, TagData>(name, TagData()));
i = res.first;
i->second.name = name;
}
@@ -93,15 +139,7 @@ voc::FacetData& Vocabulary::obtainFacet(const std::string& name)
voc::TagData& Vocabulary::obtainTag(const std::string& fullname)
{
- size_t p = fullname.find("::");
- if (p == string::npos)
- {
- voc::FacetData& facet = obtainFacet("legacy");
- return facet.obtainTag(fullname);
- } else {
- voc::FacetData& facet = obtainFacet(fullname.substr(0, p));
- return facet.obtainTag(fullname.substr(p + 2));
- }
+ return obtainFacet(getfacet(fullname)).obtainTag(fullname);
}
@@ -115,7 +153,7 @@ bool Vocabulary::hasTag(const std::string& name) const
{
const voc::FacetData* f = facetData(getfacet(name));
if (!f) return false;
- return f->tags.find(name) != f->tags.end();
+ return f->hasTag(name);
}
const voc::FacetData* Vocabulary::facetData(const std::string& name) const
@@ -131,10 +169,7 @@ const voc::TagData* Vocabulary::tagData(const std::string& tagname) const
const voc::FacetData* f = facetData(getfacet(tagname));
if (!f) return 0;
- std::map<std::string, voc::TagData>::const_iterator i = f->tags.find(tagname);
- if (i == f->tags.end()) return 0;
-
- return &i->second;
+ return f->tagData(tagname);
}
std::set<std::string> Vocabulary::facets() const
@@ -151,21 +186,17 @@ std::set<std::string> Vocabulary::tags() const
std::set<std::string> res;
for (std::map<std::string, voc::FacetData>::const_iterator i = m_facets.begin();
i != m_facets.end(); ++i)
- for (std::map<std::string, voc::TagData>::const_iterator j = i->second.tags.begin();
- j != i->second.tags.end(); ++j)
+ for (std::map<std::string, voc::TagData>::const_iterator j = i->second.m_tags.begin();
+ j != i->second.m_tags.end(); ++j)
res.insert(j->first);
return res;
}
std::set<std::string> Vocabulary::tags(const std::string& facet) const
{
- std::set<std::string> res;
const voc::FacetData* f = facetData(facet);
- if (!f) return res;
- for (std::map<std::string, voc::TagData>::const_iterator i = f->tags.begin();
- i != f->tags.end(); ++i)
- res.insert(i->first);
- return res;
+ if (!f) return std::set<std::string>();
+ return f->tags();
}
void Vocabulary::read(tagcoll::input::Input& input)
@@ -309,8 +340,8 @@ void Vocabulary::write(FILE* out)
writeDebStyleField(out, j->first, j->second);
fputc('\n', out);
- for (std::map<std::string, voc::TagData>::iterator t = f->second.tags.begin();
- t != f->second.tags.end(); t++)
+ for (std::map<std::string, voc::TagData>::iterator t = f->second.m_tags.begin();
+ t != f->second.m_tags.end(); t++)
{
//fprintf(stderr, "Writing tag %.*s\n", PFSTR(t->first));
writeDebStyleField(out, "Tag", f->first + "::" + t->first);
diff --git a/ept/debtags/vocabulary.h b/ept/debtags/vocabulary.h
index 59b4905..c126539 100644
--- a/ept/debtags/vocabulary.h
+++ b/ept/debtags/vocabulary.h
@@ -24,11 +24,9 @@
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
-#include <ept/debtags/tag.h>
-#include <tagcoll/diskindex/mmap.h>
-
#include <string>
#include <vector>
+#include <set>
#include <map>
namespace tagcoll {
@@ -41,23 +39,106 @@ namespace ept {
namespace debtags {
namespace voc {
-class TagData : public std::map<std::string, std::string>
+/// Base class for facet and tag data
+struct Data : public std::map<std::string, std::string>
{
+protected:
+ // Cache the parsed short description
+ mutable std::string m_desc;
+
public:
std::string name;
+ /**
+ * Return the short description of the tag
+ * @throws std::out_of_range if the tag is not valid
+ */
+ std::string shortDescription() const;
+
+ /**
+ * Return the long description of the tag
+ *
+ * @throws std::out_of_range if the tag is not valid
+ */
+ std::string longDescription() const;
+};
+
+/**
+ * Representation of a tag.
+ *
+ * ept::debtags::Tag represents a Tag with all its informations.
+ * It is guaranteed to have fast value-copy semantics, so it can be passed
+ * around freely and efficiently without worrying about memory management
+ * issues.
+ *
+ * The class is normally instantiated using a Vocabulary:
+ * \code
+ * Tag tag = vocabulary.tagByName("made-of::lang:c++");
+ * \endcode
+ *
+ * Tags can contain an "invalid" value, in which case using any of their
+ * methods will likely produce segfault. The "invalid" facets are useful as
+ * "none" return values:
+ *
+ * \code
+ * Tag tag = vocabulary.tagByName("made-of");
+ * if (!tag)
+ * throw SomeException("tag \"mytag\" has not been defined");
+ * \endcode
+ */
+struct TagData : public Data
+{
TagData() {}
+
+ // Facet facet() const;
};
-class FacetData : public std::map<std::string, std::string>
+/**
+ * Representation of a facet.
+ *
+ * ept::debtags::Facet represents a Facet with all its informations.
+ * It is guaranteed to have fast value-copy semantics, so it can be passed
+ * around freely and efficiently without worrying about memory management
+ * issues.
+ *
+ * The class is normally instantiated using a Vocabulary:
+ * \code
+ * Facet facet = vocabulary.faceByName("made-of");
+ * \endcode
+ *
+ * Facets can contain an "invalid" value, in which case using any of their
+ * methods will likely produce segfault. The "invalid" facets are useful as
+ * "none" return values:
+ *
+ * \code
+ * Facet facet = vocabulary.facetByName("made-of");
+ * if (!facet)
+ * throw SomeException("facet \"made-of\" has not been defined");
+ * \endcode
+ */
+class FacetData : public Data
{
public:
- std::string name;
- std::map<std::string, TagData> tags;
+ std::map<std::string, TagData> m_tags;
FacetData() {}
TagData& obtainTag(const std::string& fullname);
+
+ /**
+ * Return true if the facet has a tag with the given name (name, not fullname)
+ */
+ bool hasTag(const std::string& name) const;
+
+ /**
+ * Return the tag data for the given tag, or 0 if not found
+ */
+ const TagData* tagData(const std::string& name) const;
+
+ /**
+ * Return the list of tags in this facet
+ */
+ std::set<std::string> tags() const;
};
}
diff --git a/ept/debtags/vocabulary.test.h b/ept/debtags/vocabulary.test.h
index 977eef5..a6ed1b8 100644
--- a/ept/debtags/vocabulary.test.h
+++ b/ept/debtags/vocabulary.test.h
@@ -20,19 +20,11 @@
#include <wibble/test.h>
#include <ept/debtags/vocabulary.h>
-#include <ept/debtags/maint/vocabularymerger.h>
#include <ept/debtags/maint/path.h>
#include <tagcoll/utils/set.h>
#include <tagcoll/input/stdio.h>
-#include "debtags.test.h"
-
-// This is not exported by default
-namespace ept {
-namespace debtags {
-int tagcmp(const char* tag1, const char* tag2);
-}
-}
+#include "ept/test.h"
using namespace std;
using namespace tagcoll::utils;
@@ -62,11 +54,11 @@ struct TestVocabulary : DebtagsTestEnvironment
Test _4()
{
- Tag people = tags().tagByName( "works-with::people" ),
- midgets = tags().tagByName( "works-with::midgets" ),
- blahg = tags().tagByName( "works-with::blahg" ),
- text = tags().tagByName( "works-with::text" ),
- people2 = tags().tagByName( "works-with::people" );
+ const voc::TagData *people = tags().tagData( "works-with::people" ),
+ *midgets = tags().tagData( "works-with::midgets" ),
+ *blahg = tags().tagData( "works-with::blahg" ),
+ *text = tags().tagData( "works-with::text" ),
+ *people2 = tags().tagData( "works-with::people" );
assert( people != midgets );
assert( people != text );
assert( people != blahg );
@@ -78,11 +70,11 @@ struct TestVocabulary : DebtagsTestEnvironment
Test _5()
{
- Tag a = tags().tagByName( "works-with::people" ),
- b = tags().tagByName( "works-with::midgets" );
- std::set< Tag > s = tags().tags(),
- f = tags().tags( "works-with" ),
- n = tags().tags( "nonsense" );
+ std::string a = "works-with::people",
+ b = "works-with::midgets";
+ std::set<std::string> s = tags().tags(),
+ f = tags().tags( "works-with" ),
+ n = tags().tags( "nonsense" );
assert( set_contains(s, a) );
assert( set_contains(f, a) );
assert( set_contains(s, f) );
@@ -93,38 +85,34 @@ struct TestVocabulary : DebtagsTestEnvironment
Test _6()
{
- Facet f = tags().facetByName( "works-with" );
- Tag t = tags().tagByName( "works-with::people" );
- assert_eq(f.name(), "works-with");
- assert_eq(t.name(), "people");
- assert_eq(t.fullname(), "works-with::people");
+ const voc::FacetData* f = tags().facetData( "works-with" );
+ assert(f);
+ assert_eq(f->name, "works-with");
+
+ const voc::TagData* t = tags().tagData( "works-with::people" );
+ assert(t);
+ assert_eq(t->name, "works-with::people");
}
Test _7()
{
- Facet f = tags().facetByName( "works-with" );
- std::set< Tag > x = tags().tags( "works-with" );
- assert( x == f.tags() );
+ const voc::FacetData* f = tags().facetData( "works-with" );
+ std::set<std::string> x = tags().tags( "works-with" );
+ assert( x == f->tags() );
}
Test _8()
{
- Facet f = tags().facetByName( "does-not-work-with" );
- int x = 1;
- try {
- f.tags();
- x = 2;
- } catch (...) {
- x = 3;
- }
- assert_eq( x, 3 );
+ const voc::FacetData* f = tags().facetData( "does-not-work-with" );
+ assert(!f);
}
Test _9()
{
- Facet f = tags().facetByName( "legacy" );
- assert_eq(f.shortDescription(), "");
- assert_eq(f.longDescription(), "");
+ const voc::FacetData* f = tags().facetData( "legacy" );
+ assert(f);
+ assert_eq(f->shortDescription(), "");
+ assert_eq(f->longDescription(), "");
//assert_eq(f.shortDescription( "weehee" ), "weehee");
}
@@ -136,31 +124,26 @@ struct TestVocabulary : DebtagsTestEnvironment
Test _11()
{
- // assert that all tags are somehow working
- std::set<Facet> facets = tags().facets();
+ // assert that all facets are somehow working
+ std::set<std::string> facets = tags().facets();
- for (std::set<Facet>::const_iterator i = facets.begin();
+ for (std::set<std::string>::const_iterator i = facets.begin();
i != facets.end(); i++)
{
- i->name(string("foo"));
- i->shortDescription(string("foo"));
- i->longDescription(string("foo"));
- i->tags();
+ const voc::FacetData* f = tags().facetData(*i);
+ assert(f);
}
}
Test _12()
{
// assert that all tags are somehow working
- std::set<Tag> tags = this->tags().tags();
-
- for (std::set<Tag>::const_iterator i = tags.begin();
+ std::set<std::string> tags = this->tags().tags();
+ for (std::set<std::string>::const_iterator i = tags.begin();
i != tags.end(); i++)
{
- i->name(string("foo"));
- i->fullname(string("foo"));
- i->shortDescription(string("foo"));
- i->longDescription(string("foo"));
+ const voc::TagData* t = this->tags().tagData(*i);
+ assert(t);
}
}
@@ -169,126 +152,57 @@ struct TestVocabulary : DebtagsTestEnvironment
{
Vocabulary& tags = this->tags();
- Tag first = tags.tagByName("accessibility::TODO");
- assert(first != Tag());
- assert_eq(first.fullname(), string("accessibility::TODO"));
- assert_eq(first.name(), string("TODO"));
- assert_eq(first.shortDescription(), string("Need an extra tag"));
-
- Tag last = tags.tagByName("x11::xserver");
- assert(last != Tag());
- assert_eq(last.fullname(), string("x11::xserver"));
- assert_eq(last.name(), string("xserver"));
- assert_eq(last.shortDescription(), string("X Server"));
+ const voc::TagData* first = tags.tagData("accessibility::TODO");
+ assert(first);
+ assert_eq(first->name, string("accessibility::TODO"));
+ assert_eq(first->shortDescription(), string("Need an extra tag"));
+
+ const voc::TagData* last = tags.tagData("x11::xserver");
+ assert(last);
+ assert_eq(last->name, string("x11::xserver"));
+ assert_eq(last->shortDescription(), string("X Server"));
}
Test _14()
{
// assert that it's possible to go from facet to ID and back
- std::set<Facet> facets = tags().facets();
-
- for (std::set<Facet>::const_iterator i = facets.begin();
- i != facets.end(); i++)
- {
- Facet f = tags().facetByID(i->id());
- assert_eq(*i, f);
- assert_eq(i->name(), f.name());
- assert_eq(i->shortDescription(), f.shortDescription());
- assert_eq(i->longDescription(), f.longDescription());
- assert_eq(i->tags().size(), f.tags().size());
- }
+ // we don't use IDs anymore
}
Test _15()
{
// assert that it's possible to go from tag to ID and back
- std::set<Tag> tags = this->tags().tags();
-
- for (std::set<Tag>::const_iterator i = tags.begin();
- i != tags.end(); i++)
- {
- Tag t = this->tags().tagByID(i->id());
- assert_eq(*i, t);
- assert_eq(i->name(), t.name());
- assert_eq(i->fullname(), t.fullname());
- assert_eq(i->shortDescription(), t.shortDescription());
- assert_eq(i->longDescription(), t.longDescription());
- }
+ // we don't use IDs anymore
}
Test _16()
{
// assert that facet IDs are distinct
- std::set<Facet> facets = tags().facets();
- std::set<int> ids;
- for (std::set<Facet>::const_iterator i = facets.begin();
- i != facets.end(); i++)
- ids.insert(i->id());
-
- assert_eq(facets.size(), ids.size());
+ // we don't use IDs anymore
}
Test _17()
{
// assert that tag IDs are distinct
- std::set<Tag> tags = this->tags().tags();
- std::set<int> ids;
- for (std::set<Tag>::const_iterator i = tags.begin();
- i != tags.end(); i++)
- ids.insert(i->id());
-
- assert_eq(tags.size(), ids.size());
+ // we don't use IDs anymore
}
Test _18()
{
// assert that all the tags are indexed
- ept::debtags::VocabularyMerger voc;
- tagcoll::input::Stdio in(ept::debtags::Path::vocabulary());
- voc.read(in);
- std::set<std::string> all = voc.tagNames();
- for (std::set<std::string>::const_iterator i = all.begin();
- i != all.end(); ++i)
- assert(this->tags().hasTag(*i));
-
- // There should be the same amount of tags in both
- std::set<Tag> allTags = this->tags().tags();
- assert_eq(all.size(), allTags.size());
+ // we don't use the index anymore
}
Test _19()
{
// test the tagcmp function
-
- // If unfaceted, same as strcmp
- assert(ept::debtags::tagcmp("antani", "blinda") < 0);
- assert(ept::debtags::tagcmp("blinda", "antani") > 0);
- assert_eq(ept::debtags::tagcmp("antani", "antani"), 0);
-
- // If the same and faceted, should work
- assert_eq(ept::debtags::tagcmp("antani::blinda", "antani::blinda"), 0);
-
- // With different facet names, work just as strcmp
- assert(ept::debtags::tagcmp("antani::blinda", "blinda::blinda") < 0);
- assert(ept::debtags::tagcmp("blinda::blinda", "antani::blinda") > 0);
- assert(ept::debtags::tagcmp("anta::blinda", "antani::blinda") < 0);
- assert(ept::debtags::tagcmp("antani::blinda", "anta::blinda") > 0);
- assert(ept::debtags::tagcmp("anta::blinda", "anta-ni::blinda") < 0);
- assert(ept::debtags::tagcmp("anta-ni::blinda", "anta::blinda") > 0);
-
- // With same facet names, work just as strcmp on the tags
- assert(ept::debtags::tagcmp("a::antani", "a::blinda") < 0);
- assert(ept::debtags::tagcmp("a::blinda", "a::antani") > 0);
- assert(ept::debtags::tagcmp("a::anta", "a::antani") < 0);
- assert(ept::debtags::tagcmp("a::antani", "a::anta") > 0);
- assert(ept::debtags::tagcmp("a::anta", "a::anta-ni") < 0);
- assert(ept::debtags::tagcmp("a::anta-ni", "a::anta") > 0);
+ // we don't have tagcmp anymore
}
Test _20()
{
// check that we're seeing all the tags for a facet
- std::set<Tag> t = tags().tags("accessibility");
+ std::set<std::string> t = tags().tags("accessibility");
assert_eq(t.size(), 10u);
t = tags().tags("works-with-format");
@@ -306,10 +220,10 @@ struct TestVocabulary : DebtagsTestEnvironment
assert(!empty.hasData());
- set<Facet> facets = empty.facets();
+ set<std::string> facets = empty.facets();
assert_eq(facets.size(), 0u);
- set<Tag> tags = empty.tags();
+ set<std::string> tags = empty.tags();
assert_eq(tags.size(), 0u);
}