diff options
author | Jon Bratseth <bratseth@yahoo-inc.com> | 2016-06-15 23:09:44 +0200 |
---|---|---|
committer | Jon Bratseth <bratseth@yahoo-inc.com> | 2016-06-15 23:09:44 +0200 |
commit | 72231250ed81e10d66bfe70701e64fa5fe50f712 (patch) | |
tree | 2728bba1131a6f6e5bdf95afec7d7ff9358dac50 /messagebus/src/tests/sequencer/sequencer.cpp |
Publish
Diffstat (limited to 'messagebus/src/tests/sequencer/sequencer.cpp')
-rw-r--r-- | messagebus/src/tests/sequencer/sequencer.cpp | 194 |
1 files changed, 194 insertions, 0 deletions
diff --git a/messagebus/src/tests/sequencer/sequencer.cpp b/messagebus/src/tests/sequencer/sequencer.cpp new file mode 100644 index 00000000000..b2818cfa57d --- /dev/null +++ b/messagebus/src/tests/sequencer/sequencer.cpp @@ -0,0 +1,194 @@ +// Copyright 2016 Yahoo Inc. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. +#include <vespa/fastos/fastos.h> +#include <vespa/log/log.h> +LOG_SETUP("sequencer_test"); + +#include <vespa/messagebus/sequencer.h> +#include <vespa/messagebus/emptyreply.h> +#include <vespa/messagebus/routablequeue.h> +#include <vespa/messagebus/testlib/simplemessage.h> +#include <vespa/vespalib/testkit/testapp.h> + +using namespace mbus; + +// -------------------------------------------------------------------------------- +// +// Setup. +// +// -------------------------------------------------------------------------------- + +struct MyQueue : public RoutableQueue { + + virtual ~MyQueue() { + while (size() > 0) { + Routable::UP obj = dequeue(0); + obj->getCallStack().discard(); + } + } + + bool checkReply(bool hasSeqId, uint64_t seqId) { + if (size() == 0) { + LOG(error, "checkReply(): No reply in queue."); + return false; + } + Routable::UP obj = dequeue(0); + if (!obj->isReply()) { + LOG(error, "checkReply(): Got message when expecting reply."); + return false; + } + Reply::UP reply(static_cast<Reply*>(obj.release())); + Message::UP msg = reply->getMessage(); + if (msg.get() == NULL) { + LOG(error, "checkReply(): Reply has no message attached."); + return false; + } + if (hasSeqId) { + if (!msg->hasSequenceId()) { + LOG(error, "checkReply(): Expected sequence id %" PRIu64 ", got none.", + seqId); + return false; + } + if (msg->getSequenceId() != seqId) { + LOG(error, "checkReply(): Expected sequence id %" PRIu64 ", got %" PRIu64 ".", + seqId, msg->getSequenceId()); + return false; + } + } else { + if (msg->hasSequenceId()) { + LOG(error, "checkReply(): Message has unexpected sequence id %" PRIu64 ".", + msg->getSequenceId()); + return false; + } + } + return true; + } + + void replyNext() { + Routable::UP obj = dequeue(0); + Message::UP msg(static_cast<Message*>(obj.release())); + + Reply::UP reply(new EmptyReply()); + reply->swapState(*msg); + reply->setMessage(std::move(msg)); + IReplyHandler &handler = reply->getCallStack().pop(*reply); + handler.handleReply(std::move(reply)); + } + + Message::UP createMessage(bool hasSeqId, uint64_t seqId) { + Message::UP ret(new SimpleMessage("foo", hasSeqId, seqId)); + ret->pushHandler(*this); + return ret; + } +}; + +class Test : public vespalib::TestApp { +private: + void testSyncNone(); + void testSyncId(); + +public: + int Main() { + TEST_INIT("sequencer_test"); + + testSyncNone(); TEST_FLUSH(); + testSyncId(); TEST_FLUSH(); + + TEST_DONE(); + } +}; + +TEST_APPHOOK(Test); + +// -------------------------------------------------------------------------------- +// +// Tests. +// +// -------------------------------------------------------------------------------- + +void +Test::testSyncNone() +{ + MyQueue src; + MyQueue dst; + Sequencer seq(dst); + + seq.handleMessage(src.createMessage(false, 0)); + seq.handleMessage(src.createMessage(false, 0)); + seq.handleMessage(src.createMessage(false, 0)); + seq.handleMessage(src.createMessage(false, 0)); + seq.handleMessage(src.createMessage(false, 0)); + EXPECT_EQUAL(0u, src.size()); + EXPECT_EQUAL(5u, dst.size()); + + dst.replyNext(); + dst.replyNext(); + dst.replyNext(); + dst.replyNext(); + dst.replyNext(); + EXPECT_EQUAL(5u, src.size()); + EXPECT_EQUAL(0u, dst.size()); + + EXPECT_TRUE(src.checkReply(false, 0)); + EXPECT_TRUE(src.checkReply(false, 0)); + EXPECT_TRUE(src.checkReply(false, 0)); + EXPECT_TRUE(src.checkReply(false, 0)); + EXPECT_TRUE(src.checkReply(false, 0)); + EXPECT_EQUAL(0u, src.size()); + EXPECT_EQUAL(0u, dst.size()); +} + +void +Test::testSyncId() +{ + MyQueue src; + MyQueue dst; + Sequencer seq(dst); + + seq.handleMessage(src.createMessage(true, 1)); + seq.handleMessage(src.createMessage(true, 2)); + seq.handleMessage(src.createMessage(true, 3)); + seq.handleMessage(src.createMessage(true, 4)); + seq.handleMessage(src.createMessage(true, 5)); + EXPECT_EQUAL(0u, src.size()); + EXPECT_EQUAL(5u, dst.size()); + + seq.handleMessage(src.createMessage(true, 1)); + seq.handleMessage(src.createMessage(true, 5)); + seq.handleMessage(src.createMessage(true, 2)); + seq.handleMessage(src.createMessage(true, 10)); + seq.handleMessage(src.createMessage(true, 4)); + seq.handleMessage(src.createMessage(true, 3)); + EXPECT_EQUAL(0u, src.size()); + EXPECT_EQUAL(6u, dst.size()); + + dst.replyNext(); + dst.replyNext(); + dst.replyNext(); + dst.replyNext(); + dst.replyNext(); + EXPECT_EQUAL(5u, src.size()); + EXPECT_EQUAL(6u, dst.size()); + + dst.replyNext(); + dst.replyNext(); + dst.replyNext(); + dst.replyNext(); + dst.replyNext(); + dst.replyNext(); + EXPECT_EQUAL(11u, src.size()); + EXPECT_EQUAL(0u, dst.size()); + + EXPECT_TRUE(src.checkReply(true, 1)); + EXPECT_TRUE(src.checkReply(true, 2)); + EXPECT_TRUE(src.checkReply(true, 3)); + EXPECT_TRUE(src.checkReply(true, 4)); + EXPECT_TRUE(src.checkReply(true, 5)); + EXPECT_TRUE(src.checkReply(true, 10)); + EXPECT_TRUE(src.checkReply(true, 1)); + EXPECT_TRUE(src.checkReply(true, 2)); + EXPECT_TRUE(src.checkReply(true, 3)); + EXPECT_TRUE(src.checkReply(true, 4)); + EXPECT_TRUE(src.checkReply(true, 5)); + EXPECT_EQUAL(0u, src.size()); + EXPECT_EQUAL(0u, dst.size()); +} |