You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
134 lines
3.1 KiB
C++
134 lines
3.1 KiB
C++
#ifndef WEBCC_MESSAGE_H_
|
|
#define WEBCC_MESSAGE_H_
|
|
|
|
#include <cassert>
|
|
#include <string>
|
|
#include <utility> // for move()
|
|
#include <vector>
|
|
|
|
#include "webcc/common.h"
|
|
#include "webcc/globals.h"
|
|
|
|
namespace webcc {
|
|
|
|
class Message;
|
|
std::ostream& operator<<(std::ostream& os, const Message& message);
|
|
|
|
// Base class for HTTP request and response messages.
|
|
class Message {
|
|
public:
|
|
Message() : content_length_(kInvalidLength) {
|
|
}
|
|
|
|
virtual ~Message() = default;
|
|
|
|
const std::string& start_line() const {
|
|
return start_line_;
|
|
}
|
|
|
|
void set_start_line(const std::string& start_line) {
|
|
start_line_ = start_line;
|
|
}
|
|
|
|
std::size_t content_length() const {
|
|
return content_length_;
|
|
}
|
|
|
|
const std::string& content() const {
|
|
return content_;
|
|
}
|
|
|
|
bool IsConnectionKeepAlive() const;
|
|
|
|
void SetHeader(Header&& header) {
|
|
headers_.Set(std::move(header.first), std::move(header.second));
|
|
}
|
|
|
|
void SetHeader(const std::string& key, const std::string& value) {
|
|
headers_.Set(key, value);
|
|
}
|
|
|
|
const std::string& GetHeader(const std::string& key,
|
|
bool* existed = nullptr) const {
|
|
return headers_.Get(key, existed);
|
|
}
|
|
|
|
bool HasHeader(const std::string& key) const {
|
|
return headers_.Has(key);
|
|
}
|
|
|
|
ContentEncoding GetContentEncoding() const;
|
|
|
|
// Return true if header Accept-Encoding contains "gzip".
|
|
bool AcceptEncodingGzip() const;
|
|
|
|
const ContentType& content_type() const {
|
|
return content_type_;
|
|
}
|
|
|
|
// TODO: Set header?
|
|
void SetContentType(const ContentType& content_type) {
|
|
content_type_ = content_type;
|
|
}
|
|
|
|
void SetContentType(const std::string& content_type) {
|
|
SetHeader(headers::kContentType, content_type);
|
|
}
|
|
|
|
// Example: SetContentType("application/json", "utf-8")
|
|
void SetContentType(const std::string& media_type,
|
|
const std::string& charset);
|
|
|
|
void SetContent(std::string&& content, bool set_length);
|
|
|
|
// Prepare payload.
|
|
virtual void Prepare();
|
|
|
|
const Payload& payload() const {
|
|
return payload_;
|
|
}
|
|
|
|
// Copy the exact payload to the given output stream.
|
|
void CopyPayload(std::ostream& os) const;
|
|
|
|
// Copy the exact payload to the given string.
|
|
void CopyPayload(std::string* str) const;
|
|
|
|
// Dump to output stream.
|
|
void Dump(std::ostream& os, std::size_t indent = 0,
|
|
const std::string& prefix = "") const;
|
|
|
|
// Dump to string, only used by logger.
|
|
std::string Dump(std::size_t indent = 0,
|
|
const std::string& prefix = "") const;
|
|
|
|
protected:
|
|
void SetContentLength(std::size_t content_length) {
|
|
content_length_ = content_length;
|
|
SetHeader(headers::kContentLength, std::to_string(content_length));
|
|
}
|
|
|
|
// Get the timestamp for HTTP Date header field.
|
|
// E.g., Wed, 21 Oct 2015 07:28:00 GMT
|
|
// See: https://tools.ietf.org/html/rfc7231#section-7.1.1.2
|
|
std::string GetTimestamp();
|
|
|
|
protected:
|
|
std::string start_line_;
|
|
|
|
std::string content_;
|
|
|
|
ContentType content_type_;
|
|
|
|
std::size_t content_length_;
|
|
|
|
Headers headers_;
|
|
|
|
// NOTE: The payload itself doesn't hold the memory!
|
|
Payload payload_;
|
|
};
|
|
|
|
} // namespace webcc
|
|
|
|
#endif // WEBCC_MESSAGE_H_
|