libmoost
/home/mhx/git/github/libmoost/test/algorithm/ketama_partitioner.cpp
Go to the documentation of this file.
00001 /* vim:set ts=3 sw=3 sts=3 et: */
00028 #include <boost/test/unit_test.hpp>
00029 #include <boost/test/test_tools.hpp>
00030 
00031 #include <vector>
00032 
00033 #include "../../include/moost/algorithm/ketama_partitioner.hpp"
00034 
00035 using namespace moost::algorithm;
00036 
00037 BOOST_AUTO_TEST_SUITE( ketama_partitioner_test )
00038 
00039 BOOST_AUTO_TEST_CASE( test_ketama )
00040 {
00041   int from = 9;
00042   int to = 10;
00043 
00044   ketama_partitioner<int> old_kp(from, 4096);
00045   ketama_partitioner<int> new_kp(to, 4096);
00046 
00047   std::vector<int> bucket_counts(new_kp.num_buckets());
00048 
00049   for (int i = 0; i != 5000000; ++i)
00050   {
00051      int old_bucket = old_kp.partition(i);
00052      int new_bucket = new_kp.partition(i);
00053      ++bucket_counts[new_bucket];
00054      BOOST_REQUIRE(old_bucket == new_bucket || new_bucket == to - 1);
00055   }
00056 
00057   // make sure none deviate more than 5% from the average
00058   int average_min = (5000000 / to) * 0.95F;
00059   int average_max = (5000000 / to) * 1.05F;
00060   for (size_t i = 0; i != bucket_counts.size(); ++i)
00061   {
00062     BOOST_CHECK_PREDICATE( std::greater<int>(), (bucket_counts[i]) (average_min) );
00063     BOOST_CHECK_PREDICATE( std::less<int>(), (bucket_counts[i]) (average_max) );
00064   }
00065 }
00066 
00067 BOOST_AUTO_TEST_CASE( test_bucket_Y_ketama )
00068 {
00069    std::vector<int> from;
00070    from.push_back(1);
00071    from.push_back(2);
00072    from.push_back(3);
00073 
00074    std::vector<int> to;
00075    to.push_back(1);
00076    to.push_back(2);
00077    to.push_back(3);
00078    to.push_back(4);
00079 
00080    ketama_partitioner<int> old_kp(from, 4096);
00081    ketama_partitioner<int> new_kp(to, 4096);
00082 
00083   std::vector<int> bucket_counts(new_kp.num_buckets());
00084 
00085   for (int i = 0; i != 5000000; ++i)
00086   {
00087      int old_bucket = old_kp.partition(i);
00088      int new_bucket = new_kp.partition(i);
00089      ++bucket_counts[new_bucket];
00090      BOOST_REQUIRE(old_bucket == new_bucket || new_bucket == 3); // 3 is the index of the new server
00091   }
00092 
00093   // make sure none deviate more than 5% from the average
00094   int average_min = (5000000 / to.size() ) * 0.95F;
00095   int average_max = (5000000 / to.size() ) * 1.05F;
00096   for (size_t i = 0; i != bucket_counts.size(); ++i)
00097   {
00098     BOOST_CHECK_PREDICATE( std::greater<int>(), (bucket_counts[i]) (average_min) );
00099     BOOST_CHECK_PREDICATE( std::less<int>(), (bucket_counts[i]) (average_max) );
00100   }
00101 }
00102 
00103 BOOST_AUTO_TEST_CASE( test_bucket_string_ketama )
00104 {
00105    std::vector<std::string> from;
00106    from.push_back("10.0.1.101:11211");
00107    from.push_back("10.0.1.102:11211");
00108    from.push_back("10.0.1.103:11211");
00109 
00110    std::vector<std::string> to;
00111    to.push_back("10.0.1.101:11211");
00112    to.push_back("10.0.1.102:11211");
00113    to.push_back("10.0.1.103:11211");
00114    to.push_back("10.0.1.104:11211");
00115 
00116    ketama_partitioner<int> old_kp(from, 4096);
00117    ketama_partitioner<int> new_kp(to, 4096);
00118 
00119   std::vector<int> bucket_counts(new_kp.num_buckets());
00120 
00121   const std::string new_guy = "10.0.1.104:11211";
00122   for (int i = 0; i != 5000000; ++i)
00123   {
00124      int old_bucket = old_kp.partition(i);
00125      int new_bucket = new_kp.partition(i);
00126      ++bucket_counts[new_bucket];
00127      BOOST_REQUIRE(old_bucket == new_bucket || new_bucket == 3); // 3 is the index of the new server
00128   }
00129 
00130   // make sure none deviate more than 5% from the average
00131   int average_min = (5000000 / to.size()) * 0.95F;
00132   int average_max = (5000000 / to.size()) * 1.05F;
00133   for (size_t i = 0; i != bucket_counts.size(); ++i)
00134   {
00135     BOOST_CHECK_PREDICATE( std::greater<int>(), (bucket_counts[i]) (average_min) );
00136     BOOST_CHECK_PREDICATE( std::less<int>(), (bucket_counts[i]) (average_max) );
00137   }
00138 }
00139 
00140 BOOST_AUTO_TEST_SUITE_END()