2016-09-20 19:55:38 +08:00
|
|
|
|
#include "stdafx.h"
|
|
|
|
|
#include "acl_cpp/http/websocket.hpp"
|
|
|
|
|
#include "http_servlet.h"
|
|
|
|
|
|
|
|
|
|
http_servlet::http_servlet(acl::redis_client_cluster& cluster, size_t max_conns)
|
|
|
|
|
{
|
|
|
|
|
// <20><><EFBFBD><EFBFBD> session <20>洢<EFBFBD><E6B4A2><EFBFBD><EFBFBD>
|
|
|
|
|
session_ = new acl::redis_session(cluster, max_conns);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
http_servlet::~http_servlet(void)
|
|
|
|
|
{
|
|
|
|
|
delete session_;
|
|
|
|
|
}
|
|
|
|
|
|
2016-10-21 15:02:50 +08:00
|
|
|
|
bool http_servlet::doError(acl::HttpServletRequest&,
|
|
|
|
|
acl::HttpServletResponse& res)
|
|
|
|
|
{
|
|
|
|
|
res.setStatus(400);
|
|
|
|
|
res.setContentType("text/html; charset=");
|
|
|
|
|
// <20><><EFBFBD><EFBFBD> http <20><>Ӧͷ
|
|
|
|
|
if (res.sendHeader() == false)
|
|
|
|
|
return false;
|
|
|
|
|
|
|
|
|
|
// <20><><EFBFBD><EFBFBD> http <20><>Ӧ<EFBFBD><D3A6>
|
|
|
|
|
acl::string buf;
|
|
|
|
|
buf.format("<root error='some error happened!' />\r\n");
|
|
|
|
|
(void) res.getOutputStream().write(buf);
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
2016-09-20 19:55:38 +08:00
|
|
|
|
bool http_servlet::doUnknown(acl::HttpServletRequest&,
|
|
|
|
|
acl::HttpServletResponse& res)
|
|
|
|
|
{
|
|
|
|
|
res.setStatus(400);
|
|
|
|
|
res.setContentType("text/html; charset=");
|
|
|
|
|
// <20><><EFBFBD><EFBFBD> http <20><>Ӧͷ
|
|
|
|
|
if (res.sendHeader() == false)
|
|
|
|
|
return false;
|
|
|
|
|
// <20><><EFBFBD><EFBFBD> http <20><>Ӧ<EFBFBD><D3A6>
|
|
|
|
|
acl::string buf("<root error='unkown request method' />\r\n");
|
|
|
|
|
(void) res.getOutputStream().write(buf);
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
bool http_servlet::doGet(acl::HttpServletRequest& req,
|
|
|
|
|
acl::HttpServletResponse& res)
|
|
|
|
|
{
|
|
|
|
|
printf("in doGet\r\n");
|
|
|
|
|
return doPost(req, res);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
bool http_servlet::doPing(acl::websocket& in, acl::websocket& out)
|
|
|
|
|
{
|
|
|
|
|
unsigned long long len = in.get_frame_payload_len();
|
|
|
|
|
if (len == 0)
|
2016-10-21 15:02:50 +08:00
|
|
|
|
return out.send_frame_pong((const void*) NULL, 0);
|
2016-09-20 19:55:38 +08:00
|
|
|
|
|
|
|
|
|
out.reset().set_frame_fin(true)
|
|
|
|
|
.set_frame_opcode(acl::FRAME_PONG)
|
|
|
|
|
.set_frame_payload_len(len);
|
|
|
|
|
|
|
|
|
|
char buf[8192];
|
|
|
|
|
while (true)
|
|
|
|
|
{
|
|
|
|
|
int ret = in.read_frame_data(buf, sizeof(buf) - 1);
|
|
|
|
|
if (ret == 0)
|
|
|
|
|
break;
|
|
|
|
|
if (ret < 0)
|
|
|
|
|
{
|
|
|
|
|
printf("read_frame_data error\r\n");
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
buf[ret] = 0;
|
|
|
|
|
printf("read: [%s]\r\n", buf);
|
|
|
|
|
if (out.send_frame_data(buf, ret) == false)
|
|
|
|
|
{
|
|
|
|
|
printf("send_frame_data error\r\n");
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
bool http_servlet::doPong(acl::websocket& in, acl::websocket&)
|
|
|
|
|
{
|
|
|
|
|
unsigned long long len = in.get_frame_payload_len();
|
|
|
|
|
if (len == 0)
|
|
|
|
|
return true;
|
|
|
|
|
|
|
|
|
|
char buf[8192];
|
|
|
|
|
while (true)
|
|
|
|
|
{
|
|
|
|
|
int ret = in.read_frame_data(buf, sizeof(buf) - 1);
|
|
|
|
|
if (ret == 0)
|
|
|
|
|
break;
|
|
|
|
|
if (ret < 0)
|
|
|
|
|
{
|
|
|
|
|
printf("read_frame_data error\r\n");
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
buf[ret] = 0;
|
|
|
|
|
printf("read: [%s]\r\n", buf);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
bool http_servlet::doClose(acl::websocket&, acl::websocket&)
|
|
|
|
|
{
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
bool http_servlet::doMsg(acl::websocket& in, acl::websocket& out)
|
|
|
|
|
{
|
|
|
|
|
unsigned long long len = in.get_frame_payload_len();
|
|
|
|
|
out.reset().set_frame_fin(true)
|
|
|
|
|
.set_frame_opcode(acl::FRAME_TEXT)
|
|
|
|
|
.set_frame_payload_len(len);
|
|
|
|
|
|
|
|
|
|
char buf[8192];
|
|
|
|
|
while (true)
|
|
|
|
|
{
|
|
|
|
|
int ret = in.read_frame_data(buf, sizeof(buf) - 1);
|
|
|
|
|
if (ret == 0)
|
|
|
|
|
break;
|
|
|
|
|
if (ret < 0)
|
|
|
|
|
{
|
|
|
|
|
printf("read_frame_data error\r\n");
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
buf[ret] = 0;
|
|
|
|
|
printf("read: [%s]\r\n", buf);
|
|
|
|
|
if (out.send_frame_data(buf, ret) == false)
|
|
|
|
|
{
|
|
|
|
|
printf("send_frame_data error\r\n");
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
sleep(1);
|
|
|
|
|
char info[256];
|
|
|
|
|
snprintf(info, sizeof(info), "hello world!");
|
|
|
|
|
out.reset().set_frame_fin(true)
|
|
|
|
|
.set_frame_opcode(acl::FRAME_TEXT)
|
|
|
|
|
.set_frame_payload_len(strlen(info));
|
|
|
|
|
if (out.send_frame_data(info, strlen(info)) == false)
|
|
|
|
|
{
|
|
|
|
|
printf("send_frame_data error\r\n");
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
sleep(1);
|
|
|
|
|
snprintf(info, sizeof(info), "hello zsx!");
|
|
|
|
|
out.reset().set_frame_fin(true)
|
|
|
|
|
.set_frame_opcode(acl::FRAME_TEXT)
|
|
|
|
|
.set_frame_payload_len(strlen(info));
|
|
|
|
|
if (out.send_frame_data(info, strlen(info)) == false)
|
|
|
|
|
{
|
|
|
|
|
printf("send_frame_data error\r\n");
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
sleep(1);
|
|
|
|
|
snprintf(info, sizeof(info), "GoodBye!");
|
|
|
|
|
out.reset().set_frame_fin(true)
|
|
|
|
|
.set_frame_opcode(acl::FRAME_TEXT)
|
|
|
|
|
.set_frame_payload_len(strlen(info));
|
|
|
|
|
if (out.send_frame_data(info, strlen(info)) == false)
|
|
|
|
|
{
|
|
|
|
|
printf("send_frame_data error\r\n");
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
bool http_servlet::doWebsocket(acl::HttpServletRequest& req,
|
|
|
|
|
acl::HttpServletResponse&)
|
|
|
|
|
{
|
|
|
|
|
acl::socket_stream& ss = req.getSocketStream();
|
|
|
|
|
acl::websocket in(ss), out(ss);
|
|
|
|
|
|
|
|
|
|
while (true)
|
|
|
|
|
{
|
|
|
|
|
if (in.read_frame_head() == false)
|
|
|
|
|
{
|
|
|
|
|
printf("read_frame_head error\r\n");
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
bool ret;
|
|
|
|
|
unsigned char opcode = in.get_frame_opcode();
|
|
|
|
|
|
|
|
|
|
printf("opcode: 0x%x\r\n", opcode);
|
|
|
|
|
|
|
|
|
|
switch (opcode)
|
|
|
|
|
{
|
|
|
|
|
case acl::FRAME_PING:
|
|
|
|
|
ret = doPing(in, out);
|
|
|
|
|
break;
|
|
|
|
|
case acl::FRAME_PONG:
|
|
|
|
|
ret = doPong(in, out);
|
|
|
|
|
break;
|
|
|
|
|
case acl::FRAME_CLOSE:
|
|
|
|
|
ret = doClose(in, out);
|
|
|
|
|
break;
|
|
|
|
|
case acl::FRAME_TEXT:
|
|
|
|
|
case acl::FRAME_BINARY:
|
|
|
|
|
ret = doMsg(in, out);
|
|
|
|
|
break;
|
|
|
|
|
case acl::FRAME_CONTINUATION:
|
|
|
|
|
ret = false;
|
|
|
|
|
break;
|
|
|
|
|
default:
|
|
|
|
|
ret = false;
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (ret == false)
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// XXX: NOT REACHED
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
2016-10-21 15:02:50 +08:00
|
|
|
|
bool http_servlet::doPost(acl::HttpServletRequest& req,
|
2016-09-20 19:55:38 +08:00
|
|
|
|
acl::HttpServletResponse& res)
|
|
|
|
|
{
|
2016-10-21 15:02:50 +08:00
|
|
|
|
res.setContentType("text/html; charset=utf-8") // <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ӧ<EFBFBD>ַ<EFBFBD><D6B7><EFBFBD>
|
2016-09-20 19:55:38 +08:00
|
|
|
|
.setContentEncoding(true) // <20><><EFBFBD><EFBFBD><EFBFBD>Ƿ<EFBFBD>ѹ<EFBFBD><D1B9><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
|
|
|
|
.setChunkedTransferEncoding(false); // <20><><EFBFBD><EFBFBD> chunk <20><><EFBFBD>䷽ʽ
|
|
|
|
|
|
2016-10-21 15:02:50 +08:00
|
|
|
|
acl::string html_file;
|
|
|
|
|
html_file << var_cfg_html_path << "/client.html";
|
|
|
|
|
acl::string buf;
|
|
|
|
|
if (acl::ifstream::load(html_file, &buf) == false)
|
|
|
|
|
{
|
|
|
|
|
logger_error("load %s error %s",
|
|
|
|
|
html_file.c_str(), acl::last_serror());
|
|
|
|
|
return doError(req, res);
|
|
|
|
|
}
|
2016-09-20 19:55:38 +08:00
|
|
|
|
|
|
|
|
|
// <20><><EFBFBD><EFBFBD> http <20><>Ӧ<EFBFBD>壬<EFBFBD><E5A3AC>Ϊ<EFBFBD><CEAA><EFBFBD><EFBFBD><EFBFBD><EFBFBD> chunk <20><><EFBFBD><EFBFBD>ģʽ<C4A3><CABD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ҫ<EFBFBD><D2AA><EFBFBD><EFBFBD><EFBFBD><EFBFBD>һ<EFBFBD><D2BB>
|
|
|
|
|
// res.write <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϊ 0 <20>Ա<EFBFBD>ʾ chunk <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ݽ<EFBFBD><DDBD><EFBFBD>
|
|
|
|
|
return res.write(buf) && res.write(NULL, 0);
|
|
|
|
|
}
|