Some code towards a FastCGI server
[iotcloud.git] / src / server / iotcloud.cpp
1 #include <iostream>
2 #include "fcgio.h"
3 #include "fcgi_stdio.h"
4 #include <stdlib.h>
5 #include <string.h>
6 #define MAX_VARS 31
7
8 const char * query_str="QUERY_STRING";
9 const char * uri_str="REQUEST_URI";
10 const char * method_str="REQUEST_METHOD";
11 const char * iotcloudroot_str="IOTCLOUD_ROOT";
12
13 using namespace std;
14
15 struct iotquery {
16   const char * uri;
17   const char * query;
18   const char * method;
19   const char * iotcloudroot;
20 };
21
22 void parsequery(struct iotquery *, FCGX_Request *);
23 char * getdirectory(struct iotquery *);
24
25 int main(void) {
26     // Backup the stdio streambufs
27     streambuf * cin_streambuf  = cin.rdbuf();
28     streambuf * cout_streambuf = cout.rdbuf();
29     streambuf * cerr_streambuf = cerr.rdbuf();
30
31     FCGX_Request request;
32
33     FCGX_Init();
34     FCGX_InitRequest(&request, 0, 0);
35
36     while (FCGX_Accept_r(&request) == 0) {
37       fcgi_streambuf cin_fcgi_streambuf(request.in);
38       fcgi_streambuf cout_fcgi_streambuf(request.out);
39       fcgi_streambuf cerr_fcgi_streambuf(request.err);
40       
41       cin.rdbuf(&cin_fcgi_streambuf);
42       cout.rdbuf(&cout_fcgi_streambuf);
43       cerr.rdbuf(&cerr_fcgi_streambuf);
44
45       struct iotquery query;
46       parsequery(&query, &request);
47       char * directory = getdirectory(&query);
48       
49       cout << "Content-type: text/html\r\n"
50            << "\r\n"
51            << "<html>\n"
52            << "  <head>\n"
53            << "    <title>Hello, World!</title>\n"
54            << "  </head>\n"
55            << "  <body>\n"
56            << "    <h1>Hello, World!</h1>\n"
57            << "  </body>\n";
58       char c[80];
59
60       cout << uri_str << " " << query.uri << "\n";
61       cout << query_str << " " << query.query << "\n";
62       cout << method_str << " " << query.method << "\n";
63       cout << iotcloudroot_str << " " << query.iotcloudroot << "\n";
64       
65
66       do {
67         cin.read(c, 80);
68         c[cin.gcount()]=0;
69         cout << "[" << c << "]";
70       } while(!cin.eof());
71       
72
73       
74       
75       cout << "</html>\n";
76       // Note: the fcgi_streambuf destructor will auto flush
77
78       if (directory != NULL)
79         free(directory);
80     }
81
82     // restore stdio streambufs
83     cin.rdbuf(cin_streambuf);
84     cout.rdbuf(cout_streambuf);
85     cerr.rdbuf(cerr_streambuf);
86
87     return 0;
88 }
89
90
91 void parsequery(struct iotquery * query, FCGX_Request * request) {
92   query->uri = FCGX_GetParam(uri_str, request->envp);
93   query->query = FCGX_GetParam(query_str, request->envp);
94   query->method = FCGX_GetParam(method_str, request->envp);
95   query->iotcloudroot = FCGX_GetParam(iotcloudroot_str, request->envp);
96 }
97
98 char * getdirectory(struct iotquery * query) {
99   char * split = strchr((char *)query->uri, '?');
100   if (split == NULL)
101     return NULL;
102   int split_len = (int) (split-query->uri);
103   int rootdir_len = strlen(query->iotcloudroot);
104   int directory_len = split_len + rootdir_len + 1;
105   char * directory = (char *) malloc(directory_len);
106   memcpy(directory, query->iotcloudroot, rootdir_len);
107   memcpy(directory + rootdir_len, query->uri, split_len);
108   directory[directory_len]=0;
109   return directory;  
110 }