Skip to content

Commit

Permalink
add webservice unit-test for pull request #50
Browse files Browse the repository at this point in the history
  • Loading branch information
cyshi committed Jan 20, 2016
1 parent 5fe3eac commit 9bd6aa5
Show file tree
Hide file tree
Showing 6 changed files with 160 additions and 43 deletions.
22 changes: 15 additions & 7 deletions src/sofa/pbrpc/buffer.cc
Original file line number Diff line number Diff line change
Expand Up @@ -309,17 +309,25 @@ bool WriteBuffer::Extend()
return true;
}

int WriteBuffer::Append(const std::string& data)
bool WriteBuffer::Append(const std::string& data)
{
size_t data_size = data.size();
int64_t head = Reserve(data_size);
if (head < 0)
return Append(data.c_str(), data.size());
}

bool WriteBuffer::Append(const char* data, int size)
{
if (size <= 0)
{
return -1;
return false;
}

SetData(head, data.c_str(), data_size);
return 0;
int64_t head = Reserve(size);
if (head < 0)
{
return false;
}
SetData(head, data, size);
return true;
}

} // namespace pbrpc
Expand Down
7 changes: 4 additions & 3 deletions src/sofa/pbrpc/buffer.h
Original file line number Diff line number Diff line change
Expand Up @@ -118,9 +118,10 @@ class WriteBuffer : public google::protobuf::io::ZeroCopyOutputStream
int64 ByteCount() const;

// Append string to the buffer
// If succeed, return 0
// If failed, return -1
int Append(const std::string& data);
// If succeed, return true
// If failed, return false
bool Append(const std::string& data);
bool Append(const char* data, int size);

private:
// Add a new block to the end of the buffer.
Expand Down
67 changes: 41 additions & 26 deletions src/sofa/pbrpc/http.h
Original file line number Diff line number Diff line change
Expand Up @@ -27,31 +27,46 @@ struct HTTPRequest
POST = 2
};

Type type; // method in http header
// method in http header
Type type;

const std::map<std::string, std::string>* headers; // http request headers
// http request headers
const std::map<std::string, std::string>* headers;

const std::map<std::string, std::string>* query_params; // query parameters
// http://www.baidu.com/s?k=123
// will be parsed to {"k":"123"}
// query parameters
// http://www.baidu.com/s?k=123
// will be parsed to {"k":"123"}
const std::map<std::string, std::string>* query_params;

std::string path; // PATH field in http request
// for example, http://www.baidu.com/s?k=123
// path is "/s"
// PATH field in http request
// for example, http://www.baidu.com/s?k=123
// path is "/s"
std::string path;

std::string ip; // server ip adddress
// server ip adddress
std::string server_ip;

uint16_t port; // server port
// server port
uint16_t server_port;

ReadBufferPtr body; // the body field describes HTTP post body
// using body->ToString() to get the std::string
// client ip address
std::string client_ip;

// client port
uint16_t client_port;

// the body field describes HTTP post body
// using body->ToString() to get the std::string
ReadBufferPtr body;

HTTPRequest() : type(GET)
, headers(NULL)
, query_params(NULL)
, path()
, ip()
, port(0)
, server_ip()
, server_port(0)
, client_ip()
, client_port()
, body()
{ }
};
Expand All @@ -61,18 +76,18 @@ struct HTTPRequest
*/
struct HTTPResponse
{
std::string status_line; // HTTP server status line, reference to RFC2616
// default value is 200 OK, means this request dealed
// normally
std::string content_type; // content-type field in http response header
// default is "text/html", return a plain text to
// http client

WriteBufferPtr content; // page content will return to http client
// which maybe a web browser
// using content->Append(std::string) to set response body
// HTTP server status line, reference to RFC2616
// default value is 200 OK, means this request dealed normally
std::string status_line;

// content-type field in http response header
// default is "text/html", return a plain text to http client
std::string content_type;

// page content will return to http client which maybe a web browser
// using content->Append(std::string) to set response body
WriteBufferPtr content;

HTTPResponse() : status_line("HTTP/1.1 200 OK")
, content_type("text/html; charset=UTF-8")
, content(new WriteBuffer())
Expand Down
15 changes: 9 additions & 6 deletions src/sofa/pbrpc/web_service.cc
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ namespace sofa {
namespace pbrpc {

static const std::string ROOT_PATH = "/";
static const std::string PATH_SPLITTER = "/";

static std::string GetHostName(const std::string& ip)
{
Expand Down Expand Up @@ -62,7 +63,7 @@ static std::string format_number(T num)
static std::string FormatPath(const std::string& path)
{
std::vector<std::string> path_vec;
StringUtils::split(path, ROOT_PATH, &path_vec);
StringUtils::split(path, PATH_SPLITTER, &path_vec);
std::stringstream os;
for (size_t i = 0; i < path_vec.size(); ++i)
{
Expand Down Expand Up @@ -210,8 +211,10 @@ bool WebService::RoutePage(
request.body = http_rpc_request->_req_body;
request.headers = &http_rpc_request->_headers;
request.query_params = &http_rpc_request->_query_params;
request.ip = HostOfRpcEndpoint(http_rpc_request->_local_endpoint);
request.port = PortOfRpcEndpoint(http_rpc_request->_local_endpoint);
request.server_ip = HostOfRpcEndpoint(http_rpc_request->_local_endpoint);
request.server_port = PortOfRpcEndpoint(http_rpc_request->_local_endpoint);
request.client_ip = HostOfRpcEndpoint(http_rpc_request->_remote_endpoint);
request.client_port = PortOfRpcEndpoint(http_rpc_request->_remote_endpoint);

bool ret = false;
const std::string& method = http_rpc_request->_method;
Expand Down Expand Up @@ -383,9 +386,9 @@ void WebService::PageFooter(std::ostream& out)
void WebService::ServerBrief(std::ostream& out,
const HTTPRequest& request)
{
out << "<h1>" << GetHostName(request.ip) << "</h1>"
<< "<b>IP:</b> " << request.ip << "<br>"
<< "<b>Port:</b> " << request.port << "<br>"
out << "<h1>" << GetHostName(request.server_ip) << "</h1>"
<< "<b>IP:</b> " << request.server_ip << "<br>"
<< "<b>Port:</b> " << request.server_port << "<br>"
<< "<b>Started:</b> " << ptime_to_string(_service_pool->RpcServer()->GetStartTime()) << "<br>"
<< "<b>Version:</b> " << SOFA_PBRPC_VERSION << "<br>"
<< "<b>Compiled:</b> " << compile_info() << "<br>";
Expand Down
6 changes: 5 additions & 1 deletion unit-test/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,8 @@ TESTS = \
test_ext_closure \
test_thread_group \
test_timeout_manager \
test_io_service_pool
test_io_service_pool \
test_web_service

all: $(TESTS)

Expand Down Expand Up @@ -99,6 +100,9 @@ test_timeout_manager: test_timeout_manager.o libgtest.a
test_io_service_pool: test_io_service_pool.o libgtest.a
$(CXX) $^ -o $@ $(LIBRARY) $(LDFLAGS)

test_web_service: test_web_service.o libgtest.a
$(CXX) $^ -o $@ $(LIBRARY) $(LDFLAGS)

%.pb.o: %.pb.cc
$(CXX) $(CXXFLAGS) -c $< -o $@

Expand Down
86 changes: 86 additions & 0 deletions unit-test/test_web_service.cc
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
// Copyright (c) 2016 Baidu.com, Inc. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
//
// Author: [email protected] (Shi Chengyi)

#include <gtest/gtest.h>
#include <sofa/pbrpc/common_internal.h>
#include <sofa/pbrpc/web_service.h>

using namespace ::sofa::pbrpc;

class WebServiceTest: public ::testing::Test
{
protected:
WebServiceTest() { }

virtual ~WebServiceTest() { }

virtual void SetUp() {
_service_pool.reset(new ServicePool(NULL));
}

virtual void TearDown() {
_service_pool.reset();
}

ServicePoolPtr _service_pool;
};

TEST_F(WebServiceTest, RegisterServlet)
{
WebServicePtr web_service(new WebService(_service_pool));
Servlet s = (Servlet) 0x01;
std::string path = "/a/b/c";
bool ret = web_service->RegisterServlet(path, s);
ASSERT_TRUE(ret);
ret = web_service->RegisterServlet(path, s);
ASSERT_FALSE(ret);
ret = web_service->UnregisterServlet(path);
ASSERT_TRUE(ret);
}

TEST_F(WebServiceTest, FindServlet)
{
WebServicePtr web_service(new WebService(_service_pool));
Servlet null_servlet = web_service->FindServlet("null");
ASSERT_TRUE(NULL == null_servlet);

Servlet s1 = (Servlet) 0x01;
Servlet s2 = (Servlet) 0x02;
Servlet s3 = (Servlet) 0x03;

std::string p1 = "/";
std::string p2 = "/a";
std::string p3 = "/a/b";

web_service->RegisterServlet(p1, s1);
web_service->RegisterServlet(p2, s2);
web_service->RegisterServlet(p3, s3);

Servlet find = web_service->FindServlet(p1);
ASSERT_EQ(find, s1);

std::string path = "/null";
find = web_service->FindServlet(path);
ASSERT_TRUE(NULL == null_servlet);

path = "/a";
find = web_service->FindServlet(path);
ASSERT_EQ(find, s2);

path = "/a/b/something";
find = web_service->FindServlet(path);
ASSERT_EQ(find, s3);

web_service->UnregisterServlet(p1);
web_service->UnregisterServlet(p2);
web_service->UnregisterServlet(p3);
}

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

0 comments on commit 9bd6aa5

Please sign in to comment.