You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@mesos.apache.org by bm...@apache.org on 2018/01/17 01:38:57 UTC

mesos git commit: Added an performance benchmark for master `GetState` v1 api.

Repository: mesos
Updated Branches:
  refs/heads/master aded41aec -> 9e2f9a240


Added an performance benchmark for master `GetState` v1 api.

This test is based on the master failover benchmark. Note that
it does not include executors for now.

Review: https://reviews.apache.org/r/64969/


Project: http://git-wip-us.apache.org/repos/asf/mesos/repo
Commit: http://git-wip-us.apache.org/repos/asf/mesos/commit/9e2f9a24
Tree: http://git-wip-us.apache.org/repos/asf/mesos/tree/9e2f9a24
Diff: http://git-wip-us.apache.org/repos/asf/mesos/diff/9e2f9a24

Branch: refs/heads/master
Commit: 9e2f9a2401a7665872f9cb2d994ca5013cd852c9
Parents: aded41a
Author: Meng Zhu <mz...@mesosphere.io>
Authored: Tue Jan 16 17:19:53 2018 -0800
Committer: Benjamin Mahler <bm...@apache.org>
Committed: Tue Jan 16 17:37:21 2018 -0800

----------------------------------------------------------------------
 src/tests/master_benchmarks.cpp | 151 ++++++++++++++++++++++++++++++++++-
 1 file changed, 149 insertions(+), 2 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/mesos/blob/9e2f9a24/src/tests/master_benchmarks.cpp
----------------------------------------------------------------------
diff --git a/src/tests/master_benchmarks.cpp b/src/tests/master_benchmarks.cpp
index 7d69588..80de24d 100644
--- a/src/tests/master_benchmarks.cpp
+++ b/src/tests/master_benchmarks.cpp
@@ -17,6 +17,7 @@
 #include <list>
 #include <string>
 #include <tuple>
+#include <vector>
 
 #include <mesos/resources.hpp>
 #include <mesos/version.hpp>
@@ -34,6 +35,8 @@
 
 #include "tests/mesos.hpp"
 
+namespace http = process::http;
+
 using process::await;
 using process::Clock;
 using process::Failure;
@@ -53,6 +56,7 @@ using std::make_tuple;
 using std::string;
 using std::tie;
 using std::tuple;
+using std::vector;
 
 using testing::WithParamInterface;
 
@@ -315,8 +319,6 @@ TEST_P(MasterFailover_BENCHMARK_Test, AgentReregistrationDelay)
 
   list<Future<Nothing>> reregistered;
 
-  cout << "Starting reregistration for all agents" << endl;
-
   // Measure the time for all agents to receive `SlaveReregisteredMessage`.
   Stopwatch watch;
   watch.start();
@@ -337,6 +339,151 @@ TEST_P(MasterFailover_BENCHMARK_Test, AgentReregistrationDelay)
        << watch.elapsed() << endl;
 }
 
+
+class MasterStateQuery_BENCHMARK_Test
+  : public MesosTest,
+    public WithParamInterface<tuple<
+      size_t, size_t, size_t, size_t, size_t>> {};
+
+
+INSTANTIATE_TEST_CASE_P(
+    AgentFrameworkTaskCountContentType,
+    MasterStateQuery_BENCHMARK_Test,
+    ::testing::Values(
+        make_tuple(1000, 5, 2, 5, 2),
+        make_tuple(10000, 5, 2, 5, 2),
+        make_tuple(20000, 5, 2, 5, 2),
+        make_tuple(40000, 5, 2, 5, 2)));
+
+
+// This test measures the performance of the `master::call::GetState`
+// v1 api (and also measures master v0 '/state' endpoint as the
+// baseline). We set up a lot of master state from artificial agents
+// similar to the master failover benchmark.
+TEST_P(MasterStateQuery_BENCHMARK_Test, GetState)
+{
+  size_t agentCount;
+  size_t frameworksPerAgent;
+  size_t tasksPerFramework;
+  size_t completedFrameworksPerAgent;
+  size_t tasksPerCompletedFramework;
+
+  tie(agentCount,
+    frameworksPerAgent,
+    tasksPerFramework,
+    completedFrameworksPerAgent,
+    tasksPerCompletedFramework) = GetParam();
+
+  // Disable authentication to avoid the overhead, since we don't care about
+  // it in this test.
+  master::Flags masterFlags = CreateMasterFlags();
+  masterFlags.authenticate_agents = false;
+
+  Try<Owned<cluster::Master>> master = StartMaster(masterFlags);
+  ASSERT_SOME(master);
+
+  vector<Owned<TestSlave>> slaves;
+
+  for (size_t i = 0; i < agentCount; i++) {
+    SlaveID slaveId;
+    slaveId.set_value("agent" + stringify(i));
+
+    slaves.push_back(Owned<TestSlave>(new TestSlave(
+        master.get()->pid,
+        slaveId,
+        frameworksPerAgent,
+        tasksPerFramework,
+        completedFrameworksPerAgent,
+        tasksPerCompletedFramework)));
+  }
+
+  cout << "Test setup: "
+       << agentCount << " agents with a total of "
+       << frameworksPerAgent * tasksPerFramework * agentCount
+       << " running tasks and "
+       << completedFrameworksPerAgent * tasksPerCompletedFramework * agentCount
+       << " completed tasks" << endl;
+
+  list<Future<Nothing>> reregistered;
+
+  foreach (const Owned<TestSlave>& slave, slaves) {
+    reregistered.push_back(slave->reregister());
+  }
+
+  // Wait all agents to finish reregistration.
+  await(reregistered).await();
+
+  Clock::pause();
+  Clock::settle();
+  Clock::resume();
+
+  Stopwatch watch;
+  watch.start();
+
+  // We first measure v0 "state" endpoint performance as the baseline.
+  Future<http::Response> v0Response = http::get(
+      master.get()->pid,
+      "state",
+      None(),
+      createBasicAuthHeaders(DEFAULT_CREDENTIAL));
+
+  v0Response.await();
+
+  watch.stop();
+
+  ASSERT_EQ(v0Response->status, http::OK().status);
+
+  cout << "v0 '/state' response took " << watch.elapsed() << endl;
+
+  // Helper function to post a request to '/api/v1' master endpoint
+  // and return the response.
+  auto post = [](
+      const process::PID<master::Master>& pid,
+      const v1::master::Call& call,
+      const ContentType& contentType)
+  {
+    http::Headers headers = createBasicAuthHeaders(DEFAULT_CREDENTIAL);
+    headers["Accept"] = stringify(contentType);
+
+    return http::post(
+        pid,
+        "api/v1",
+        headers,
+        serialize(contentType, call),
+        stringify(contentType));
+  };
+
+  // We measure both JSON and protobuf formats.
+  const ContentType contentTypes[] =
+    { ContentType::PROTOBUF, ContentType::JSON };
+
+  for (ContentType contentType : contentTypes){
+    v1::master::Call v1Call;
+    v1Call.set_type(v1::master::Call::GET_STATE);
+
+    watch.start();
+
+    Future<http::Response> response =
+      post(master.get()->pid, v1Call, contentType);
+
+    response.await();
+
+    watch.stop();
+
+    ASSERT_EQ(response->status, http::OK().status);
+
+    Future<v1::master::Response> v1Response =
+      deserialize<v1::master::Response>(contentType, response->body);
+
+    ASSERT_TRUE(v1Response->IsInitialized());
+    EXPECT_EQ(v1::master::Response::GET_STATE, v1Response->type());
+
+    cout << "v1 'master::call::GetState' "
+         << contentType << " response took " << watch.elapsed() << endl;
+  }
+}
+
+
 } // namespace tests {
 } // namespace internal {
 } // namespace mesos {