Back to home page

EIC code displayed by LXR

 
 

    


Warning, file /include/CivetServer.h was not indexed or was modified since last indexation (in which case cross-reference links may be missing, inaccurate or erroneous).

0001 /* Copyright (c) 2013-2017 the Civetweb developers
0002  * Copyright (c) 2013 No Face Press, LLC
0003  *
0004  * License http://opensource.org/licenses/mit-license.php MIT License
0005  */
0006 
0007 #ifndef CIVETSERVER_HEADER_INCLUDED
0008 #define CIVETSERVER_HEADER_INCLUDED
0009 #ifdef __cplusplus
0010 
0011 #include "civetweb.h"
0012 #include <map>
0013 #include <stdexcept>
0014 #include <string>
0015 #include <vector>
0016 
0017 #ifndef CIVETWEB_CXX_API
0018 #if defined(_WIN32)
0019 #if defined(CIVETWEB_CXX_DLL_EXPORTS)
0020 #define CIVETWEB_CXX_API __declspec(dllexport)
0021 #elif defined(CIVETWEB_CXX_DLL_IMPORTS)
0022 #define CIVETWEB_CXX_API __declspec(dllimport)
0023 #else
0024 #define CIVETWEB_CXX_API
0025 #endif
0026 #elif __GNUC__ >= 4
0027 #define CIVETWEB_CXX_API __attribute__((visibility("default")))
0028 #else
0029 #define CIVETWEB_CXX_API
0030 #endif
0031 #endif
0032 
0033 // forward declaration
0034 class CivetServer;
0035 
0036 /**
0037  * Exception class for thrown exceptions within the CivetHandler object.
0038  */
0039 class CIVETWEB_CXX_API CivetException : public std::runtime_error
0040 {
0041   public:
0042     CivetException(const std::string &msg) : std::runtime_error(msg)
0043     {
0044     }
0045 };
0046 
0047 /**
0048  * Basic interface for a URI request handler.  Handlers implementations
0049  * must be reentrant.
0050  */
0051 class CIVETWEB_CXX_API CivetHandler
0052 {
0053   public:
0054     /**
0055      * Destructor
0056      */
0057     virtual ~CivetHandler()
0058     {
0059     }
0060 
0061     /**
0062      * Callback method for GET request.
0063      *
0064      * @param server - the calling server
0065      * @param conn - the connection information
0066      * @returns true if implemented, false otherwise
0067      */
0068     virtual bool handleGet(CivetServer *server, struct mg_connection *conn);
0069 
0070     /**
0071      * Callback method for GET request.
0072      *
0073      * @param server - the calling server
0074      * @param conn - the connection information
0075      * @param status_code - pointer to return status code
0076      * @returns true if implemented, false otherwise
0077      */
0078     virtual bool handleGet(CivetServer *server,
0079                            struct mg_connection *conn,
0080                            int *status_code);
0081 
0082     /**
0083      * Callback method for POST request.
0084      *
0085      * @param server - the calling server
0086      * @param conn - the connection information
0087      * @returns true if implemented, false otherwise
0088      */
0089     virtual bool handlePost(CivetServer *server, struct mg_connection *conn);
0090 
0091     /**
0092      * Callback method for POST request.
0093      *
0094      * @param server - the calling server
0095      * @param conn - the connection information
0096      * @param status_code - pointer to return status code
0097      * @returns true if implemented, false otherwise
0098      */
0099     virtual bool handlePost(CivetServer *server,
0100                             struct mg_connection *conn,
0101                             int *status_code);
0102 
0103     /**
0104      * Callback method for HEAD request.
0105      *
0106      * @param server - the calling server
0107      * @param conn - the connection information
0108      * @returns true if implemented, false otherwise
0109      */
0110     virtual bool handleHead(CivetServer *server, struct mg_connection *conn);
0111 
0112     /**
0113      * Callback method for HEAD request.
0114      *
0115      * @param server - the calling server
0116      * @param conn - the connection information
0117      * @param status_code - pointer to return status code
0118      * @returns true if implemented, false otherwise
0119      */
0120     virtual bool handleHead(CivetServer *server,
0121                             struct mg_connection *conn,
0122                             int *status_code);
0123 
0124     /**
0125      * Callback method for PUT request.
0126      *
0127      * @param server - the calling server
0128      * @param conn - the connection information
0129      * @returns true if implemented, false otherwise
0130      */
0131     virtual bool handlePut(CivetServer *server, struct mg_connection *conn);
0132 
0133     /**
0134      * Callback method for PUT request.
0135      *
0136      * @param server - the calling server
0137      * @param conn - the connection information
0138      * @param status_code - pointer to return status code
0139      * @returns true if implemented, false otherwise
0140      */
0141     virtual bool handlePut(CivetServer *server,
0142                            struct mg_connection *conn,
0143                            int *status_code);
0144 
0145     /**
0146      * Callback method for DELETE request.
0147      *
0148      * @param server - the calling server
0149      * @param conn - the connection information
0150      * @returns true if implemented, false otherwise
0151      */
0152     virtual bool handleDelete(CivetServer *server, struct mg_connection *conn);
0153 
0154     /**
0155      * Callback method for DELETE request.
0156      *
0157      * @param server - the calling server
0158      * @param conn - the connection information
0159      * @param status_code - pointer to return status code
0160      * @returns true if implemented, false otherwise
0161      */
0162     virtual bool handleDelete(CivetServer *server,
0163                               struct mg_connection *conn,
0164                               int *status_code);
0165 
0166     /**
0167      * Callback method for OPTIONS request.
0168      *
0169      * @param server - the calling server
0170      * @param conn - the connection information
0171      * @returns true if implemented, false otherwise
0172      */
0173     virtual bool handleOptions(CivetServer *server, struct mg_connection *conn);
0174 
0175     /**
0176      * Callback method for OPTIONS request.
0177      *
0178      * @param server - the calling server
0179      * @param conn - the connection information
0180      * @param status_code - pointer to return status code
0181      * @returns true if implemented, false otherwise
0182      */
0183     virtual bool handleOptions(CivetServer *server,
0184                                struct mg_connection *conn,
0185                                int *status_code);
0186 
0187     /**
0188      * Callback method for PATCH request.
0189      *
0190      * @param server - the calling server
0191      * @param conn - the connection information
0192      * @returns true if implemented, false otherwise
0193      */
0194     virtual bool handlePatch(CivetServer *server, struct mg_connection *conn);
0195 
0196     /**
0197      * Callback method for PATCH request.
0198      *
0199      * @param server - the calling server
0200      * @param conn - the connection information
0201      * @param status_code - pointer to return status code
0202      * @returns true if implemented, false otherwise
0203      */
0204     virtual bool handlePatch(CivetServer *server,
0205                              struct mg_connection *conn,
0206                              int *status_code);
0207 };
0208 
0209 /**
0210  * Basic interface for a URI authorization handler.  Handler implementations
0211  * must be reentrant.
0212  */
0213 class CIVETWEB_CXX_API CivetAuthHandler
0214 {
0215   public:
0216     /**
0217      * Destructor
0218      */
0219     virtual ~CivetAuthHandler()
0220     {
0221     }
0222 
0223     /**
0224      * Callback method for authorization requests. It is up the this handler
0225      * to generate 401 responses if authorization fails.
0226      *
0227      * @param server - the calling server
0228      * @param conn - the connection information
0229      * @returns true if authorization succeeded, false otherwise
0230      */
0231     virtual bool authorize(CivetServer *server, struct mg_connection *conn) = 0;
0232 };
0233 
0234 /**
0235  * Basic interface for a websocket handler.  Handlers implementations
0236  * must be reentrant.
0237  */
0238 class CIVETWEB_CXX_API CivetWebSocketHandler
0239 {
0240   public:
0241     /**
0242      * Destructor
0243      */
0244     virtual ~CivetWebSocketHandler()
0245     {
0246     }
0247 
0248     /**
0249      * Callback method for when the client intends to establish a websocket
0250      *connection, before websocket handshake.
0251      *
0252      * @param server - the calling server
0253      * @param conn - the connection information
0254      * @returns true to keep socket open, false to close it
0255      */
0256     virtual bool handleConnection(CivetServer *server,
0257                                   const struct mg_connection *conn);
0258 
0259     /**
0260      * Callback method for when websocket handshake is successfully completed,
0261      *and connection is ready for data exchange.
0262      *
0263      * @param server - the calling server
0264      * @param conn - the connection information
0265      */
0266     virtual void handleReadyState(CivetServer *server,
0267                                   struct mg_connection *conn);
0268 
0269     /**
0270      * Callback method for when a data frame has been received from the client.
0271      *
0272      * @param server - the calling server
0273      * @param conn - the connection information
0274      * @bits: first byte of the websocket frame, see websocket RFC at
0275      *http://tools.ietf.org/html/rfc6455, section 5.2
0276      * @data, data_len: payload, with mask (if any) already applied.
0277      * @returns true to keep socket open, false to close it
0278      */
0279     virtual bool handleData(CivetServer *server,
0280                             struct mg_connection *conn,
0281                             int bits,
0282                             char *data,
0283                             size_t data_len);
0284 
0285     /**
0286      * Callback method for when the connection is closed.
0287      *
0288      * @param server - the calling server
0289      * @param conn - the connection information
0290      */
0291     virtual void handleClose(CivetServer *server,
0292                              const struct mg_connection *conn);
0293 };
0294 
0295 /**
0296  * CivetCallbacks
0297  *
0298  * wrapper for mg_callbacks
0299  */
0300 struct CIVETWEB_CXX_API CivetCallbacks : public mg_callbacks {
0301     CivetCallbacks();
0302 };
0303 
0304 /**
0305  * CivetServer
0306  *
0307  * Basic class for embedded web server.  This has an URL mapping built-in.
0308  */
0309 class CIVETWEB_CXX_API CivetServer
0310 {
0311   public:
0312     /**
0313      * Constructor
0314      *
0315      * This automatically starts the sever.
0316      * It is good practice to call getContext() after this in case there
0317      * were errors starting the server.
0318      *
0319      * Note: CivetServer should not be used as a static instance in a Windows
0320      * DLL, since the constructor creates threads and the destructor joins
0321      * them again (creating/joining threads should not be done in static
0322      * constructors).
0323      *
0324      * @param options - the web server options.
0325      * @param callbacks - optional web server callback methods.
0326      *
0327      * @throws CivetException
0328      */
0329     CivetServer(const char **options,
0330                 const struct CivetCallbacks *callbacks = 0,
0331                 const void *UserContext = 0);
0332     CivetServer(const std::vector<std::string> &options,
0333                 const struct CivetCallbacks *callbacks = 0,
0334                 const void *UserContext = 0);
0335 
0336     /**
0337      * Destructor
0338      */
0339     virtual ~CivetServer();
0340 
0341     /**
0342      * close()
0343      *
0344      * Stops server and frees resources.
0345      */
0346     void close();
0347 
0348     /**
0349      * getContext()
0350      *
0351      * @return the context or 0 if not running.
0352      */
0353     const struct mg_context *
0354     getContext() const
0355     {
0356         return context;
0357     }
0358 
0359     /**
0360      * addHandler(const std::string &, CivetHandler *)
0361      *
0362      * Adds a URI handler.  If there is existing URI handler, it will
0363      * be replaced with this one.
0364      *
0365      * URI's are ordered and prefix (REST) URI's are supported.
0366      *
0367      *  @param uri - URI to match.
0368      *  @param handler - handler instance to use.
0369      */
0370     void addHandler(const std::string &uri, CivetHandler *handler);
0371 
0372     void
0373     addHandler(const std::string &uri, CivetHandler &handler)
0374     {
0375         addHandler(uri, &handler);
0376     }
0377 
0378     /**
0379      * addWebSocketHandler
0380      *
0381      * Adds a WebSocket handler for a specific URI.  If there is existing URI
0382      *handler, it will
0383      * be replaced with this one.
0384      *
0385      * URI's are ordered and prefix (REST) URI's are supported.
0386      *
0387      *  @param uri - URI to match.
0388      *  @param handler - handler instance to use.
0389      */
0390     void addWebSocketHandler(const std::string &uri,
0391                              CivetWebSocketHandler *handler);
0392 
0393     void
0394     addWebSocketHandler(const std::string &uri, CivetWebSocketHandler &handler)
0395     {
0396         addWebSocketHandler(uri, &handler);
0397     }
0398 
0399     /**
0400      * removeHandler(const std::string &)
0401      *
0402      * Removes a handler.
0403      *
0404      * @param uri - the exact URL used in addHandler().
0405      */
0406     void removeHandler(const std::string &uri);
0407 
0408     /**
0409      * removeWebSocketHandler(const std::string &)
0410      *
0411      * Removes a web socket handler.
0412      *
0413      * @param uri - the exact URL used in addWebSocketHandler().
0414      */
0415     void removeWebSocketHandler(const std::string &uri);
0416 
0417     /**
0418      * addAuthHandler(const std::string &, CivetAuthHandler *)
0419      *
0420      * Adds a URI authorization handler.  If there is existing URI authorization
0421      * handler, it will be replaced with this one.
0422      *
0423      * URI's are ordered and prefix (REST) URI's are supported.
0424      *
0425      * @param uri - URI to match.
0426      * @param handler - authorization handler instance to use.
0427      */
0428     void addAuthHandler(const std::string &uri, CivetAuthHandler *handler);
0429 
0430     void
0431     addAuthHandler(const std::string &uri, CivetAuthHandler &handler)
0432     {
0433         addAuthHandler(uri, &handler);
0434     }
0435 
0436     /**
0437      * removeAuthHandler(const std::string &)
0438      *
0439      * Removes an authorization handler.
0440      *
0441      * @param uri - the exact URL used in addAuthHandler().
0442      */
0443     void removeAuthHandler(const std::string &uri);
0444 
0445     /**
0446      * getListeningPorts()
0447      *
0448      * Returns a list of ports that are listening
0449      *
0450      * @return A vector of ports
0451      */
0452 
0453     std::vector<int> getListeningPorts();
0454 
0455     /**
0456      * getListeningPorts()
0457      *
0458      * Variant of getListeningPorts() returning the full port information
0459      * (protocol, SSL, ...)
0460      *
0461      * @return A vector of ports
0462      */
0463     std::vector<struct mg_server_port> getListeningPortsFull();
0464 
0465     /**
0466      * getCookie(struct mg_connection *conn, const std::string &cookieName,
0467      * std::string &cookieValue)
0468      *
0469      * Puts the cookie value string that matches the cookie name in the
0470      * cookieValue destination string.
0471      *
0472      * @param conn - the connection information
0473      * @param cookieName - cookie name to get the value from
0474      * @param cookieValue - cookie value is returned using this reference
0475      * @returns the size of the cookie value string read.
0476      */
0477     static int getCookie(struct mg_connection *conn,
0478                          const std::string &cookieName,
0479                          std::string &cookieValue);
0480 
0481     /**
0482      * getHeader(struct mg_connection *conn, const std::string &headerName)
0483      * @param conn - the connection information
0484      * @param headerName - header name to get the value from
0485      * @returns a char array which contains the header value as string
0486      */
0487     static const char *getHeader(struct mg_connection *conn,
0488                                  const std::string &headerName);
0489 
0490     /**
0491      * getMethod(struct mg_connection *conn)
0492      * @param conn - the connection information
0493      * @returns method of HTTP request
0494      */
0495     static const char *getMethod(struct mg_connection *conn);
0496 
0497     /**
0498      * getParam(struct mg_connection *conn, const char *, std::string &, size_t)
0499      *
0500      * Returns a query which contained in the supplied buffer.  The
0501      * occurrence value is a zero-based index of a particular key name.  This
0502      * should not be confused with the index over all of the keys.  Note that
0503      *this
0504      * function assumes that parameters are sent as text in http query string
0505      * format, which is the default for web forms. This function will work for
0506      * html forms with method="GET" and method="POST" attributes. In other
0507      *cases,
0508      * you may use a getParam version that directly takes the data instead of
0509      *the
0510      * connection as a first argument.
0511      *
0512      * @param conn - parameters are read from the data sent through this
0513      *connection
0514      * @param name - the key to search for
0515      * @param dst - the destination string
0516      * @param occurrence - the occurrence of the selected name in the query (0
0517      *based).
0518      * @return true if key was found
0519      */
0520     static bool getParam(struct mg_connection *conn,
0521                          const char *name,
0522                          std::string &dst,
0523                          size_t occurrence = 0);
0524 
0525     /**
0526      * getParam(const std::string &, const char *, std::string &, size_t)
0527      *
0528      * Returns a query parameter contained in the supplied buffer.  The
0529      * occurrence value is a zero-based index of a particular key name.  This
0530      * should not be confused with the index over all of the keys.
0531      *
0532      * @param data - the query string (text)
0533      * @param name - the key to search for
0534      * @param dst - the destination string
0535      * @param occurrence - the occurrence of the selected name in the query (0
0536      *based).
0537      * @return true if key was found
0538      */
0539     static bool
0540     getParam(const std::string &data,
0541              const char *name,
0542              std::string &dst,
0543              size_t occurrence = 0)
0544     {
0545         return getParam(data.c_str(), data.length(), name, dst, occurrence);
0546     }
0547 
0548     /**
0549      * getParam(const char *, size_t, const char *, std::string &, size_t)
0550      *
0551      * Returns a query parameter contained in the supplied buffer.  The
0552      * occurrence value is a zero-based index of a particular key name.  This
0553      * should not be confused with the index over all of the keys.
0554      *
0555      * @param data the - query string (text)
0556      * @param data_len - length of the query string
0557      * @param name - the key to search for
0558      * @param dst - the destination string
0559      * @param occurrence - the occurrence of the selected name in the query (0
0560      *based).
0561      * @return true if key was found
0562      */
0563     static bool getParam(const char *data,
0564                          size_t data_len,
0565                          const char *name,
0566                          std::string &dst,
0567                          size_t occurrence = 0);
0568 
0569     /**
0570      * getPostData(struct mg_connection *)
0571      *
0572      * Returns response body from a request made as POST. Since the
0573      * connections map is protected, it can't be directly accessed.
0574      * This uses string to store post data to handle big posts.
0575      *
0576      * @param conn - connection from which post data will be read
0577      * @return Post data (empty if not available).
0578      */
0579     static std::string getPostData(struct mg_connection *conn);
0580 
0581     /**
0582      * urlDecode(const std::string &, std::string &, bool)
0583      *
0584      * @param src - string to be decoded
0585      * @param dst - destination string
0586      * @param is_form_url_encoded - true if form url encoded
0587      *       form-url-encoded data differs from URI encoding in a way that it
0588      *       uses '+' as character for space, see RFC 1866 section 8.2.1
0589      *       http://ftp.ics.uci.edu/pub/ietf/html/rfc1866.txt
0590      */
0591     static void
0592     urlDecode(const std::string &src,
0593               std::string &dst,
0594               bool is_form_url_encoded = true)
0595     {
0596         urlDecode(src.c_str(), src.length(), dst, is_form_url_encoded);
0597     }
0598 
0599     /**
0600      * urlDecode(const char *, size_t, std::string &, bool)
0601      *
0602      * @param src - buffer to be decoded
0603      * @param src_len - length of buffer to be decoded
0604      * @param dst - destination string
0605      * @param is_form_url_encoded - true if form url encoded
0606      *       form-url-encoded data differs from URI encoding in a way that it
0607      *       uses '+' as character for space, see RFC 1866 section 8.2.1
0608      *       http://ftp.ics.uci.edu/pub/ietf/html/rfc1866.txt
0609      */
0610     static void urlDecode(const char *src,
0611                           size_t src_len,
0612                           std::string &dst,
0613                           bool is_form_url_encoded = true);
0614 
0615     /**
0616      * urlDecode(const char *, std::string &, bool)
0617      *
0618      * @param src - buffer to be decoded (0 terminated)
0619      * @param dst - destination string
0620      * @param is_form_url_encoded true - if form url encoded
0621      *       form-url-encoded data differs from URI encoding in a way that it
0622      *       uses '+' as character for space, see RFC 1866 section 8.2.1
0623      *       http://ftp.ics.uci.edu/pub/ietf/html/rfc1866.txt
0624      */
0625     static void urlDecode(const char *src,
0626                           std::string &dst,
0627                           bool is_form_url_encoded = true);
0628 
0629     /**
0630      * urlEncode(const std::string &, std::string &, bool)
0631      *
0632      * @param src - buffer to be encoded
0633      * @param dst - destination string
0634      * @param append - true if string should not be cleared before encoding.
0635      */
0636     static void
0637     urlEncode(const std::string &src, std::string &dst, bool append = false)
0638     {
0639         urlEncode(src.c_str(), src.length(), dst, append);
0640     }
0641 
0642     /**
0643      * urlEncode(const char *, size_t, std::string &, bool)
0644      *
0645      * @param src - buffer to be encoded (0 terminated)
0646      * @param dst - destination string
0647      * @param append - true if string should not be cleared before encoding.
0648      */
0649     static void
0650     urlEncode(const char *src, std::string &dst, bool append = false);
0651 
0652     /**
0653      * urlEncode(const char *, size_t, std::string &, bool)
0654      *
0655      * @param src - buffer to be encoded
0656      * @param src_len - length of buffer to be decoded
0657      * @param dst - destination string
0658      * @param append - true if string should not be cleared before encoding.
0659      */
0660     static void urlEncode(const char *src,
0661                           size_t src_len,
0662                           std::string &dst,
0663                           bool append = false);
0664 
0665     // generic user context which can be set/read,
0666     // the server does nothing with this apart from keep it.
0667     const void *
0668     getUserContext() const
0669     {
0670         return UserContext;
0671     }
0672 
0673   protected:
0674     class CivetConnection
0675     {
0676       public:
0677         std::vector<char> postData;
0678     };
0679 
0680     struct mg_context *context;
0681     std::map<const struct mg_connection *, CivetConnection> connections;
0682 
0683     // generic user context which can be set/read,
0684     // the server does nothing with this apart from keep it.
0685     const void *UserContext;
0686 
0687   private:
0688     /**
0689      * requestHandler(struct mg_connection *, void *cbdata)
0690      *
0691      * Handles the incoming request.
0692      *
0693      * @param conn - the connection information
0694      * @param cbdata - pointer to the CivetHandler instance.
0695      * @returns 0 if implemented, false otherwise
0696      */
0697     static int requestHandler(struct mg_connection *conn, void *cbdata);
0698 
0699     static int webSocketConnectionHandler(const struct mg_connection *conn,
0700                                           void *cbdata);
0701     static void webSocketReadyHandler(struct mg_connection *conn, void *cbdata);
0702     static int webSocketDataHandler(struct mg_connection *conn,
0703                                     int bits,
0704                                     char *data,
0705                                     size_t data_len,
0706                                     void *cbdata);
0707     static void webSocketCloseHandler(const struct mg_connection *conn,
0708                                       void *cbdata);
0709     /**
0710      * authHandler(struct mg_connection *, void *cbdata)
0711      *
0712      * Handles the authorization requests.
0713      *
0714      * @param conn - the connection information
0715      * @param cbdata - pointer to the CivetAuthHandler instance.
0716      * @returns 1 if authorized, 0 otherwise
0717      */
0718     static int authHandler(struct mg_connection *conn, void *cbdata);
0719 
0720     /**
0721      * closeHandler(struct mg_connection *)
0722      *
0723      * Handles closing a request (internal handler)
0724      *
0725      * @param conn - the connection information
0726      */
0727     static void closeHandler(const struct mg_connection *conn);
0728 
0729     /**
0730      * Stores the user provided close handler
0731      */
0732     void (*userCloseHandler)(const struct mg_connection *conn);
0733 };
0734 
0735 #endif /*  __cplusplus */
0736 #endif /* CIVETSERVER_HEADER_INCLUDED */