Skip to content

Commit

Permalink
added request::is_websocket() and response::set_header(name, value)
Browse files Browse the repository at this point in the history
  • Loading branch information
ponomarev committed Mar 5, 2011
1 parent 336df41 commit 313c36a
Show file tree
Hide file tree
Showing 13 changed files with 104 additions and 19 deletions.
8 changes: 7 additions & 1 deletion include/details/connection_base.hpp
Expand Up @@ -29,6 +29,7 @@

#include "details/guard.hpp"
#include "details/websocket_info.hpp"
#include "details/response_impl.hpp"

namespace xiva { namespace details {

Expand Down Expand Up @@ -60,9 +61,11 @@ class connection_base {
boost::shared_ptr<guard> const& get_guard() const;

protected:
void init(request_impl const &req, bool secure);
void init(request_impl &req, bool secure);
void init_formatters(connection_data const &cdata, request_impl const &req, response_impl const &resp);

void handle_response(response_impl const &resp);

bool print_message(message const &msg, std::streambuf &buf);

static bool print_policy_data(std::string const &data, std::streambuf &buf);
Expand All @@ -77,10 +80,13 @@ class connection_base {
connection_base(connection_base const &);
connection_base& operator = (connection_base const &);

void print_common_headers(std::string const &content_type, std::streambuf &buf) const;

std::auto_ptr<formatters_data> fmt_data_;
websocket_info ws_info_;
std::string name_;
boost::shared_ptr<guard> guard_;
response_impl::headers_ptr_type headers_;
};

inline std::string const&
Expand Down
1 change: 1 addition & 0 deletions include/details/connection_impl.hpp
Expand Up @@ -185,6 +185,7 @@ template <typename ConnectionTraits> void
connection_impl<ConnectionTraits>::handled(request_impl const &req, response_impl const &resp) {
timer_.cancel();
try {
connection_base_type::handle_response(resp);
std::string const *content = resp.content_ptr();
if (NULL != content) {
write_static_content(resp, *content);
Expand Down
21 changes: 18 additions & 3 deletions include/details/request_impl.hpp
Expand Up @@ -53,7 +53,10 @@ class request_impl {

bool has_cookie(std::string const &name) const;
std::string const& cookie(std::string const &name) const;


bool is_websocket() const;
void set_websocket();

void swap(request_impl &other) throw ();

private:
Expand Down Expand Up @@ -85,17 +88,19 @@ class request_impl {
param_map_type params_;
header_map_type headers_;
cookie_map_type cookies_;
bool is_websocket_;
};


inline
request_impl::request_impl() :
params_(), headers_(), cookies_()
params_(), headers_(), cookies_(), is_websocket_(false)
{
}

template <typename Iter> inline
request_impl::request_impl(Iter begin, Iter end) :
params_(), headers_(), cookies_()
params_(), headers_(), cookies_(), is_websocket_(false)
{
init(begin, end);
}
Expand All @@ -110,6 +115,16 @@ request_impl::body() const {
return body_;
}

inline bool
request_impl::is_websocket() const {
return is_websocket_;
}

inline void
request_impl::set_websocket() {
is_websocket_ = true;
}

template <typename Iter> inline void
request_impl::init(Iter begin, Iter end) {

Expand Down
23 changes: 20 additions & 3 deletions include/details/response_impl.hpp
Expand Up @@ -21,8 +21,11 @@
#include <string>
#include <map>

#include <boost/shared_ptr.hpp>

#include "xiva/shared.hpp"
#include "xiva/channel_info.hpp"
#include "details/functors.hpp"

namespace xiva { namespace details {

Expand All @@ -32,6 +35,11 @@ class response_impl {
response_impl();
virtual ~response_impl();

typedef std::map<channel_info, std::string> channels_data_type;

typedef std::map<std::string, std::string, ci_less<std::string> > headers_data_type;
typedef boost::shared_ptr<headers_data_type> headers_ptr_type;

void swap(response_impl &impl) throw ();

std::string const& content_type() const;
Expand All @@ -40,9 +48,12 @@ class response_impl {
std::string const& default_formatter_id() const;
void formatter_id(std::string const &fmt_id);

std::map<channel_info, std::string> const& channels_data() const;
channels_data_type const& channels_data() const;
void formatter_by_channel(channel_info const &ch_info, std::string const &fmt_id);

headers_ptr_type const& headers() const;
void set_header(std::string const &name, std::string const &value);

bool single_message() const;
void single_message(bool value);

Expand All @@ -57,7 +68,8 @@ class response_impl {
private:
std::string type_;
std::string formatter_id_;
std::map<channel_info, std::string> channels_data_;
channels_data_type channels_data_;
headers_ptr_type headers_;
std::string content_;
std::string const *content_ptr_;
bool single_message_;
Expand All @@ -84,11 +96,16 @@ response_impl::formatter_id(std::string const &fmt_id) {
formatter_id_.assign(fmt_id);
}

inline std::map<channel_info, std::string> const&
inline response_impl::channels_data_type const&
response_impl::channels_data() const {
return channels_data_;
}

inline response_impl::headers_ptr_type const&
response_impl::headers() const {
return headers_;
}

inline bool
response_impl::single_message() const {
return single_message_;
Expand Down
2 changes: 1 addition & 1 deletion include/details/websocket_info.hpp
Expand Up @@ -33,7 +33,7 @@ class websocket_info {
bool empty() const;
bool valid() const;

void parse(request_impl const &req, bool secure);
bool parse(request_impl const &req, bool secure);

static void write_message(std::ostream &stream, std::string const &msg);

Expand Down
2 changes: 2 additions & 0 deletions include/xiva/request.hpp
Expand Up @@ -44,6 +44,8 @@ class XIVA_API request {
bool has_cookie(std::string const &name) const;
std::string const& cookie(std::string const &name) const;

bool is_websocket() const;

private:
details::request_impl const &impl_;
};
Expand Down
2 changes: 2 additions & 0 deletions include/xiva/response.hpp
Expand Up @@ -38,6 +38,8 @@ class XIVA_API response {

void formatter_by_channel(channel_info const &ch_info, std::string const &fmt_id);

void set_header(std::string const &name, std::string const &value);

void single_message(bool value);

void content(std::string const &body);
Expand Down
37 changes: 29 additions & 8 deletions library/connection_base.cpp
Expand Up @@ -13,6 +13,7 @@
#include "details/formatters_factory.hpp"
#include "details/http_constants.hpp"
#include "details/http.hpp"
#include "details/request_impl.hpp"

namespace xiva { namespace details {

Expand All @@ -30,15 +31,22 @@ connection_base::id() const {
}

void
connection_base::init(request_impl const &req, bool secure) {
ws_info_.parse(req, secure);
connection_base::init(request_impl &req, bool secure) {
if (ws_info_.parse(req, secure)) {
req.set_websocket();
}
}

void
connection_base::init_formatters(connection_data const &cdata, request_impl const &req, response_impl const &resp) {
fmt_data_ = cdata.fmt_factory().create_formatters_data(req, resp);
}

void
connection_base::handle_response(response_impl const &resp) {
headers_ = resp.headers();
}

bool
connection_base::allow_message(message const &msg, message_filter const *filter) const {
if (NULL == fmt_data_.get()) {
Expand Down Expand Up @@ -120,9 +128,7 @@ connection_base::print_headers(std::string const &content_type, std::streambuf &
stream << http_header::connection_close();
stream << http_header("Transfer-Encoding", "chunked");
}
stream << http_date(boost::posix_time::second_clock::universal_time());
stream << http_header::server();
stream << http_header("Content-Type", content_type.c_str());
print_common_headers(content_type, buf);
stream << http_constants<char>::endl;
if (is_websocket) {
ws_info_.write_body(stream);
Expand All @@ -142,15 +148,30 @@ connection_base::print_static_content(

stream << http_status(200);
stream << http_header::connection_close();
stream << http_date(boost::posix_time::second_clock::universal_time());
stream << http_header::server();
stream << http_header("Content-Type", content_type.c_str());
print_common_headers(content_type, buf);
stream << "Content-Length: " << content.size() << http_constants<char>::endl;
stream << http_constants<char>::endl;
stream << content;
return true;
}

void
connection_base::print_common_headers(std::string const &content_type, std::streambuf &buf) const {

std::ostream stream(&buf);

stream << http_date(boost::posix_time::second_clock::universal_time());
stream << http_header::server();
stream << http_header("Content-Type", content_type.c_str());

if (headers_ && !headers_->empty()) {
response_impl::headers_data_type::const_iterator it = headers_->begin(), end = headers_->end();
for (; it != end; ++it) {
stream << http_header(it->first.c_str(), it->second.c_str());
}
}
}

bool
connection_base::print_message_content(std::string const &content, std::streambuf &buf) const {

Expand Down
5 changes: 5 additions & 0 deletions library/request.cpp
Expand Up @@ -52,4 +52,9 @@ request::cookie(std::string const &name) const {
return impl_.cookie(name);
}

bool
request::is_websocket() const {
return impl_.is_websocket();
}

} // namespace
2 changes: 2 additions & 0 deletions library/request_impl.cpp
Expand Up @@ -39,6 +39,7 @@ get(Map const &map, std::string const &name) {
return (map.end() != i) ? i->second : http_constants<char>::empty_string;
}


request_impl::~request_impl() {
}

Expand All @@ -48,6 +49,7 @@ request_impl::swap(request_impl &other) throw () {
std::swap(params_, other.params_);
std::swap(headers_, other.headers_);
std::swap(cookies_, other.cookies_);
std::swap(is_websocket_, other.is_websocket_);
}

bool
Expand Down
5 changes: 5 additions & 0 deletions library/response.cpp
Expand Up @@ -32,6 +32,11 @@ response::formatter_by_channel(channel_info const &ch_info, std::string const &f
impl_.formatter_by_channel(ch_info, fmt_id);
}

void
response::set_header(std::string const &name, std::string const &value) {
impl_.set_header(name, value);
}

void
response::single_message(bool value) {
impl_.single_message(value);
Expand Down
10 changes: 9 additions & 1 deletion library/response_impl.cpp
Expand Up @@ -3,7 +3,7 @@

namespace xiva { namespace details {

response_impl::response_impl() : content_ptr_(NULL), single_message_(false)
response_impl::response_impl() : headers_(new headers_data_type()), content_ptr_(NULL), single_message_(false)
{
}

Expand All @@ -18,6 +18,14 @@ response_impl::swap(response_impl &other) throw () {
std::swap(content_ptr_, other.content_ptr_);
std::swap(single_message_, other.single_message_);
std::swap(channels_data_, other.channels_data_);
std::swap(headers_, other.headers_);
}

void
response_impl::set_header(std::string const &name, std::string const &value) {
if (!name.empty()) {
headers_->insert(std::make_pair(name, value));
}
}

void
Expand Down
5 changes: 3 additions & 2 deletions library/websocket_info.cpp
Expand Up @@ -128,11 +128,11 @@ get_websocket_key_value(char const *s, std::string const &key) {
return v32;
}

void
bool
websocket_info::parse(request_impl const &req, bool secure) {

if (req.header(WS_STR_CONNECTION) != WS_STR_UPGRADE || req.header(WS_STR_UPGRADE) != WS_STR_WEBSOCKET) {
return;
return false;
}
empty_ = false;

Expand Down Expand Up @@ -175,6 +175,7 @@ websocket_info::parse(request_impl const &req, bool secure) {

origin_ = req.header(WS_STR_ORIGIN);
protocol_ = req.header(WS_STR_WEBSOCKET_PROTOCOL);
return true;
}

void
Expand Down

0 comments on commit 313c36a

Please sign in to comment.