73 const char * dbpath =
".stub/stubdb1";
98 const char * dbpath =
".stub/stubdb2";
111 #ifdef XAPIAN_HAS_REMOTE_BACKEND
122 #ifdef XAPIAN_HAS_REMOTE_BACKEND
142 #ifdef XAPIAN_HAS_REMOTE_BACKEND
143 # define EXPECTED_EXCEPTION Xapian::DatabaseOpeningError
145 # define EXPECTED_EXCEPTION Xapian::FeatureUnavailableError
150 out <<
"remote foo\n";
163 #ifdef XAPIAN_HAS_REMOTE_BACKEND
166 out <<
"remote [::1]:65535\n";
206 out <<
"remote [::1]\n";
224 mkdir(
".stub", 0755);
225 const char * dbpath =
".stub/stubdb3";
226 ofstream out(dbpath);
241 mkdir(
".stub", 0755);
242 const char * dbpath =
".stub/stubdb4";
243 ofstream out(dbpath);
245 out <<
"bad line here\n";
258 mkdir(
".stub", 0755);
259 const char * dbpath =
".stub/stubdb5";
260 ofstream out(dbpath);
275 mkdir(
".stub", 0755);
276 const char * dbpath =
".stub/stubdb6";
277 ofstream out(dbpath);
321 mkdir(
".stub", 0755);
322 const char * dbpath =
".stub/stubdb8";
323 ofstream out(dbpath);
330 FAIL_TEST(
"Managed to check inmemory stub");
334 "InMemory database checking not implemented");
346 <<
", count is now " << count <<
"\n";
350 MyErrorHandler() : count (0) {}
355 MyErrorHandler myhandler;
360 for (
int testcount = 0; testcount < 14; testcount ++) {
361 tout <<
"testcount=" << testcount <<
"\n";
443 tout <<
"db=" << dbs <<
"\n";
449 enquire.set_query(myquery);
451 tout <<
"query=" << myquery <<
"\n";
456 case 0:
case 3:
case 6:
case 9:
459 case 1:
case 4:
case 7:
case 10:
462 case 2:
case 5:
case 8:
case 11:
485 return doc.
get_data().find(needle) != string::npos;
512 for ( ; i != mymset.
end(); ++i) {
514 TEST(myfunctor(doc));
515 docid_checked[*i] =
true;
525 mymset = enquire.
get_mset(0, 0, 0, &myfunctor);
539 mymset = enquire.
get_mset(0, 1, 0, &myfunctor);
555 for (
Xapian::docid did = 1; did < docid_checked.size(); ++did) {
556 if (!docid_checked[did]) {
564 mymset = enquire.
get_mset(0, 1, 0, &myfunctor);
583 mymset = enquire.
get_mset(0, 1, 0, &myfunctor);
600 mymset = enquire.
get_mset(0, 1, 0, &myfunctor);
633 for ( ; i != mymset.
end(); ++i) {
635 TEST(myfunctor(doc));
636 docid_checked[*i] =
true;
640 for (
Xapian::docid did = 1; did < docid_checked.size(); ++did) {
641 if (!docid_checked[did]) {
848 "Had no fewer items when performing collapse: don't know whether it worked.");
850 map<string, Xapian::docid> values;
852 for ( ; i != mymset.
end(); ++i) {
854 TEST(values[value] == 0 || value.empty());
863 SKIP_TEST(
"Don't have a suitable database currently");
897 "Lower bound was not lower when performing collapse: don't know whether it worked.");
899 "Upper bound was not lower when performing collapse: don't know whether it worked.");
901 map<string, Xapian::docid> values;
903 for ( ; i != mymset.
end(); ++i) {
905 TEST(values[value] == 0 || value.empty());
923 map<string, Xapian::docid> values;
925 for ( ; i != mymset.
end(); ++i) {
927 TEST(values[value] == 0 || value.empty());
946 "Lower bound was not 1 when performing collapse but not asking for any results.");
948 "Upper bound was changed when performing collapse but not asking for any results.");
950 map<string, Xapian::docid> values;
952 for ( ; i != mymset.
end(); ++i) {
954 TEST(values[value] == 0 || value.empty());
965 for (
int i = 0; i < 10; ++i) {
996 tout <<
"*ati = '" << *ati <<
"'\n";
997 tout <<
"*ati.length = '" << (*ati).length() <<
"'\n";
998 tout <<
"*ati == \"one\" = " << (*ati ==
"one") <<
"\n";
999 tout <<
"*ati[3] = " << ((*ati)[3]) <<
"\n";
1000 tout <<
"*ati = '" << *ati <<
"'\n";
1002 TEST(*ati ==
"three");
1007 TEST(*ati2 ==
"one");
1016 TEST(*ati ==
"two");
1021 TEST(*ati2 ==
"three");
1037 TEST(*ati ==
"five");
1042 TEST(*ati ==
"four");
1047 TEST(*ati ==
"one");
1052 TEST(*ati ==
"six");
1057 TEST(*ati ==
"three");
1062 TEST(*ati ==
"two");
1075 ati.
skip_to(
string(
"zzzzzz"));
1161 for (m = mymset.
begin(); m != mymset.
end(); ++m) ++count;
1167 if (value_no == 0) {
1168 TEST(value.size() > 263);
1169 TEST_EQUAL(
static_cast<unsigned char>(value[262]), 255);
1170 for (
int k = 0; k < 256; ++k) {
1171 TEST_EQUAL(
static_cast<unsigned char>(value[k + 7]), k);
1180 for (m = mymset.
begin(); m != mymset.
end(); ++m) ++count;
1206 t.
skip_to(
string(
"big\0zero", 8));
1278 while (i != eset1.
end() && j != eset3.
end()) {
1287 bool eset1_eq_eset2 =
true;
1290 while (i != eset1.
end() && j != eset2.
end()) {
1292 eset1_eq_eset2 =
false;
1298 TEST(!eset1_eq_eset2);
1307 string s =
"let_us_see_if_we_can_break_it_with_a_really_really_long_term.";
1308 for (
int i = 0; i < 8; ++i) {
1338 vector<Xapian::docid> v(p, pend);
1342 vector<Xapian::docid>::const_iterator i;
1343 for (i = v.begin(); i != v.end(); ++i) {
1442 for (
int pass = 1; pass <= 2; ++pass) {
1444 tout <<
"Sorting on value " << value_no <<
'\n';
1454 j = allbset.
begin();
1455 for (i = partbset1.
begin(); i != partbset1.
end(); ++i) {
1456 tout <<
"Entry " << n <<
": " << *i <<
" | " << *j <<
'\n';
1458 if (*i != *j) ok =
false;
1463 for (i = partbset2.
begin(); i != partbset2.
end(); ++i) {
1464 tout <<
"Entry " << n <<
": " << *i <<
" | " << *j <<
'\n';
1466 if (*i != *j) ok =
false;
1472 FAIL_TEST(
"Split msets aren't consistent with unsplit");
1495 min(start + size, bigmset.
size()));
1503 bigmset[start + i].get_weight());
1516 #ifdef XAPIAN_HAS_CHERT_BACKEND
1517 mkdir(
".chert", 0755);
1526 mkdir(
".chert/emptydirectory", 0700);
1531 touch(
".chert/somefile");
1554 #ifdef XAPIAN_HAS_GLASS_BACKEND
1555 mkdir(
".glass", 0755);
1564 mkdir(
".glass/emptydirectory", 0700);
1569 touch(
".glass/somefile");
1601 string empty_dir =
"emptydirectory";
1602 mkdir(empty_dir.c_str(), 0700);
1609 #ifdef XAPIAN_HAS_CHERT_BACKEND
1610 const string dbdir =
".chert/test_chertdatabaseopen1";
1611 mkdir(
".chert", 0755);
1678 static const Xapian::docid order1[] = { 1,2,3,4,5,6,7,8,9 };
1679 static const Xapian::docid order2[] = { 2,1,3,6,5,4,7,9,8 };
1680 static const Xapian::docid order3[] = { 3,2,1,6,5,4,9,8,7 };
1681 static const Xapian::docid order4[] = { 7,8,9,4,5,6,1,2,3 };
1682 static const Xapian::docid order5[] = { 9,8,7,6,5,4,3,2,1 };
1683 static const Xapian::docid order6[] = { 7,9,8,6,5,4,2,1,3 };
1684 static const Xapian::docid order7[] = { 7,9,8,6,5,4,2,1,3 };
1685 static const Xapian::docid order8[] = { 2,6,7,1,5,9,3,4,8 };
1686 static const Xapian::docid order9[] = { 7,6,2,9,5,1,8,4,3 };
1693 for (i = 0; i <
sizeof(order1) /
sizeof(
Xapian::docid); ++i) {
1701 for (i = 0; i <
sizeof(order2) /
sizeof(
Xapian::docid); ++i) {
1709 for (i = 0; i <
sizeof(order1) /
sizeof(
Xapian::docid); ++i) {
1718 for (i = 0; i <
sizeof(order2) /
sizeof(
Xapian::docid); ++i) {
1727 for (i = 0; i <
sizeof(order3) /
sizeof(
Xapian::docid); ++i) {
1735 for (i = 0; i <
sizeof(order4) /
sizeof(
Xapian::docid); ++i) {
1743 for (i = 0; i <
sizeof(order5) /
sizeof(
Xapian::docid); ++i) {
1751 for (i = 0; i <
sizeof(order6) /
sizeof(
Xapian::docid); ++i) {
1759 for (i = 0; i <
sizeof(order7) /
sizeof(
Xapian::docid); ++i) {
1767 for (i = 0; i <
sizeof(order8) /
sizeof(
Xapian::docid); ++i) {
1775 for (i = 0; i <
sizeof(order8) /
sizeof(
Xapian::docid); ++i) {
1783 for (i = 0; i <
sizeof(order9) /
sizeof(
Xapian::docid); ++i) {
1791 for (i = 0; i <
sizeof(order9) /
sizeof(
Xapian::docid); ++i) {
1799 static const struct {
Xapian::docid did;
const char* text; } content[] = {
1800 {1,
"This is a test document used with the API test. This paragraph "
1801 "must be at least three lines (including the blank line) to be "
1802 "counted as a \"paragraph\"."},
1803 {2,
"This is a second simple data test, used to test multiple "
1804 "(inmemory anyway) databases. The text in this file is "
1805 "unimportant, although I suppose it ought to include the "
1806 "standard word \"word\" in a few places."},
1807 {3,
"This file will be indexed by paragraph, and the simple query will "
1808 "search for the word \"word\". Well expect the mset to contain "
1809 "two documents, including this paragraph and the fourth, below. "
1810 "Since this paragraph uses the word \"word\" so much, this "
1811 "should be the first one in the match set. Ill just say the word "
1812 "a few more times (word!) to make sure of that. If this doesnt "
1813 "word (typo, I meant work), then there may be fourletter words "
1815 {4,
"Ill leave this at two paragraphs. This one hasnt got any useful "
1816 "information in it either."},
1817 {5,
"This paragraph only has a load of absolute rubbish, and nothing "
1818 "of any use whatsoever."},
1819 {7,
"This is the other paragraph with the word in the simple query "
1820 "in it. For simplicity, all paragraphs are at least two lines, "
1821 "due to how the hacked up indexer works."},
1822 {9,
"This is another paragraph which wont be returned. Well, not "
1823 "with the simple query, anyway."},
1824 {11,
"And yet another. This one does mention banana splits, though, "
1825 "so cant be that bad."}
1832 for (
auto& i : content) {
1844 static const char *
const words[] = {
"paragraph",
"word" };
1846 const size_t MSET_SIZE = 10;
1864 static const pair<Xapian::docid, double> to_compare[] = {
1865 {7, 1.445962071042388164},
1866 {3, 1.4140112748017070743},
1867 {1, 1.3747698831232337824},
1868 {5, 1.1654938419498412916},
1869 {9, 1.1654938419498412916},
1870 {4, 1.1543806706320836053},
1871 {2, 0.12268031290495594321}
1886 void init(
double factor)
override {
1887 scale_factor = factor;
1891 std::string
name()
const override {
return "MyWeight"; }
1899 return scale_factor;
1916 static const char *
const query[] = {
1917 "this",
"line",
"paragraph",
"rubbish"
1973 mset_expect_order(mymset, 8, 6, 4, 5, 7, 10, 12, 11, 13, 9, 14);
1974 mymset = enq.
get_mset(0, 20, 0, NULL, &vsmd1);
1976 mymset = enq.
get_mset(0, 20, 0, NULL, &vsmd2);
static void make_netstats1_db(Xapian::WritableDatabase &db, const string &)
static Xapian::Query query(const string &t)
#define EXPECTED_EXCEPTION
DEFINE_TESTCASE(termstats, backend)
Xapian::Database get_remote_database(const string &dbname, unsigned int timeout)
string get_database_path(const string &dbname)
Xapian::Database get_database(const string &dbname)
test functionality of the Xapian API
Base class for backend handling in test harness.
static const char * get_xapian_progsrv_command()
Get the command line required to run xapian-progsrv.
GrepMatchDecider(const string &needle_)
bool operator()(const Xapian::Document &doc) const override
Decide whether we want this document to be in the MSet.
double get_sumpart(Xapian::termcount, Xapian::termcount, Xapian::termcount) const override
Calculate the weight contribution for this object's term to a document.
double get_maxextra() const override
Return an upper bound on what get_sumextra() can return for any document.
std::string name() const override
Return the name of this weighting scheme.
void init(double factor) override
Allow the subclass to perform any initialisation it needs to.
MyWeight * unserialise(const string &) const override
Unserialise parameters.
MyWeight * clone() const override
Clone this object.
string serialise() const override
Return this object's parameters serialised as a single string.
double get_sumextra(Xapian::termcount, Xapian::termcount) const override
Calculate the term-independent weight component for a document.
double get_maxpart() const override
Return an upper bound on what get_sumpart() can return for any document.
Class implementing a "boolean" weighting scheme.
DatabaseCreateError indicates a failure to create a database.
DatabaseLockError indicates failure to lock a database.
Indicates an attempt to access a database not present.
DatabaseOpeningError indicates failure to open a database.
This class is used to access a database, or a group of databases.
PostingIterator postlist_begin(const std::string &tname) const
An iterator pointing to the start of the postlist for a given term.
void add_database(const Database &database)
Add an existing database (or group of databases) to those accessed by this object.
Xapian::doclength get_avlength() const
Get the average length of the documents in the database.
PostingIterator postlist_end(const std::string &) const
Corresponding end iterator to postlist_begin().
void keep_alive()
Send a "keep-alive" to remote databases to stop them timing out.
Xapian::termcount get_collection_freq(const std::string &tname) const
Return the total number of occurrences of the given term.
Xapian::doccount get_termfreq(const std::string &tname) const
Get the number of documents in the database indexed by a given term.
Xapian::termcount get_doclength(Xapian::docid did) const
Get the length of a document.
TermIterator allterms_begin(const std::string &prefix=std::string()) const
An iterator which runs across all terms with a given prefix.
bool term_exists(const std::string &tname) const
Check if a given term exists in the database.
static size_t check(const std::string &path, int opts=0, std::ostream *out=NULL)
Check the integrity of a database or database table.
TermIterator allterms_end(const std::string &=std::string()) const
Corresponding end iterator to allterms_begin(prefix).
Xapian::doccount get_doccount() const
Get the number of documents in the database.
Xapian::Document get_document(Xapian::docid did) const
Get a document from the database, given its document id.
Xapian::docid get_lastdocid() const
Get the highest document id which has been used in the database.
Xapian::termcount get_unique_terms(Xapian::docid did) const
Get the number of unique terms in document.
A handle representing a document in a Xapian database.
std::string get_data() const
Get data stored in the document.
std::string get_value(Xapian::valueno slot) const
Get value by number.
Iterator over a Xapian::ESet.
double get_weight() const
Get the weight for the current position.
Class representing a list of search results.
ESetIterator end() const
Return iterator pointing to just after the last item in this ESet.
Xapian::doccount size() const
Return number of items in this ESet object.
ESetIterator begin() const
Return iterator pointing to the first item in this ESet.
This class provides an interface to the information retrieval system for the purpose of searching.
static const int USE_EXACT_TERMFREQ
Calculate exact term frequencies in get_eset().
void set_query(const Xapian::Query &query, Xapian::termcount qlen=0)
Set the query to run.
void set_collapse_key(Xapian::valueno collapse_key, Xapian::doccount collapse_max=1)
Set the collapse key to use for queries.
TermIterator get_matching_terms_begin(Xapian::docid did) const
Get terms which match a given document, by document id.
ESet get_eset(Xapian::termcount maxitems, const RSet &omrset, int flags=0, const Xapian::ExpandDecider *edecider=0, double min_wt=0.0) const
Get the expand set for the given rset.
void set_sort_by_relevance_then_value(Xapian::valueno sort_key, bool reverse)
Set the sorting to be by relevance then value.
void set_cutoff(int percent_cutoff, double weight_cutoff=0)
Set the percentage and/or weight cutoffs.
void set_sort_by_value_then_relevance(Xapian::valueno sort_key, bool reverse)
Set the sorting to be by value, then by relevance for documents with the same value.
MSet get_mset(Xapian::doccount first, Xapian::doccount maxitems, Xapian::doccount checkatleast=0, const RSet *omrset=0, const MatchDecider *mdecider=0) const
Get (a portion of) the match set for the current query.
void set_sort_by_value(Xapian::valueno sort_key, bool reverse)
Set the sorting to be by value only.
void set_docid_order(docid_order order)
Set sort order for document IDs.
void set_weighting_scheme(const Weight &weight_)
Set the weighting scheme to use for queries.
@ DESCENDING
docids sort in descending order.
@ ASCENDING
docids sort in ascending order (default)
TermIterator get_matching_terms_end(Xapian::docid) const
End iterator corresponding to get_matching_terms_begin()
Decide if a Xapian::Error exception should be ignored.
All exceptions thrown by Xapian are subclasses of Xapian::Error.
const std::string & get_msg() const
Message giving details of the error, intended for human consumption.
std::string get_description() const
Return a string describing this object.
Indicates an attempt to use a feature which is unavailable.
Iterator over a Xapian::MSet.
Xapian::Document get_document() const
Get the Document object for the current position.
Class representing a list of search results.
Xapian::doccount size() const
Return number of items in this MSet object.
Xapian::doccount get_uncollapsed_matches_upper_bound() const
Upper bound on the total number of matching documents before collapsing.
Xapian::doccount get_uncollapsed_matches_estimated() const
Estimate of the total number of matching documents before collapsing.
Xapian::doccount get_uncollapsed_matches_lower_bound() const
Lower bound on the total number of matching documents before collapsing.
bool empty() const
Return true if this MSet object is empty.
Xapian::doccount get_matches_upper_bound() const
Upper bound on the total number of matching documents.
MSetIterator begin() const
Return iterator pointing to the first item in this MSet.
double get_max_attained() const
The maximum weight attained by any document.
Xapian::doccount get_matches_lower_bound() const
Lower bound on the total number of matching documents.
MSetIterator end() const
Return iterator pointing to just after the last item in this MSet.
Xapian::doccount get_matches_estimated() const
Estimate of the total number of matching documents.
Base class for matcher decision functor.
Indicates a problem communicating with a remote database.
Indicates a timeout expired while communicating with a remote database.
Class for iterating over a list of terms.
Xapian::termcount get_wdf() const
Return the wdf for the document at the current position.
void skip_to(Xapian::docid did)
Advance the iterator to document did.
std::string get_description() const
Return a string describing this object.
Xapian::termcount get_doclength() const
Return the length of the document at the current position.
Xapian::termcount get_unique_terms() const
Return the number of unique terms in the current document.
Class representing a query.
@ OP_OR
Match documents which at least one subquery matches.
static const Xapian::Query MatchAll
A query matching all documents.
void add_document(Xapian::docid did)
Add a document to the relevance set.
Class representing a stemming algorithm.
Parses a piece of text and generate terms.
void index_text(const Xapian::Utf8Iterator &itor, Xapian::termcount wdf_inc=1, const std::string &prefix=std::string())
Index some text.
void set_document(const Xapian::Document &doc)
Set the current document.
void set_stemming_strategy(stem_strategy strategy)
Set the stemming strategy.
void set_stemmer(const Xapian::Stem &stemmer)
Set the Xapian::Stem object to be used for generating stemmed terms.
Class for iterating over a list of terms.
Xapian::doccount get_termfreq() const
Return the term frequency for the term at the current position.
void skip_to(const std::string &term)
Advance the iterator to term term.
UnimplementedError indicates an attempt to use an unimplemented feature.
MatchDecider filtering results based on whether document values are in a user-defined set.
void add_value(const std::string &value)
Add a value to the test set.
Abstract base class for weighting schemes.
This class provides read/write access to a database.
void replace_document(Xapian::docid did, const Xapian::Document &document)
Replace a given document in the database.
void commit()
Commit any pending modifications made to the database.
Xapian::docid add_document(const Xapian::Document &document)
Add a new document to the database.
void sleep(double t)
Sleep until the time represented by this object.
const valueno BAD_VALUENO
Reserved value to indicate "no valueno".
const int DB_CREATE
Create a new database.
const int DB_CREATE_OR_OPEN
Create database if it doesn't already exist.
const int DB_BACKEND_CHERT
Use the chert backend.
unsigned XAPIAN_TERMCOUNT_BASE_TYPE termcount
A counts of terms.
const int DB_BACKEND_STUB
Open a stub database file.
const int DB_OPEN
Open an existing database.
unsigned valueno
The number for a value slot in a document.
unsigned XAPIAN_DOCID_BASE_TYPE doccount
A count of documents.
const int DB_BACKEND_GLASS
Use the glass backend.
unsigned XAPIAN_DOCID_BASE_TYPE docid
A unique identifier for a document.
const int DB_CREATE_OR_OVERWRITE
Create database if it doesn't already exist, or overwrite if it does.
include <netdb.h>, with portability workarounds.
include <sys/stat.h> with portability enhancements
<unistd.h>, but with compat.
static Xapian::Stem stemmer
#define TEST_REL(A, REL, B)
Test a relation holds,e.g. TEST_REL(a,>,b);.
std::ostringstream tout
The debug printing stream.
a generic test suite engine
#define FAIL_TEST(MSG)
Fail the current testcase with message MSG.
#define SKIP_TEST(MSG)
Skip the current testcase with message MSG.
#define TEST_EQUAL(a, b)
Test for equality of two things.
#define TEST_STRINGS_EQUAL(a, b)
Test for equality of two strings.
#define TEST_EQUAL_DOUBLE(a, b)
Test two doubles for near equality.
#define TEST(a)
Test a condition, without an additional explanation for failure.
#define TEST_NOT_EQUAL(a, b)
Test for non-equality of two things.
#define TEST_AND_EXPLAIN(a, b)
Test a condition, and display the test with an extra explanation if the condition fails.
bool mset_range_is_same_weights(const Xapian::MSet &mset1, unsigned int first1, const Xapian::MSet &mset2, unsigned int first2, unsigned int count)
void mset_expect_order(const Xapian::MSet &A, Xapian::docid d1, Xapian::docid d2, Xapian::docid d3, Xapian::docid d4, Xapian::docid d5, Xapian::docid d6, Xapian::docid d7, Xapian::docid d8, Xapian::docid d9, Xapian::docid d10, Xapian::docid d11, Xapian::docid d12)
bool mset_range_is_same(const Xapian::MSet &mset1, unsigned int first1, const Xapian::MSet &mset2, unsigned int first2, unsigned int count)
Xapian-specific test helper functions and macros.
#define TEST_EXCEPTION(TYPE, CODE)
Check that CODE throws exactly Xapian exception TYPE.
#define TEST_EXCEPTION_BASE_CLASS(TYPE, CODE)
Check that CODE throws Xapian exception derived from TYPE.
#define TEST_MSET_SIZE(M, S)
Check MSet M has size S.
void touch(const string &filename)
Touch a file, just like the Unix "touch" command.
void rm_rf(const string &filename)
Remove a directory and contents, just like the Unix "rm -rf" command.
C++ function versions of useful Unix commands.
Public interfaces for the Xapian library.