|
- ///////////////////////////////////////////////////////////////////////////////
- //
- // Copyright (C) 2008-2012 Artyom Beilis (Tonkikh) <artyomtnk@yahoo.com>
- //
- // See accompanying file COPYING.TXT file for licensing details.
- //
- ///////////////////////////////////////////////////////////////////////////////
- #ifndef CPPCMS_HTTP_RESPONSE_H
- #define CPPCMS_HTTP_RESPONSE_H
-
- #include <cppcms/defs.h>
- #include <booster/noncopyable.h>
- #include <booster/hold_ptr.h>
-
- #include <string>
- #include <iostream>
- #include <cppcms/cstdint.h>
-
- namespace booster{
- namespace system {
- class error_code;
- }
- }
- namespace cppcms {
- class cache_interface;
- namespace impl { namespace cgi { class connection; }}
- namespace http {
-
- class context;
- class cookie;
-
- ///
- /// \brief this class represents all HTTP/CGI response related API, generation of output content and
- /// HTTP headers.
- ///
- class CPPCMS_API response : public booster::noncopyable {
- public:
- ///
- /// This type represent the enum of HTTP Status type as of RFC 2616 sec. 6.1.1
- ///
- typedef enum {
- continue_transfer = 100,
- switching_protocol = 101,
- ok = 200,
- created = 201,
- accepted = 202,
- non_authoritative_information = 203,
- no_content = 204,
- reset_content = 205,
- partial_content = 206,
- multiple_choices = 300,
- moved_permanently = 301,
- found = 302,
- see_other = 303,
- not_modified = 304,
- use_proxy = 305,
- temporary_redirect = 307,
- bad_request = 400,
- unauthorized = 401,
- payment_required = 402,
- forbidden = 403,
- not_found = 404,
- method_not_allowed = 405,
- not_acceptable = 406,
- proxy_authentication_required = 407,
- request_time_out = 408,
- conflict = 409,
- gone = 410,
- precondition_failed = 412,
- request_entity_too_large = 413,
- request_uri_too_large = 414,
- unsupported_media_type = 415,
- requested_range_not_satisfiable = 416,
- expectation_failed = 417,
- internal_server_error = 500,
- not_implemented = 501,
- bad_gateway = 502,
- service_unavailable = 503,
- gateway_timeout = 504,
- http_version_not_supported = 505
- } status_type;
-
- ///
- /// This enum represents different types of IO modes giving fine grained control over HTTP output.
- ///
- /// These modes are set via io_mode member function
- ///
- typedef enum {
- normal, ///< Synchronous IO. Write the request, it is buffered and possible compressed using gzip.
- nogzip, ///< Same as normal but disable gzip compression
- raw, ///< User has full control over the output, it is also fully responsible for generation
- ///< of HTTP headers, no-session management given.
- asynchronous,
- ///< In this mode the data is buffered and never transferred unless it is requested by async_flush_output,
- ///< or async_complete_response member functions of http::context explicitly.
- asynchronous_raw
- ///< Same as asynchronous but the user is responsible for generation of its own HTTP headers.
-
- } io_mode_type;
-
-
- // Standard HTTP Response Headers RFC 2616
-
- ///
- /// Set HTTP Header Accept-Ranges
- ///
- void accept_ranges(std::string const &);
- ///
- /// Set HTTP Header Age
- ///
- void age(unsigned seconds);
- ///
- /// Set HTTP Header Allow
- ///
- void allow(std::string const &);
- ///
- /// Set HTTP Header Cache-Control
- ///
- void cache_control(std::string const &);
- ///
- /// Set HTTP Header Content-Encoding.
- ///
- /// Note: if you set this header manually, gzip compression will be automatically disabled.
- ///
- void content_encoding(std::string const &);
- ///
- /// Set HTTP Header Content-Language
- ///
- void content_language(std::string const &);
- ///
- /// Set HTTP Header Content-Length
- ///
- void content_length(unsigned long long len);
- ///
- /// Set HTTP Header Content-Location
- ///
- void content_location(std::string const &);
- ///
- /// Set HTTP Header Content-Md5
- ///
- void content_md5(std::string const &);
- ///
- /// Set HTTP Header Content-Range
- ///
- void content_range(std::string const &);
- ///
- /// Set HTTP Header Content-Type
- ///
- void content_type(std::string const &);
- ///
- /// Set HTTP Header Date
- ///
- void date(time_t);
- ///
- /// Set HTTP Header Etag
- ///
- void etag(std::string const &);
- ///
- /// Set HTTP Header Expires, it is formatted as HTTP Date-Time from the POSIX time \a t
- ///
- void expires(time_t t);
- ///
- /// Set HTTP Header Last-Modified, it is formatted as HTTP Date-Time from the POSIX time \a t
- ///
- void last_modified(time_t t);
- ///
- /// Set HTTP Header Location
- ///
- void location(std::string const &);
- ///
- /// Set HTTP Header Pragma
- ///
- void pragma(std::string const &);
- ///
- /// Set HTTP Header Proxy-Authenticate
- ///
- void proxy_authenticate(std::string const &);
- ///
- /// Set HTTP Header Retry-After
- ///
- void retry_after(std::string const &);
- ///
- /// Set HTTP Header Retry-After
- ///
- void retry_after(unsigned);
- ///
- /// Set GCI Status Header, the message is created according to the code automatically
- ///
- void status(int code);
- ///
- /// Set HTTP Header Status with the status code \a code and a custom \a message
- ///
- void status(int code,std::string const &message);
- ///
- /// Set HTTP Header Trailer
- ///
- void trailer(std::string const &);
- ///
- /// Set HTTP Header Transfer-Encoding, note
- ///
- void transfer_encoding(std::string const &);
- ///
- /// Set HTTP Header Vary
- ///
- void vary(std::string const &);
- ///
- /// Set HTTP Header Via
- ///
- void via(std::string const &);
- ///
- /// Set HTTP Header Warning
- ///
- void warning(std::string const &);
- ///
- /// Set HTTP Header WWW-Authenticate
- ///
- void www_authenticate(std::string const &);
-
-
- ///
- /// Set Generic HTTP header "name: value"
- ///
- void set_header(std::string const &name,std::string const &value);
- ///
- /// Get output header value, returns empty string if it is not set
- ///
- std::string get_header(std::string const &name);
- ///
- /// Erase specific header \a h
- ///
- void erase_header(std::string const &h);
-
- ///
- /// add header - independently of set_header/get_header/erase_header - allows
- /// to specify multiple headers of same type like Set-Cookie or WWW-Authenticate
- ///
- /// \ver{v1_2}
- void add_header(std::string const &name,std::string const &value);
-
- ///
- /// This function set HTTP Content-Type header, but unlike contet_type function it also adds
- /// current locale charset encoding (unless localization.disable_charset_in_content_type set to true in configuration)
- ///
- void set_content_header(std::string const &content_type);
-
- ///
- /// Shortcut to set_content_header("text/html") - this is the default content-type header
- ///
- void set_html_header();
- ///
- /// Shortcut to set_content_header("text/xhtml")
- ///
- void set_xhtml_header();
- ///
- /// Shortcut to set_content_header("text/plain")
- ///
- void set_plain_text_header();
- ///
- /// Redirect to other \a location by setting HTTP Location header and a Status header with a status \a status
- ///
- void set_redirect_header(std::string const &location,int status = found);
- ///
- /// Set HTTP Cookie
- ///
- void set_cookie(cookie const &);
-
- ///
- /// This creates a default HTTP response (including HTML body) with a status \a stat a message \a msg.
- ///
- /// Note: if \a msg is empty default message for HTTP Status code \a stat is used.
- ///
- void make_error_response(int stat,std::string const &msg = std::string());
-
- ///
- /// Get current io_mode, see a description for io_mode_type.
- ///
- io_mode_type io_mode();
- ///
- /// Set current io_mode, see a description for io_mode_type.
- ///
- /// Note: you can't change it after requesting for output stream, i.e. calling out() member function.
- ///
- void io_mode(io_mode_type);
-
- ///
- /// Request an output stream to write the body of HTTP response after writing headers.
- ///
- /// Note:
- ///
- /// - it triggers saving changes in the session, so further changes will have no effect.
- /// - it triggers writing all headers to output stream, such that changing any header or adding cookies will have no effect.
- /// - it is impossible to change an io_mode after calling this function.
- ///
- std::ostream &out();
-
- ///
- /// Create an HTTP time string from POSIX time as of RFC 2616
- ///
- static std::string make_http_time(time_t);
- ///
- /// Return a string that represents a message for HTTP status code \a status
- ///
- static char const *status_to_string(int status);
-
- ///
- /// Check if out() member function was called, (so it is impossible to do some tasks like changing HTTP headers.
- /// See out description for more details
- ///
- bool some_output_was_written();
- ///
- /// Finalize an output request. Generally this function is called automatically for synchronous application, however
- /// when working with asynchronous requests you should call this function before calling async_complete_response.
- ///
- void finalize();
-
- ///
- /// Defines the size of the output buffer for the output data.
- ///
- /// Setting the to 0 makes the output non-buffered and prevents unnecessary copy of large objects in memory
- ///
- /// The default is defined in configuration by service.output_buffer_size and service.async_output_buffer_size for synchronous and asynchronous
- /// applications accordingly, can be called before and after out() was called
- ///
- /// Calling with negative value would reset it to the default
- ///
- /// Note: when gzip compression active, buffering is still present at intermediate levels
- ///
- /// \ver{v1_2}
- void setbuf(int buffer_size);
- ///
- /// Sets full buffering mode for asynchronous applications
- ///
- /// When set to true the output data is transferred only when async_flush_output or async_complete_response are called this
- /// is the default behavior.
- ///
- /// When set to false, the data is sent upon flushing of the std::ostream provided by out(). If I/O operation blocks,
- /// the actual output is buffered, it is possible to test if blocking occurred by calling pending_blocked_output()
- ///
- /// When the full buffering is disable, if an error occurs, the out() is set to fail state.
- ///
- /// \ver{v1_2}
- void full_asynchronous_buffering(bool enable);
-
- ///
- /// Get current state of asynchronous buffering
- ///
- /// \ver{v1_2}
- bool full_asynchronous_buffering();
-
- ///
- /// Returns true of some of the output wasn't sent due to blocking upon flushing of std::stream &out() which is used together with full_asynchronous_buffering(false) mode.
- ///
- /// Note: it does not look on to internal buffers thus it is user's responsibility to call
- ///
- /// Once the condition occurs you can flush the output asynchronously using async_complete_response or async_flush_output
- ///
- /// \ver{v1_2}
- bool pending_blocked_output();
-
-
- /// \cond INTERNAL
- response(context &);
- ~response();
- /// \endcond
- private:
- friend class impl::cgi::connection;
- friend class ::cppcms::cache_interface;
-
- void copy_to_cache();
- std::string copied_data();
- bool need_gzip();
-
- std::pair<char const *,size_t> output();
-
- void write_http_headers(std::ostream &);
-
- int flush_async_chunk(booster::system::error_code &e);
-
- struct _data;
- booster::hold_ptr<_data> d;
-
- context &context_;
- std::ostream *stream_;
- io_mode_type io_mode_;
-
- uint32_t disable_compression_ : 1;
- uint32_t ostream_requested_ : 1;
- uint32_t copy_to_cache_ : 1;
- uint32_t finalized_ : 1;
- uint32_t reserved_ : 28;
- };
-
- } /* http */
- } /* cppcms */
-
-
- #endif
|