#define CBTREEDB_SELF_VERIFY
#include "stx-cbtreedb.h"
#include <iostream>
#include <sstream>
#include <fstream>
#include <assert.h>
#include <stdlib.h>
static const unsigned int items = 10000;
template <typename cbtreedb>
void run_test_random(const std::string& dbname)
{
std::cout << "Creating test database using random writer." << std::endl;
typename cbtreedb::Writer writer;
writer.SetSignature("cbtestdb");
for(unsigned int i = 0; i <= items; ++i)
{
writer.Add(2*i, &i, sizeof(i));
}
std::ostringstream testdb;
writer.Write(testdb);
std::string testdbstr = testdb.str();
std::string refdbstr;
{
std::ifstream ifdb((AM_TOP_SRCDIR "/testsuite/" + dbname).c_str());
if (!ifdb.good()) {
ifdb.open(("testsuite/" + dbname).c_str());
}
char buffer[32*1024];
do
{
ifdb.read(buffer, sizeof(buffer));
refdbstr.append(buffer, ifdb.gcount());
}
while ( ifdb.good() && !ifdb.eof() );
}
if (testdbstr != refdbstr)
{
std::cout << "Reference database does not match!" << std::endl;
std::ofstream ofdb((dbname + "-new").c_str());
ofdb << testdbstr;
ofdb.close();
assert( testdbstr == refdbstr );
}
}
template <typename cbtreedb>
void run_test_sequential(const std::string& dbname)
{
std::cout << "Creating test database using sequential writer." << std::endl;
typename cbtreedb::WriterSequential writer;
writer.SetSignature("cbtestdb");
for(unsigned int i = 0; i <= items; ++i)
{
writer.Add(2*i, sizeof(i));
}
std::ostringstream testdb;
writer.WriteHeader(testdb);
for(unsigned int i = 0; i <= items; ++i)
{
writer.WriteValue(2*i, &i, sizeof(i));
}
writer.WriteFinalize();
std::string testdbstr = testdb.str();
std::string refdbstr;
{
std::ifstream ifdb((AM_TOP_SRCDIR "/testsuite/" + dbname).c_str());
if (!ifdb.good()) {
ifdb.open(("testsuite/" + dbname).c_str());
}
char buffer[32*1024];
do
{
ifdb.read(buffer, sizeof(buffer));
refdbstr.append(buffer, ifdb.gcount());
}
while ( ifdb.good() && !ifdb.eof() );
}
if (testdbstr != refdbstr)
{
std::cout << "Reference database does not match!" << std::endl;
std::ofstream ofdb((dbname + "-new").c_str());
ofdb << testdbstr;
ofdb.close();
assert( testdbstr == refdbstr );
}
}
template <typename cbtreedb>
void run_test_open(const std::string& dbname, const std::string& expectederrorstring)
{
std::string dbstr;
{
std::ifstream ifdb((AM_TOP_SRCDIR "/testsuite/" + dbname).c_str());
if (!ifdb.good()) {
ifdb.open(("testsuite/" + dbname).c_str());
}
char buffer[32*1024];
do
{
ifdb.read(buffer, sizeof(buffer));
dbstr.append(buffer, ifdb.gcount());
}
while ( ifdb.good() && !ifdb.eof() );
}
assert(dbstr.size());
typename cbtreedb::Reader reader;
reader.SetSignature("cbtestdb");
typename cbtreedb::PageCache cache(128);
reader.SetPageCache(&cache);
std::istringstream testdb(dbstr);
std::string errorstring;
if (! reader.Open(testdb,&errorstring) )
{
if (errorstring != expectederrorstring)
{
std::cout << "Open errorstring mismatched: " << std::endl
<< "Got: " << errorstring << std::endl
<< "Expected: " << expectederrorstring << std::endl;
abort();
}
return;
}
assert( reader.Verify() );
assert( reader.Size() == items+1 );
}
int main()
{
run_test_random< stx::CBTreeDB<uint32_t, std::less<uint32_t>, 1024> >("test_format1.db");
run_test_sequential< stx::CBTreeDB<uint32_t, std::less<uint32_t>, 1024> >("test_format1.db");
run_test_random< stx::CBTreeDB<uint64_t, std::less<uint64_t>, 2048> >("test_format2.db");
run_test_sequential< stx::CBTreeDB<uint64_t, std::less<uint64_t>, 2048> >("test_format2.db");
run_test_open< stx::CBTreeDB<uint32_t, std::less<uint32_t>, 1024> >
("test_format1.db", "");
run_test_open< stx::CBTreeDB<uint32_t, std::less<uint32_t>, 2048> >
("test_format1.db", "Database not compatible with this reader: page sizes mismatch.");
run_test_open< stx::CBTreeDB<uint64_t, std::less<uint64_t>, 1024> >
("test_format1.db", "Database not compatible with this reader: key sizes mismatch.");
run_test_open< stx::CBTreeDB<uint32_t, std::greater<uint32_t>, 1024> >
("test_format1.db", "Database not compatible with this reader: root keys order mismatches.");
run_test_open< stx::CBTreeDB<uint64_t, std::less<uint64_t>, 2048> >
("test_format2.db", "");
run_test_open< stx::CBTreeDB<uint64_t, std::less<uint64_t>, 1024> >
("test_format2.db", "Database not compatible with this reader: page sizes mismatch.");
run_test_open< stx::CBTreeDB<uint32_t, std::less<uint32_t>, 2048> >
("test_format2.db", "Database not compatible with this reader: key sizes mismatch.");
run_test_open< stx::CBTreeDB<uint64_t, std::greater<uint64_t>, 2048> >
("test_format2.db", "Database not compatible with this reader: root keys order mismatches.");
return 0;
}