"Fossies" - the Fresh Open Source Software Archive

Member "sitecopy-0.16.6/lib/neon/ne_request.h" (8 Feb 2008, 14411 Bytes) of archive /linux/www/sitecopy-0.16.6.tar.gz:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "ne_request.h" see the Fossies "Dox" file reference documentation.

    1 /* 
    2    HTTP Request Handling
    3    Copyright (C) 1999-2006, 2008, Joe Orton <joe@manyfish.co.uk>
    4 
    5    This library is free software; you can redistribute it and/or
    6    modify it under the terms of the GNU Library General Public
    7    License as published by the Free Software Foundation; either
    8    version 2 of the License, or (at your option) any later version.
    9    
   10    This library is distributed in the hope that it will be useful,
   11    but WITHOUT ANY WARRANTY; without even the implied warranty of
   12    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
   13    Library General Public License for more details.
   14 
   15    You should have received a copy of the GNU Library General Public
   16    License along with this library; if not, write to the Free
   17    Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
   18    MA 02111-1307, USA
   19 
   20 */
   21 
   22 #ifndef NE_REQUEST_H
   23 #define NE_REQUEST_H
   24 
   25 #include "ne_utils.h" /* For ne_status */
   26 #include "ne_string.h" /* For ne_buffer */
   27 #include "ne_session.h"
   28 
   29 NE_BEGIN_DECLS
   30 
   31 #define NE_OK (0) /* Success */
   32 #define NE_ERROR (1) /* Generic error; use ne_get_error(session) for message */
   33 #define NE_LOOKUP (2) /* Server or proxy hostname lookup failed */
   34 #define NE_AUTH (3) /* User authentication failed on server */
   35 #define NE_PROXYAUTH (4) /* User authentication failed on proxy */
   36 #define NE_CONNECT (5) /* Could not connect to server */
   37 #define NE_TIMEOUT (6) /* Connection timed out */
   38 #define NE_FAILED (7) /* The precondition failed */
   39 #define NE_RETRY (8) /* Retry request (ne_end_request ONLY) */
   40 #define NE_REDIRECT (9) /* See ne_redirect.h */
   41 
   42 /* Opaque object representing a single HTTP request. */
   43 typedef struct ne_request_s ne_request;
   44 
   45 /***** Request Handling *****/
   46 
   47 /* Create a request in session 'sess', with given method and path.
   48  * 'path' must conform to the 'abs_path' grammar in RFC2396, with an
   49  * optional "? query" part, and MUST be URI-escaped by the caller. */
   50 ne_request *ne_request_create(ne_session *sess,
   51                   const char *method, const char *path);
   52 
   53 /* The request body will be taken from 'size' bytes of 'buffer'. */
   54 void ne_set_request_body_buffer(ne_request *req, const char *buffer,
   55                 size_t size);
   56 
   57 /* The request body will be taken from 'length' bytes read from the
   58  * file descriptor 'fd', starting from file offset 'offset'. */
   59 void ne_set_request_body_fd(ne_request *req, int fd,
   60                             ne_off_t offset, ne_off_t length);
   61 
   62 /* "Pull"-based request body provider: a callback which is invoked to
   63  * provide blocks of request body on demand.
   64  *
   65  * Before each time the body is provided, the callback will be called
   66  * once with buflen == 0.  The body may have to be provided >1 time
   67  * per request (for authentication retries etc.).
   68  *
   69  * For a call with buflen == 0, the callback must return zero on success
   70  * or non-zero on error; the session error string must be set on error.
   71  * For a call with buflen > 0, the callback must return:
   72  *        <0           : error, abort request; session error string must be set.
   73  *         0           : ignore 'buffer' contents, end of body.
   74  *     0 < x <= buflen : buffer contains x bytes of body data.  */
   75 typedef ssize_t (*ne_provide_body)(void *userdata, 
   76                    char *buffer, size_t buflen);
   77 
   78 /* Install a callback which is invoked as needed to provide the
   79  * request body, a block at a time.  The total size of the request
   80  * body is 'length'; the callback must ensure that it returns no more
   81  * than 'length' bytes in total. */
   82 void ne_set_request_body_provider(ne_request *req, ne_off_t length,
   83                   ne_provide_body provider, void *userdata);
   84 
   85 /* Handling response bodies; two callbacks must be provided:
   86  *
   87  * 1) 'acceptance' callback: determines whether you want to handle the
   88  * response body given the response-status information, e.g., if you
   89  * only want 2xx responses, say so here.
   90  *
   91  * 2) 'reader' callback: passed blocks of the response-body as they
   92  * arrive, if the acceptance callback returned non-zero.  */
   93 
   94 /* 'acceptance' callback type. Return non-zero to accept the response,
   95  * else zero to ignore it. */
   96 typedef int (*ne_accept_response)(void *userdata, ne_request *req, 
   97                                   const ne_status *st);
   98 
   99 /* An 'acceptance' callback which only accepts 2xx-class responses.
  100  * Ignores userdata. */
  101 int ne_accept_2xx(void *userdata, ne_request *req, const ne_status *st);
  102 
  103 /* An acceptance callback which accepts all responses.  Ignores
  104  * userdata. */
  105 int ne_accept_always(void *userdata, ne_request *req, const ne_status *st);
  106 
  107 /* Callback for reading a block of data.  Returns zero on success, or
  108  * non-zero on error.  If returning an error, the response will be
  109  * aborted and the callback will not be invoked again.  The request
  110  * dispatch (or ne_read_response_block call) will fail with NE_ERROR;
  111  * the session error string should have been set by the callback. */
  112 typedef int (*ne_block_reader)(void *userdata, const char *buf, size_t len);
  113 
  114 /* Add a response reader for the given request, with the given
  115  * acceptance function. userdata is passed as the first argument to
  116  * the acceptance + reader callbacks. 
  117  *
  118  * The acceptance callback is called once each time the request is
  119  * sent: it may be sent >1 time because of authentication retries etc.
  120  * For each time the acceptance callback is called, if it returns
  121  * non-zero, blocks of the response body will be passed to the reader
  122  * callback as the response is read.  After all the response body has
  123  * been read, the callback will be called with a 'len' argument of
  124  * zero.  */
  125 void ne_add_response_body_reader(ne_request *req, ne_accept_response accpt,
  126                  ne_block_reader reader, void *userdata);
  127 
  128 /* Retrieve the value of the response header field with given name;
  129  * returns NULL if no response header with given name was found.  The
  130  * return value is valid only until the next call to either
  131  * ne_request_destroy or ne_begin_request for this request. */
  132 const char *ne_get_response_header(ne_request *req, const char *name);
  133 
  134 /* Iterator interface for response headers: if passed a NULL cursor,
  135  * returns the first header; if passed a non-NULL cursor pointer,
  136  * returns the next header.  The return value is a cursor pointer: if
  137  * it is non-NULL, *name and *value are set to the name and value of
  138  * the header field.  If the return value is NULL, no more headers are
  139  * found, *name and *value are undefined.
  140  *
  141  * The order in which response headers is returned is undefined.  Both
  142  * the cursor and name/value pointers are valid only until the next
  143  * call to either ne_request_destroy or ne_begin_request for this
  144  * request. */
  145 void *ne_response_header_iterate(ne_request *req, void *cursor,
  146                                  const char **name, const char **value);
  147 
  148 /* Adds a header to the request with given name and value. */
  149 void ne_add_request_header(ne_request *req, const char *name, 
  150                const char *value);
  151 /* Adds a header to the request with given name, using printf-like
  152  * format arguments for the value. */
  153 void ne_print_request_header(ne_request *req, const char *name,
  154                  const char *format, ...) 
  155     ne_attribute((format(printf, 3, 4)));
  156 
  157 /* ne_request_dispatch: Sends the given request, and reads the
  158  * response.  Returns:
  159  *  - NE_OK if the request was sent and response read successfully
  160  *  - NE_AUTH, NE_PROXYAUTH for a server or proxy server authentication error
  161  *  - NE_CONNECT if connection could not be established
  162  *  - NE_TIMEOUT if an timeout occurred sending or reading from the server
  163  *  - NE_ERROR for other fatal dispatch errors
  164  * On any error, the session error string is set.  On success or
  165  * authentication error, the actual response-status can be retrieved using
  166  * ne_get_status(). */
  167 int ne_request_dispatch(ne_request *req);
  168 
  169 /* Returns a pointer to the response status information for the given
  170  * request; pointer is valid until request object is destroyed. */
  171 const ne_status *ne_get_status(const ne_request *req) ne_attribute((const));
  172 
  173 /* Returns pointer to session associated with request. */
  174 ne_session *ne_get_session(const ne_request *req) ne_attribute((const));
  175 
  176 /* Destroy memory associated with request pointer */
  177 void ne_request_destroy(ne_request *req);
  178 
  179 /* "Caller-pulls" request interface.  This is an ALTERNATIVE interface
  180  * to ne_request_dispatch: either use that, or do all this yourself:
  181  *
  182  * caller must call:
  183  *  1. ne_begin_request (fail if returns non-NE_OK)
  184  *  2. while(ne_read_response_block(...) > 0) ... loop ...;
  185  *     (fail if ne_read_response_block returns <0)
  186  *  3. ne_end_request
  187  *
  188  * ne_end_request and ne_begin_request both return an NE_* code; if
  189  * ne_end_request returns NE_RETRY, you must restart the loop from (1)
  190  * above. */
  191 int ne_begin_request(ne_request *req);
  192 int ne_end_request(ne_request *req);
  193 
  194 /* Read a block of the response into the passed buffer of size 'buflen'.
  195  *
  196  * Returns:
  197  *  <0 - error, stop reading.
  198  *   0 - end of response
  199  *  >0 - number of bytes read into buffer.
  200  */
  201 ssize_t ne_read_response_block(ne_request *req, char *buffer, size_t buflen);
  202 
  203 /* Read response blocks until end of response; exactly equivalent to
  204  * calling ne_read_response_block() until it returns 0.  Returns
  205  * non-zero on error. */
  206 int ne_discard_response(ne_request *req);
  207 
  208 /* Read response blocks until end of response, writing content to the
  209  * given file descriptor.  Returns NE_ERROR on error. */
  210 int ne_read_response_to_fd(ne_request *req, int fd);
  211 
  212 /* Defined request flags: */
  213 typedef enum ne_request_flag_e {
  214     NE_REQFLAG_EXPECT100 = 0, /* enable this flag to enable use of the
  215                                * "Expect: 100-continue" for the
  216                                * request. */
  217 
  218     NE_REQFLAG_IDEMPOTENT, /* disable this flag if the request uses a
  219                             * non-idempotent method such as POST. */
  220 
  221     NE_REQFLAG_LAST /* enum sentinel value */
  222 } ne_request_flag;
  223 
  224 /* Set a new value for a particular request flag. */
  225 void ne_set_request_flag(ne_request *req, ne_request_flag flag, int value);
  226 
  227 /* Return 0 if the given flag is not set, >0 it is set, or -1 if the
  228  * flag is not supported. */
  229 int ne_get_request_flag(ne_request *req, ne_request_flag flag);
  230 
  231 /**** Request hooks handling *****/
  232 
  233 typedef void (*ne_free_hooks)(void *cookie);
  234 
  235 /* Hook called when a request is created; passed the request method,
  236  * and the string used as the Request-URI (note that this may be a
  237  * absolute URI if a proxy is in use, an absolute path, a "*", etc).
  238  * A create_request hook is called exactly once per request. */
  239 typedef void (*ne_create_request_fn)(ne_request *req, void *userdata,
  240                      const char *method, const char *requri);
  241 void ne_hook_create_request(ne_session *sess, 
  242                 ne_create_request_fn fn, void *userdata);
  243 
  244 /* Hook called before the request is sent.  'header' is the raw HTTP
  245  * header before the trailing CRLF is added; more headers can be added
  246  * here.  A pre_send hook may be called >1 time per request if the
  247  * request is retried due to a post_send hook returning NE_RETRY. */
  248 typedef void (*ne_pre_send_fn)(ne_request *req, void *userdata, 
  249                    ne_buffer *header);
  250 void ne_hook_pre_send(ne_session *sess, ne_pre_send_fn fn, void *userdata);
  251 
  252 /* Hook called directly after the response headers have been read, but
  253  * before the resposnse body has been read.  'status' is the response
  254  * status-code.  A post_header hook may be called >1 time per request
  255  * if the request is retried due to a post_send hook returning
  256  * NE_RETRY. */
  257 typedef void (*ne_post_headers_fn)(ne_request *req, void *userdata,
  258                                    const ne_status *status);
  259 void ne_hook_post_headers(ne_session *sess, 
  260                           ne_post_headers_fn fn, void *userdata);
  261 
  262 /* Hook called after the request is dispatched (request sent, and
  263  * the entire response read).  If an error occurred reading the response,
  264  * this hook will not run.  May return:
  265  *  NE_OK     everything is okay
  266  *  NE_RETRY  try sending the request again.
  267  * anything else signifies an error, and the request is failed. The return
  268  * code is passed back the _dispatch caller, so the session error must
  269  * also be set appropriately (ne_set_error).
  270  */
  271 typedef int (*ne_post_send_fn)(ne_request *req, void *userdata,
  272                    const ne_status *status);
  273 void ne_hook_post_send(ne_session *sess, ne_post_send_fn fn, void *userdata);
  274 
  275 /* Hook called when the function is destroyed. */
  276 typedef void (*ne_destroy_req_fn)(ne_request *req, void *userdata);
  277 void ne_hook_destroy_request(ne_session *sess,
  278                  ne_destroy_req_fn fn, void *userdata);
  279 
  280 typedef void (*ne_destroy_sess_fn)(void *userdata);
  281 /* Hook called when the session is about to be destroyed. */
  282 void ne_hook_destroy_session(ne_session *sess,
  283                  ne_destroy_sess_fn fn, void *userdata);
  284 
  285 typedef void (*ne_close_conn_fn)(void *userdata);
  286 /* Hook called when the connection is closed; note that this hook
  287  * may be called *AFTER* the destroy_session hook. */
  288 void ne_hook_close_conn(ne_session *sess, ne_close_conn_fn fn, void *userdata);
  289 
  290 /* The ne_unhook_* functions remove a hook registered with the given
  291  * session.  If a hook is found which was registered with a given
  292  * function 'fn', and userdata pointer 'userdata', then it will be
  293  * removed from the hooks list.
  294  *
  295  * It is unsafe to use any of these functions from a hook function to
  296  * unregister itself, except for ne_unhook_destroy_request. */
  297 void ne_unhook_create_request(ne_session *sess, 
  298                               ne_create_request_fn fn, void *userdata);
  299 void ne_unhook_pre_send(ne_session *sess, ne_pre_send_fn fn, void *userdata);
  300 void ne_unhook_post_headers(ne_session *sess, ne_post_headers_fn fn, void *userdata);
  301 void ne_unhook_post_send(ne_session *sess, ne_post_send_fn fn, void *userdata);
  302 void ne_unhook_destroy_request(ne_session *sess,
  303                                ne_destroy_req_fn fn, void *userdata);
  304 void ne_unhook_destroy_session(ne_session *sess,
  305                                ne_destroy_sess_fn fn, void *userdata);
  306 void ne_unhook_close_conn(ne_session *sess, 
  307                           ne_close_conn_fn fn, void *userdata);
  308 
  309 /* Store an opaque context for the request, 'priv' is returned by a
  310  * call to ne_request_get_private with the same ID. */
  311 void ne_set_request_private(ne_request *req, const char *id, void *priv);
  312 void *ne_get_request_private(ne_request *req, const char *id);
  313 
  314 NE_END_DECLS
  315 
  316 #endif /* NE_REQUEST_H */