00001 /****************************************************************************** 00002 * cgi_in.h 2000-10-31 AgF * 00003 * CGI interface for C++ programs * 00004 ******************************************************************************* 00005 00006 This header file defines the class CGI_Interface and the object cgi to 00007 facilitate web interface through CGI (Comman Gateway Interface). 00008 00009 The constructor outputs a cgi header and reads input parameters from both 00010 POST and GET methods. 00011 00012 Instructions: 00013 ------------- 00014 Write #include <cgi_in.h> in the beginning of your C++ program to get easy 00015 access to input parameters. 00016 00017 The member functions cgi.GetString(char * key), cgi.GetInt(char * key), 00018 and cgi.GetFloat(char * key) are used for getting the values for any input 00019 parameter, where key is the name of the parameter (case sensitive). 00020 00021 Using with multiple modules: 00022 ---------------------------- 00023 If your C++ program consists of multiple modules compiled separately, 00024 then #define NOTMAIN in all but one of the modules to avoid multiple 00025 instances of the object cgi. 00026 00027 Testing on a PC: 00028 ---------------- 00029 If the program is compiled on a PC (DOS or Windows) it will not attempt to 00030 read CGI input, which only exists on a web server. Instead, it will read 00031 the input from a file named input.txt. This file should have the format: 00032 PARAMETER1=VALUE1 00033 PARAMETER2=VALUE2 00034 PARAMETER3=VALUE3 00035 00036 modified by Dan Spinosa 2005 00037 00038 *****************************************************************************/ 00039 00040 #include <iostream> 00041 #include <string.h> 00042 #include <stdlib.h> 00043 00044 const int MAXKEYS = 1000; // max. number input parameters 00045 const int MAXINPUTLEN = 13000; // max. total length of all inputs and keys 00046 00047 using namespace std; 00048 00049 // class CGI_Interface facilitates input/output 00051 class CGI_Interface { 00052 public: 00053 CGI_Interface(); // constructor 00054 char * GetString(char * key); // get input parameter named 'key' as string 00055 int GetInt(char * key); // get input parameter named 'key' as integer 00056 float GetFloat(char * key); // get input parameter named 'key' as float 00057 int NumberOfKeys(); // get number of keys 00058 char * GetNextKey(); // call repeatedly to get all key names 00059 void BeginKey(); // reset GetNextKey 00060 protected: 00061 char InputBuffer[MAXINPUTLEN]; // stores all input 00062 char * keys[MAXKEYS]; // all keys (= field names) 00063 char * values[MAXKEYS]; // corresponding values 00064 int NumKeys; // number of keys 00065 int KeyIndex; // index for GetNextKey 00066 }; 00067 00068 //#ifdef __unix__ // check if compiled under unix (this is normal use) 00069 // constructor 00070 CGI_Interface::CGI_Interface() { 00071 //cout << "CGI INTERFACE CONSTRUCTOR" << endl; 00072 char * p; int len; 00073 //if it wasn't passed in (as a hack) 00074 // read input from cin 00075 cin.get(InputBuffer, MAXINPUTLEN, 0); 00076 // append input from QUERY_STRING 00077 p = getenv("QUERY_STRING"); 00078 len = strlen(InputBuffer); 00079 00080 00081 if (p && *p && len + 4 < MAXINPUTLEN) { 00082 if (len > 1) strcat(InputBuffer,"&"); 00083 strncat(InputBuffer, p, MAXINPUTLEN-len-1); 00084 } 00085 // InputBuffer has the form: 00086 // key1=value1&key2=value2&key3=value3 ... 00087 // split the string into keys and values: 00088 NumKeys = KeyIndex = 0; p = InputBuffer; 00089 while (NumKeys < MAXKEYS) { 00090 keys[NumKeys] = p; // pointer to key 00091 p = strchr (p, '='); // search for '=' 00092 if (p==0) break; // stop if '=' not found 00093 *p = 0; // end key string 00094 values[NumKeys++] = ++p; // point to value 00095 p = strchr (p, '&'); // search for '&' separator 00096 if (p==0) break; // stop if '&' not found 00097 *p = 0; p++; // end value string 00098 } 00099 00100 // translate special characters in values: 00101 for (int i=0; i<NumKeys; i++) { 00102 // replace all '+' with space 00103 p = values[i]; 00104 while (1) { 00105 p = strchr(p,'+'); 00106 if (p==0) break; 00107 *p = ' '; 00108 } 00109 // replace %XX with character that has hexadecimal code XX 00110 p = values[i]; 00111 while (1) { 00112 p = strchr(p,'%'); 00113 if (p==0) break; 00114 int hi = p[1] | 0x20; 00115 int lo = p[2] | 0x20; 00116 if (hi > '9') hi -= 87; else hi -= 48; 00117 if (lo > '9') lo -= 87; else lo -= 48; 00118 *p = (char)(hi * 16 + lo); 00119 strcpy (p+1, p+3); p++; 00120 } 00121 } 00122 // write cgi header to tell that the output is html: 00123 //cout << "Content-type: text/html\n\n"; 00124 } 00125 00126 /* 00127 #else // not compiled under unix. Assume it is compiled on PC for testing only 00128 00129 #include <PC fstream.h> 00130 // PC test version of constructor 00131 CGI_Interface::CGI_Interface() { 00132 int len, spaceleft = MAXINPUTLEN-1; char * p, * q; 00133 NumKeys = KeyIndex = 0; 00134 // get input from file named input.txt 00135 ifstream inputfile("input.txt", ios::in); 00136 if (inputfile) { 00137 p = InputBuffer; 00138 // read from inputfile until end of file or InputBuffer full 00139 while (!inputfile.eof() && spaceleft > 1) { 00140 *p = 0; 00141 inputfile.getline(p, spaceleft); 00142 if (*p) { 00143 len = strlen(p); 00144 keys[NumKeys] = p; // point to key 00145 q = strchr(p, '='); // find '=' 00146 if (q) { 00147 values[NumKeys++] = q+1; // value comes after '=' 00148 *q = 0;} // end key string 00149 p += len; spaceleft -= len;}} 00150 inputfile.close();} 00151 else { 00152 cout << "\nFile input.txt not found<p>\n";}} 00153 #endif 00154 */ 00155 00156 // get input as string 00157 char * CGI_Interface::GetString(char * key) { 00158 for (int i=0; i<NumKeys; i++) { 00159 if (strcmp(keys[i],key)==0) { 00160 return values[i]; 00161 } 00162 } 00163 return ""; 00164 } 00165 00166 // get input as integer 00167 int CGI_Interface::GetInt(char * key) { 00168 for (int i=0; i<NumKeys; i++) { 00169 if (strcmp(keys[i],key)==0) { 00170 return atoi(values[i]); 00171 } 00172 } 00173 return 0; 00174 } 00175 00176 // get input as float 00177 float CGI_Interface::GetFloat(char * key) { 00178 for (int i=0; i<NumKeys; i++) { 00179 if (strcmp(keys[i],key)==0) { 00180 return float(atof(values[i])); 00181 } 00182 } 00183 return 0.; 00184 } 00185 00186 // get number of keys 00187 int CGI_Interface::NumberOfKeys() { 00188 return NumKeys; 00189 } 00190 00191 // call repeatedly to get all keys 00192 char * CGI_Interface::GetNextKey() { 00193 if (KeyIndex >= NumKeys) return 0; 00194 return keys[KeyIndex++]; 00195 } 00196 00197 // reset GetNextKey 00198 void CGI_Interface::BeginKey() { 00199 KeyIndex = 0; 00200 } 00201 00202 // define cgi interface object and call constructor 00203 #ifndef NOTMAIN 00204 //CGI_Interface cgi; 00205 #endif 00206 00207