Added a wrapper for HttpProcess to prevent segfaults during test failures. Review: https://reviews.apache.org/r/32350
Project: http://git-wip-us.apache.org/repos/asf/mesos/repo Commit: http://git-wip-us.apache.org/repos/asf/mesos/commit/a0d201b7 Tree: http://git-wip-us.apache.org/repos/asf/mesos/tree/a0d201b7 Diff: http://git-wip-us.apache.org/repos/asf/mesos/diff/a0d201b7 Branch: refs/heads/master Commit: a0d201b711e56b9fdec464f2d4cb25c2a8a06a79 Parents: 91034cd Author: Benjamin Mahler <[email protected]> Authored: Fri Mar 20 15:32:54 2015 -0700 Committer: Benjamin Mahler <[email protected]> Committed: Tue Mar 24 16:48:22 2015 -0700 ---------------------------------------------------------------------- 3rdparty/libprocess/src/tests/http_tests.cpp | 103 ++++++++++------------ 1 file changed, 49 insertions(+), 54 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/mesos/blob/a0d201b7/3rdparty/libprocess/src/tests/http_tests.cpp ---------------------------------------------------------------------- diff --git a/3rdparty/libprocess/src/tests/http_tests.cpp b/3rdparty/libprocess/src/tests/http_tests.cpp index 17fb092..e254506 100644 --- a/3rdparty/libprocess/src/tests/http_tests.cpp +++ b/3rdparty/libprocess/src/tests/http_tests.cpp @@ -38,10 +38,19 @@ using testing::EndsWith; using testing::Invoke; using testing::Return; + class HttpProcess : public Process<HttpProcess> { public: - HttpProcess() + HttpProcess() {} + + MOCK_METHOD1(body, Future<http::Response>(const http::Request&)); + MOCK_METHOD1(pipe, Future<http::Response>(const http::Request&)); + MOCK_METHOD1(get, Future<http::Response>(const http::Request&)); + MOCK_METHOD1(post, Future<http::Response>(const http::Request&)); + +protected: + virtual void initialize() { route("/auth", None(), &HttpProcess::auth); route("/body", None(), &HttpProcess::body); @@ -59,24 +68,33 @@ public: } return http::OK(); } - - MOCK_METHOD1(body, Future<http::Response>(const http::Request&)); - MOCK_METHOD1(pipe, Future<http::Response>(const http::Request&)); - MOCK_METHOD1(get, Future<http::Response>(const http::Request&)); - MOCK_METHOD1(post, Future<http::Response>(const http::Request&)); }; -TEST(HTTP, auth) +class Http { - ASSERT_TRUE(GTEST_IS_THREADSAFE); +public: + Http() : process(new HttpProcess()) + { + spawn(process.get()); + } + + ~Http() + { + terminate(process.get()); + wait(process.get()); + } - HttpProcess process; + Owned<HttpProcess> process; +}; - spawn(process); + +TEST(HTTP, auth) +{ + Http http; // Test the case where there is no auth. - Future<http::Response> noAuthFuture = http::get(process.self(), "auth"); + Future<http::Response> noAuthFuture = http::get(http.process->self(), "auth"); AWAIT_READY(noAuthFuture); EXPECT_EQ(http::statuses[401], noAuthFuture.get().status); @@ -88,7 +106,7 @@ TEST(HTTP, auth) headers["Authorization"] = "Basic " + base64::encode("testuser:wrongpass"); Future<http::Response> wrongAuthFuture = - http::get(process.self(), "auth", None(), headers); + http::get(http.process->self(), "auth", None(), headers); AWAIT_READY(wrongAuthFuture); EXPECT_EQ(http::statuses[401], wrongAuthFuture.get().status); @@ -99,23 +117,16 @@ TEST(HTTP, auth) headers["Authorization"] = "Basic " + base64::encode("testuser:testpass"); Future<http::Response> rightAuthFuture = - http::get(process.self(), "auth", None(), headers); + http::get(http.process->self(), "auth", None(), headers); AWAIT_READY(rightAuthFuture); EXPECT_EQ(http::statuses[200], rightAuthFuture.get().status); - - terminate(process); - wait(process); } TEST(HTTP, Endpoints) { - ASSERT_TRUE(GTEST_IS_THREADSAFE); - - HttpProcess process; - - spawn(process); + Http http; // First hit '/body' (using explicit sockets and HTTP/1.0). Try<Socket> create = Socket::create(); @@ -123,17 +134,17 @@ TEST(HTTP, Endpoints) Socket socket = create.get(); - AWAIT_READY(socket.connect(process.self().address)); + AWAIT_READY(socket.connect(http.process->self().address)); std::ostringstream out; - out << "GET /" << process.self().id << "/body" + out << "GET /" << http.process->self().id << "/body" << " HTTP/1.0\r\n" << "Connection: Keep-Alive\r\n" << "\r\n"; const string& data = out.str(); - EXPECT_CALL(process, body(_)) + EXPECT_CALL(*http.process, body(_)) .WillOnce(Return(http::OK())); AWAIT_READY(socket.send(data)); @@ -149,11 +160,11 @@ TEST(HTTP, Endpoints) ok.reader = pipe.reader(); Future<Nothing> request; - EXPECT_CALL(process, pipe(_)) + EXPECT_CALL(*http.process, pipe(_)) .WillOnce(DoAll(FutureSatisfy(&request), Return(ok))); - Future<http::Response> future = http::get(process.self(), "pipe"); + Future<http::Response> future = http::get(http.process->self(), "pipe"); AWAIT_READY(request); @@ -166,9 +177,6 @@ TEST(HTTP, Endpoints) EXPECT_EQ(http::statuses[200], future.get().status); EXPECT_SOME_EQ("chunked", future.get().headers.get("Transfer-Encoding")); EXPECT_EQ("Hello World\n", future.get().body); - - terminate(process); - wait(process); } @@ -353,31 +361,24 @@ http::Response validateGetWithQuery(const http::Request& request) TEST(HTTP, Get) { - ASSERT_TRUE(GTEST_IS_THREADSAFE); - - HttpProcess process; + Http http; - spawn(process); - - EXPECT_CALL(process, get(_)) + EXPECT_CALL(*http.process, get(_)) .WillOnce(Invoke(validateGetWithoutQuery)); - Future<http::Response> noQueryFuture = http::get(process.self(), "get"); + Future<http::Response> noQueryFuture = http::get(http.process->self(), "get"); AWAIT_READY(noQueryFuture); ASSERT_EQ(http::statuses[200], noQueryFuture.get().status); - EXPECT_CALL(process, get(_)) + EXPECT_CALL(*http.process, get(_)) .WillOnce(Invoke(validateGetWithQuery)); Future<http::Response> queryFuture = - http::get(process.self(), "get", "foo=bar"); + http::get(http.process->self(), "get", "foo=bar"); AWAIT_READY(queryFuture); ASSERT_EQ(http::statuses[200], queryFuture.get().status); - - terminate(process); - wait(process); } @@ -395,23 +396,19 @@ http::Response validatePost(const http::Request& request) TEST(HTTP, Post) { - ASSERT_TRUE(GTEST_IS_THREADSAFE); - - HttpProcess process; - - spawn(process); + Http http; // Test the case where there is a content type but no body. Future<http::Response> future = - http::post(process.self(), "post", None(), None(), "text/plain"); + http::post(http.process->self(), "post", None(), None(), "text/plain"); AWAIT_EXPECT_FAILED(future); - EXPECT_CALL(process, post(_)) + EXPECT_CALL(*http.process, post(_)) .WillOnce(Invoke(validatePost)); future = http::post( - process.self(), + http.process->self(), "post", None(), "This is the payload.", @@ -424,19 +421,17 @@ TEST(HTTP, Post) hashmap<string, string> headers; headers["Content-Type"] = "text/plain"; - EXPECT_CALL(process, post(_)) + EXPECT_CALL(*http.process, post(_)) .WillOnce(Invoke(validatePost)); future = - http::post(process.self(), "post", headers, "This is the payload."); + http::post(http.process->self(), "post", headers, "This is the payload."); AWAIT_READY(future); ASSERT_EQ(http::statuses[200], future.get().status); - - terminate(process); - wait(process); } + TEST(HTTP, QueryEncodeDecode) { // If we use Type<a, b> directly inside a macro without surrounding
