Skip to content

Commit

Permalink
HRCPP-402 Added test for near cache support
Browse files Browse the repository at this point in the history
  • Loading branch information
rigazilla committed Oct 5, 2017
1 parent 2996cc9 commit 726c0ad
Show file tree
Hide file tree
Showing 7 changed files with 306 additions and 0 deletions.
1 change: 1 addition & 0 deletions xunit-test/CMakeLists.txt
@@ -1,3 +1,4 @@
ADD_SUBDIRECTORY(PutGetTest)
ADD_SUBDIRECTORY(ClearTest)
ADD_SUBDIRECTORY(QueryTest)
ADD_SUBDIRECTORY(NearCacheTest)
24 changes: 24 additions & 0 deletions xunit-test/NearCacheTest/CMakeLists.txt
@@ -0,0 +1,24 @@
file(GLOB SRCS *.cpp)

add_executable(NearCacheMultiClientTest ${SRCS})

add_definitions(-DHR_PROTO_EXPORT=)
set_property(TARGET NearCacheMultiClientTest PROPERTY CXX_STANDARD 11)
set_property(TARGET NearCacheMultiClientTest PROPERTY CXX_STANDARD_REQUIRED ON)
set_target_properties (NearCacheMultiClientTest PROPERTIES COMPILE_FLAGS "${COMPILER_FLAGS} ${WARNING_FLAGS_NO_PEDANTIC} ${STATIC_FLAGS} ${NO_UNUSED_FLAGS}")
set_target_properties(NearCacheMultiClientTest PROPERTIES COMPILE_DEFINITIONS "${DLLEXPORT_STATIC}" )

target_link_libraries(NearCacheMultiClientTest
hotrod-static
libgtest
${platform_libs}
)

add_test (start_server ${PYTHON_EXECUTABLE} ${CMAKE_ROOT_SOURCE_DIR}/test/bin/server_ctl.py start ${JAVA_RUNTIME} ${HOTROD_JBOSS_HOME} standalone.xml)
add_test (probe_port ${PYTHON_EXECUTABLE} ${CMAKE_ROOT_SOURCE_DIR}/test/bin/probe_port.py localhost 11222 60)

add_test(xunit_nearCacheMultiClientTest NearCacheMultiClientTest --gtest_output=xml:${PROJECT_BINARY_DIR}/test-output/)

add_test (stop_server ${PYTHON_EXECUTABLE} ${CMAKE_ROOT_SOURCE_DIR}/test/bin/server_ctl.py stop)
add_test (probe_port_stop ${PYTHON_EXECUTABLE} ${CMAKE_ROOT_SOURCE_DIR}/test/bin/probe_port.py localhost 11222 60 down)

91 changes: 91 additions & 0 deletions xunit-test/NearCacheTest/NearCacheMultiClientTest.cpp
@@ -0,0 +1,91 @@
#include "infinispan/hotrod/ConfigurationBuilder.h"
#include "infinispan/hotrod/RemoteCacheManager.h"
#include "NearCacheMultiClientTest.h"
#include <functional>
#include <chrono>
#include <thread>
using ::infinispan::hotrod::ConfigurationBuilder;
using ::infinispan::hotrod::Configuration;

std::unique_ptr<infinispan::hotrod::RemoteCacheManager> NearCacheTest::remoteCacheManager;

void waitFor(const std::function<bool()> &func, long waitTime = 1000, int pollInterval = 100);
/*void waitFor(const std::function<bool()> &func, long waitTime = 1000, int pollInterval = 100)
{
using namespace std::chrono;
milliseconds end = duration_cast< milliseconds >(system_clock::now().time_since_epoch())+ milliseconds(waitTime);
while(duration_cast< milliseconds >(system_clock::now().time_since_epoch())<end)
{
if (func()) return;
std::this_thread::sleep_for(milliseconds(pollInterval));
}
ASSERT_TRUE(func()) << "Error timeout";
}
*/
NearCacheTest::NearCacheTest()
{
}

void NearCacheTest::SetUp() {
if (NearCacheTest::remoteCacheManager == nullptr){
ConfigurationBuilder builder;
builder.addServer().host("127.0.0.1").port(11222);
builder.protocolVersion(Configuration::PROTOCOL_VERSION_24);
builder.balancingStrategyProducer(nullptr);
builder.nearCache().mode(NearCacheMode::INVALIDATED).maxEntries(10);
NearCacheTest::remoteCacheManager.reset(new RemoteCacheManager(builder.build(), false));
}
};

void NearCacheTest::TearDown() {
NearCacheTest::remoteCacheManager->stop();
}

TEST_F(NearCacheTest, ClientsInvalidatedTest) {
NearCacheTest::remoteCacheManager->start();
BasicMarshaller<std::string> *km1 = new BasicMarshaller<std::string>();
BasicMarshaller<std::string> *vm1 = new BasicMarshaller<std::string>();
RemoteCache<std::string, std::string> cache1 = NearCacheTest::remoteCacheManager->getCache<std::string, std::string>(km1,
&Marshaller<std::string>::destroy,
vm1,
&Marshaller<std::string>::destroy, true);

BasicMarshaller<std::string> *km2 = new BasicMarshaller<std::string>();
BasicMarshaller<std::string> *vm2 = new BasicMarshaller<std::string>();
RemoteCache<std::string, std::string> cache2 = NearCacheTest::remoteCacheManager->getCache<std::string, std::string>(km2,
&Marshaller<std::string>::destroy,
vm2,
&Marshaller<std::string>::destroy, true);

cache1.clear();
cache2.clear();
std::string k("k");
ASSERT_EQ(nullptr, cache1.get(k));
ASSERT_EQ(nullptr, cache2.get(k));
cache1.put(k, "v1");
auto stats1 = cache2.stats();
//Get needs to go remotely because this is first time cache2 client reads the value
ASSERT_EQ("v1", *cache2.get(k));
//Get is only local now
ASSERT_EQ("v1", *cache2.get(k));
auto stats2 = cache2.stats();
ASSERT_EQ(std::stoi(stats1["hits"]) + 1, std::stoi(stats2["hits"])) << "Client 2 did not reach the server!";
cache1.put(k, "v2");
//Get needs to go remotely
std::function<bool()> f = [&cache2, &k](){std::string* res=cache2.get(k); return (res!=nullptr) && *res== std::string("v2");};
waitFor(f);

auto stats3 = cache2.stats();
ASSERT_EQ(std::stoi(stats2["hits"]) + 1, std::stoi(stats3["hits"])) << "Client 2 did not reach the server for new value!";
auto cache1Stats1 = cache1.stats();
cache2.put(k, "v3");

//Get needs to go remotely
std::function<bool()> f1 = [&cache1, &k](){ std::string* res=cache1.get(k); return (res!=nullptr) && *res== std::string("v3"); };
waitFor(f1);

auto cache1Stats2 = cache1.stats();
ASSERT_EQ(std::stoi(cache1Stats1["hits"]) + 1, std::stoi(cache1Stats2["hits"])) << "Client 1 did not reach the server for new value!";

}

36 changes: 36 additions & 0 deletions xunit-test/NearCacheTest/NearCacheMultiClientTest.h
@@ -0,0 +1,36 @@
#include "gtest/gtest.h"
#include <memory>

namespace infinispan {
namespace hotrod
{
class RemoteCacheManager;
}
}

// The fixture for testing class Foo.

class NearCacheTest : public ::testing::Test {
public:
static std::unique_ptr<infinispan::hotrod::RemoteCacheManager> remoteCacheManager;

protected:

// You can do set-up work for each test here.
NearCacheTest();

// You can do clean-up work that doesn't throw exceptions here.
virtual ~NearCacheTest() {} ;

// If the constructor and destructor are not enough for setting up
// and cleaning up each test, you can define the following methods:

// Code here will be called immediately after the constructor (right
// before each test).
virtual void SetUp();

// Code here will be called immediately after each test (right
// before the destructor).
virtual void TearDown();

};
110 changes: 110 additions & 0 deletions xunit-test/NearCacheTest/NearCacheStaleReadsTest.cpp
@@ -0,0 +1,110 @@
#include "infinispan/hotrod/ConfigurationBuilder.h"
#include "infinispan/hotrod/RemoteCacheManager.h"
#include "NearCacheStaleReadsTest.h"
#include <functional>
#include <chrono>
#include <thread>
using ::infinispan::hotrod::ConfigurationBuilder;
using ::infinispan::hotrod::Configuration;

std::unique_ptr<infinispan::hotrod::RemoteCacheManager> NearCacheStaleReadsTest::remoteCacheManager;

void waitFor(const std::function<bool()> &func, long waitTime = 1000, int pollInterval = 100)
{
using namespace std::chrono;
milliseconds end = duration_cast< milliseconds >(system_clock::now().time_since_epoch())+ milliseconds(waitTime);
while(duration_cast< milliseconds >(system_clock::now().time_since_epoch())<end)
{
if (func()) return;
std::this_thread::sleep_for(milliseconds(pollInterval));
}
ASSERT_TRUE(func()) << "Error timeout";
}

NearCacheStaleReadsTest::NearCacheStaleReadsTest()
{
}

void NearCacheStaleReadsTest::SetUp() {
if (NearCacheStaleReadsTest::remoteCacheManager == nullptr){
ConfigurationBuilder builder;
builder.addServer().host("127.0.0.1").port(11222);
builder.protocolVersion(Configuration::PROTOCOL_VERSION_24);
builder.balancingStrategyProducer(nullptr);
builder.nearCache().mode(NearCacheMode::INVALIDATED).maxEntries(-1);
NearCacheStaleReadsTest::remoteCacheManager.reset(new RemoteCacheManager(builder.build(), false));
}
};

void NearCacheStaleReadsTest::TearDown() {
NearCacheStaleReadsTest::remoteCacheManager->stop();
}

TEST_F(NearCacheStaleReadsTest, AvoidStaleReadAfterPutRemoveTest) {
std::function<void(int, RemoteCache<std::string, std::string>)> f = [](int i, RemoteCache<std::string, std::string> cache) {
std::string value = std::string("v") + std::to_string(i);
cache.put("k", value);
ASSERT_EQ(value, *cache.get("k"));
cache.remove("k");
ASSERT_EQ(nullptr, cache.get("k"));
};
}

TEST_F(NearCacheStaleReadsTest, AvoidStaleReadAfterPutAllTest) {
std::function<void(int, RemoteCache<std::string, std::string>)> f = [](int i, RemoteCache<std::string, std::string> cache) {
std::map<std::string, std::string> map;
std::string value = std::string("v") + std::to_string(i);
map["k"]=value;
cache.putAll(map);
ASSERT_EQ(value, *cache.get("k"));
};
}

TEST_F(NearCacheStaleReadsTest, AvoidStaleReadAfterReplaceTest) {
std::function<void(int, RemoteCache<std::string, std::string>)> f = [](int i, RemoteCache<std::string, std::string> cache) {

std::string value = std::string("v") + std::to_string(i);
cache.replace("k", value);
auto versioned = cache.getWithVersion("k");
ASSERT_EQ(value, *versioned.first);
};
}

TEST_F(NearCacheStaleReadsTest, AvoidStaleReadAfterReplaceWithVersionTest) {
std::function<void(int, RemoteCache<std::string, std::string>)> f = [](int i, RemoteCache<std::string, std::string> cache) {
std::string value = std::string("v") + std::to_string(i);
auto versioned = cache.getWithVersion("k");
ASSERT_TRUE(cache.replaceWithVersion("k", value, (ulong) versioned.second.version)) << "Not replaced!";
ASSERT_EQ(value, *cache.get("k"));
};
}

TEST_F(NearCacheStaleReadsTest, AvoidStaleReadAfterPutAsyncRemoveWithVersionTest) {
std::function<void(int, RemoteCache<std::string, std::string>)> f = [](int i, RemoteCache<std::string, std::string> cache) {
std::string value = std::string("v") + std::to_string(i);
cache.putAsync("k", value).wait();
auto versioned = cache.getWithVersion("k");
ASSERT_EQ(value, *versioned.first);
ASSERT_TRUE(cache.removeWithVersion("k", (ulong) versioned.second.version)) << "Not removed!";
ASSERT_EQ(value, *cache.get("k"));
ASSERT_EQ(nullptr, cache.get("k"));
};
}

void Repeat(std::function<void(int, RemoteCache<std::string, std::string>)> &f)
{
BasicMarshaller<std::string> *km1 = new BasicMarshaller<std::string>();
BasicMarshaller<std::string> *vm1 = new BasicMarshaller<std::string>();
RemoteCache<std::string, std::string> cache = NearCacheStaleReadsTest::remoteCacheManager->getCache<std::string, std::string>(km1,
&Marshaller<std::string>::destroy,
vm1,
&Marshaller<std::string>::destroy, true);

cache.clear();
cache.putIfAbsent("k", "v0");
for (int i = 1; i != 1000; i++)
{
f(i, cache);
}
}

36 changes: 36 additions & 0 deletions xunit-test/NearCacheTest/NearCacheStaleReadsTest.h
@@ -0,0 +1,36 @@
#include "gtest/gtest.h"
#include <memory>

namespace infinispan {
namespace hotrod
{
class RemoteCacheManager;
}
}

// The fixture for testing class Foo.

class NearCacheStaleReadsTest : public ::testing::Test {
public:
static std::unique_ptr<infinispan::hotrod::RemoteCacheManager> remoteCacheManager;

protected:

// You can do set-up work for each test here.
NearCacheStaleReadsTest();

// You can do clean-up work that doesn't throw exceptions here.
virtual ~NearCacheStaleReadsTest() {} ;

// If the constructor and destructor are not enough for setting up
// and cleaning up each test, you can define the following methods:

// Code here will be called immediately after the constructor (right
// before each test).
virtual void SetUp();

// Code here will be called immediately after each test (right
// before the destructor).
virtual void TearDown();

};
8 changes: 8 additions & 0 deletions xunit-test/NearCacheTest/main.cpp
@@ -0,0 +1,8 @@
#include "gtest/gtest.h"

int main(int argc, char **argv)
{
::testing::InitGoogleTest(&argc, argv);
int ret = RUN_ALL_TESTS();
return ret;
}

0 comments on commit 726c0ad

Please sign in to comment.