MythTV  0.26-pre
httprequest.h
Go to the documentation of this file.
00001 
00002 // Program Name: httprequest.h
00003 // Created     : Oct. 21, 2005
00004 //
00005 // Purpose     : Http Request/Response
00006 //                                                                            
00007 // Copyright (c) 2005 David Blain <dblain@mythtv.org>
00008 //                                          
00009 // Licensed under the GPL v2 or later, see COPYING for details                    
00010 //
00012 
00013 #ifndef HTTPREQUEST_H_
00014 #define HTTPREQUEST_H_
00015 
00016 #include <QFile>
00017 #include <QRegExp>
00018 #include <QBuffer>
00019 #include <QTextStream>
00020 
00021 using namespace std;
00022 
00023 #include "upnpexp.h"
00024 #include "upnputil.h"
00025 #include "bufferedsocketdevice.h"
00026 #include "serializers/serializer.h"
00027 
00028 #define SOAP_ENVELOPE_BEGIN  "<s:Envelope xmlns:s=\"http://schemas.xmlsoap.org/soap/envelope/\" " \
00029                              "s:encodingStyle=\"http://schemas.xmlsoap.org/soap/encoding/\">"     \
00030                              "<s:Body>"
00031 #define SOAP_ENVELOPE_END    "</s:Body>\r\n</s:Envelope>";
00032 
00033 
00035 // Typedefs / Defines
00037 
00038 typedef enum 
00039 {
00040     RequestTypeUnknown      = 0x0000,
00041     RequestTypeGet          = 0x0001,
00042     RequestTypeHead         = 0x0002,
00043     RequestTypePost         = 0x0004,
00044     RequestTypeMSearch      = 0x0008,
00045     RequestTypeSubscribe    = 0x0010,
00046     RequestTypeUnsubscribe  = 0x0020,
00047     RequestTypeNotify       = 0x0040,
00048     RequestTypeResponse     = 0x0080
00049 
00050 } RequestType;                
00051 
00052 typedef enum 
00053 {
00054     ContentType_Unknown    = 0,
00055     ContentType_Urlencoded = 1,
00056     ContentType_XML        = 2
00057 
00058 } ContentType;
00059 
00060 typedef enum 
00061 {
00062     ResponseTypeNone     = -1,
00063     ResponseTypeUnknown  =  0,
00064     ResponseTypeXML      =  1,
00065     ResponseTypeHTML     =  2,
00066     ResponseTypeFile     =  3,
00067     ResponseTypeOther    =  4
00068 
00069 } ResponseType;
00070 
00071 
00072 typedef struct
00073 {
00074     const char *pszExtension;
00075     const char *pszType;
00076 
00077 } MIMETypes;
00078 
00080 
00081 class IPostProcess
00082 {
00083     public:
00084         virtual void ExecutePostProcess( ) = 0;
00085         virtual ~IPostProcess() {};
00086 };
00087 
00089 // 
00091 
00092 class UPNP_PUBLIC HTTPRequest
00093 {
00094     protected:
00095 
00096         static const char  *m_szServerHeaders;
00097 
00098         QRegExp             m_procReqLineExp;
00099         QRegExp             m_parseRangeExp;
00100 
00101     public:    
00102         
00103         RequestType         m_eType;
00104         ContentType         m_eContentType;
00105 
00106         QString             m_sRawRequest;
00107 
00108         QString             m_sBaseUrl;
00109         QString             m_sResourceUrl;
00110         QString             m_sMethod;
00111 
00112         QStringMap          m_mapParams;
00113         QStringMap          m_mapHeaders;
00114 
00115         QString             m_sPayload;
00116 
00117         QString             m_sProtocol;
00118         int                 m_nMajor;
00119         int                 m_nMinor;
00120 
00121         bool                m_bProtected;
00122 
00123         bool                m_bSOAPRequest;
00124         QString             m_sNameSpace;
00125 
00126         // Response
00127 
00128         ResponseType        m_eResponseType;
00129         QString             m_sResponseTypeText;    // used for ResponseTypeOther
00130 
00131         long                m_nResponseStatus;
00132         QStringMap          m_mapRespHeaders;
00133 
00134         QString             m_sFileName;
00135 
00136         QBuffer             m_response;
00137 
00138         IPostProcess       *m_pPostProcess;
00139 
00140     protected:
00141 
00142         RequestType     SetRequestType      ( const QString &sType  );
00143         void            SetRequestProtocol  ( const QString &sLine  );
00144         ContentType     SetContentType      ( const QString &sType  );
00145 
00146         void            SetServerHeaders    ( void );
00147 
00148         void            ProcessRequestLine  ( const QString &sLine  );
00149         bool            ProcessSOAPPayload  ( const QString &sSOAPAction );
00150         void            ExtractMethodFromURL( );
00151 
00152         QString         GetResponseStatus   ( void );
00153         QString         GetResponseType     ( void );
00154         QString         GetAdditionalHeaders( void );
00155 
00156         bool            ParseRange          ( QString sRange, 
00157                                               long long   llSize, 
00158                                               long long *pllStart, 
00159                                               long long *pllEnd   );
00160 
00161         QString         BuildHeader         ( long long nSize );
00162 
00163         qint64          SendData            ( QIODevice *pDevice, qint64 llStart, qint64 llBytes );
00164         qint64          SendFile            ( QFile &file, qint64 llStart, qint64 llBytes );
00165 
00166         bool            IsUrlProtected      ( const QString &sBaseUrl );
00167         bool            Authenticated       ();
00168 
00169     public:
00170         
00171                         HTTPRequest     ();
00172         virtual        ~HTTPRequest     () {};
00173 
00174         bool            ParseRequest    ();
00175 
00176         void            FormatErrorResponse ( bool  bServerError, 
00177                                               const QString &sFaultString, 
00178                                               const QString &sDetails );
00179 
00180         void            FormatActionResponse( Serializer *ser );
00181         void            FormatActionResponse( const NameValues &pArgs );
00182         void            FormatFileResponse  ( const QString &sFileName );
00183         void            FormatRawResponse   ( const QString &sXML );
00184 
00185         long            SendResponse    ( void );
00186         long            SendResponseFile( QString sFileName );
00187 
00188         QString         GetHeaderValue  ( const QString &sKey, QString sDefault );
00189 
00190         bool            GetKeepAlive    ();
00191 
00192         Serializer *    GetSerializer   ();
00193 
00194         static QString  GetMimeType     ( const QString &sFileExtension );
00195         static QString  TestMimeType    ( const QString &sFileName );
00196         static long     GetParameters   ( QString  sParams, QStringMap &mapParams );
00197         static QString  Encode          ( const QString &sIn );
00198         static QString  GetETagHash     ( const QByteArray &data );
00199 
00200         // ------------------------------------------------------------------
00201 
00202         virtual qlonglong  BytesAvailable  () = 0;
00203         virtual qulonglong WaitForMore     ( int msecs, bool *timeout = NULL ) = 0;
00204         virtual bool    CanReadLine     () = 0;
00205         virtual QString ReadLine        ( int msecs = 0 ) = 0;
00206         virtual qlonglong  ReadBlock       ( char *pData, qulonglong nMaxLen, int msecs = 0 ) = 0;
00207         virtual qlonglong  WriteBlock      ( const char *pData,
00208                                           qulonglong nLen    ) = 0;
00209         virtual qlonglong  WriteBlockDirect( const char *pData,
00210                                           qulonglong nLen    ) = 0;
00211         virtual QString GetHostAddress  () = 0;
00212         virtual QString GetPeerAddress  () = 0;
00213         virtual void    Flush           () = 0;
00214         virtual bool    IsValid         () = 0;
00215         virtual int     getSocketHandle () = 0;
00216         virtual void    SetBlocking     ( bool bBlock ) = 0;
00217         virtual bool    IsBlocking      () = 0;
00218 };
00219 
00221 // 
00223 
00224 class BufferedSocketDeviceRequest : public HTTPRequest
00225 {
00226     public:    
00227 
00228         BufferedSocketDevice    *m_pSocket;
00229 
00230     public:
00231         
00232                  BufferedSocketDeviceRequest( BufferedSocketDevice *pSocket );
00233         virtual ~BufferedSocketDeviceRequest() {};
00234 
00235         virtual qlonglong  BytesAvailable  ();
00236         virtual qulonglong WaitForMore     ( int msecs, bool *timeout = NULL );
00237         virtual bool    CanReadLine     ();
00238         virtual QString ReadLine        ( int msecs = 0 );
00239         virtual qlonglong  ReadBlock       ( char *pData, qulonglong nMaxLen, int msecs = 0  );
00240         virtual qlonglong  WriteBlock      ( const char *pData, qulonglong nLen    );
00241         virtual qlonglong  WriteBlockDirect( const char *pData, qulonglong nLen    );
00242         virtual QString GetHostAddress  ();
00243         virtual QString GetPeerAddress  ();
00244         virtual void    Flush           () { m_pSocket->Flush(); }
00245         virtual bool    IsValid         () {return( m_pSocket->IsValid() ); }
00246         virtual int     getSocketHandle () {return( m_pSocket->socket() ); }
00247         virtual void    SetBlocking     ( bool bBlock );
00248         virtual bool    IsBlocking      ();
00249 
00250 };
00251 
00253 // 
00255 
00256 class UPNP_PUBLIC HttpException
00257 {
00258     public:
00259         int     code;
00260         QString msg;
00261 
00262         HttpException( int nCode = -1, const QString &sMsg = "") 
00263                : code( nCode ), msg ( sMsg  ) 
00264         {}
00265 
00266         // Needed to force a v-table.
00267         virtual ~HttpException() 
00268         {}
00269 };
00270 
00271 class UPNP_PUBLIC HttpRedirectException : public HttpException
00272 {
00273     public:
00274 
00275         QString hostName;
00276       //int     port;
00277 
00278         HttpRedirectException( const QString &sHostName = "", 
00279                                      int      nCode     = -1, 
00280                                const QString &sMsg      = "" ) 
00281                : HttpException( nCode, sMsg ), hostName( sHostName )
00282         {}
00283 
00284         virtual ~HttpRedirectException() 
00285         {}
00286 
00287 };
00288 
00289 #endif
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends