webroar 0.3.1 → 0.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/CHANGELOG +48 -1
- data/README +11 -14
- data/Rakefile +1 -1
- data/conf/mime_type.yml +172 -166
- data/conf/server_internal_config.yml +30 -8
- data/doc/user-guide.html +294 -153
- data/doc/user-guide.txt +9 -13
- data/lib/command_runner.rb +1 -0
- data/lib/dependencies.rb +18 -15
- data/lib/installer.rb +115 -50
- data/src/admin_panel/app/controllers/admin_controller.rb +1 -15
- data/src/admin_panel/app/controllers/application_controller.rb +2 -2
- data/src/admin_panel/app/controllers/application_specification_controller.rb +2 -1
- data/src/admin_panel/app/controllers/headers_controller.rb +73 -0
- data/src/admin_panel/app/controllers/mail_specification_controller.rb +10 -0
- data/src/admin_panel/app/controllers/server_specification_controller.rb +14 -0
- data/src/admin_panel/app/helpers/admin_helper.rb +0 -85
- data/src/admin_panel/app/models/app.rb +1 -1
- data/src/admin_panel/app/models/application_specification.rb +33 -25
- data/src/admin_panel/app/models/headers.rb +116 -0
- data/src/admin_panel/app/models/mail_specification.rb +20 -5
- data/src/admin_panel/app/models/server_specification.rb +2 -7
- data/src/admin_panel/app/views/admin/configuration.html.erb +10 -5
- data/src/admin_panel/app/views/exceptions/_exception_list_partial.html.erb +4 -4
- data/src/admin_panel/app/views/graph/_graph_page.html.erb +3 -0
- data/src/admin_panel/app/views/headers/_add_expires_text_box.html.erb +35 -0
- data/src/admin_panel/app/views/headers/_expires_by_type_form.html.erb +65 -0
- data/src/admin_panel/app/views/headers/_headers_table.html.erb +113 -0
- data/src/admin_panel/app/views/mail_specification/_current_spec.html.erb +168 -0
- data/src/admin_panel/app/views/{admin → server_specification}/_add_div.html.erb +1 -1
- data/src/admin_panel/config/initializers/application_constants.rb +6 -0
- data/src/admin_panel/lib/control.rb +6 -3
- data/src/admin_panel/lib/scgi.rb +74 -21
- data/src/admin_panel/lib/yaml_writer.rb +51 -17
- data/src/admin_panel/public/javascripts/application.js +20 -1
- data/src/head/wr_access_log.c +2 -2
- data/src/head/wr_application.c +294 -236
- data/src/head/wr_application.h +8 -8
- data/src/head/wr_configurator.c +451 -517
- data/src/head/wr_configurator.h +10 -115
- data/src/head/wr_connection.c +26 -25
- data/src/head/wr_connection.h +2 -3
- data/src/head/wr_controller.c +110 -93
- data/src/head/wr_controller.h +6 -6
- data/src/head/wr_main.c +31 -24
- data/src/head/wr_request.c +70 -93
- data/src/head/wr_request.h +0 -4
- data/src/head/wr_resolver.c +21 -15
- data/src/head/wr_resolver.h +2 -2
- data/src/head/wr_server.c +36 -26
- data/src/head/wr_server.h +5 -5
- data/src/head/wr_worker.c +551 -512
- data/src/head/wr_worker.h +33 -20
- data/src/helper/wr_config.c +316 -0
- data/src/helper/wr_config.h +235 -0
- data/src/helper/wr_helper.h +1 -5
- data/src/helper/wr_logger.c +4 -4
- data/src/helper/wr_scgi.c +3 -4
- data/src/helper/wr_scgi.h +2 -0
- data/src/helper/wr_string.h +2 -2
- data/src/helper/wr_util.c +3 -1
- data/src/helper/wr_util.h +0 -0
- data/src/helper/wr_yaml_parser.c +30 -0
- data/src/helper/wr_yaml_parser.h +1 -0
- data/src/ruby_lib/exception_tracker/instrumentation/action_controller.rb +2 -1
- data/src/ruby_lib/mailer/smtpmail.rb +7 -4
- data/src/ruby_lib/profiler/instrumentation/action_controller.rb +2 -1
- data/src/ruby_lib/profiler/instrumentation/active_record.rb +3 -0
- data/src/ruby_lib/rack/adapter/rails.rb +14 -7
- data/src/ruby_lib/ruby_interface/client.rb +1 -1
- data/src/ruby_lib/ruby_interface/version.rb +2 -2
- data/src/ruby_lib/webroar_app_loader.rb +4 -2
- data/src/worker/wkr_controller.c +200 -140
- data/src/worker/wkr_http.c +14 -28
- data/src/worker/wkr_http.h +4 -4
- data/src/worker/wkr_http_request.c +12 -11
- data/src/worker/wkr_http_request.h +7 -8
- data/src/worker/wkr_http_response.c +10 -14
- data/src/worker/wkr_http_response.h +0 -1
- data/src/worker/wkr_main.c +74 -140
- data/src/worker/wkr_static.c +295 -108
- data/src/worker/wkr_static.h +20 -7
- data/src/worker/worker.c +245 -70
- data/src/worker/worker.h +46 -34
- data/tasks/compile.rake +128 -175
- data/tasks/test.rake +345 -469
- data/test/spec/webroar_command_spec.rb +23 -0
- metadata +173 -43
- data/src/admin_panel/vendor/plugins/action_mailer_optional_tls/README +0 -34
- data/src/admin_panel/vendor/plugins/action_mailer_optional_tls/Rakefile +0 -13
- data/src/admin_panel/vendor/plugins/action_mailer_optional_tls/init.rb +0 -5
- data/src/admin_panel/vendor/plugins/action_mailer_optional_tls/lib/action_mailer_tls.rb +0 -16
- data/src/admin_panel/vendor/plugins/action_mailer_optional_tls/lib/smtp_tls.rb +0 -123
- data/src/admin_panel/vendor/plugins/action_mailer_optional_tls/test/tls_test.rb +0 -42
- data/src/head/wr_config.h +0 -165
- data/src/ruby_lib/mailer/action_mailer_tls.rb +0 -16
- data/src/ruby_lib/mailer/smtp_tls.rb +0 -123
data/src/worker/wkr_static.c
CHANGED
|
@@ -27,10 +27,12 @@
|
|
|
27
27
|
#include <string.h>
|
|
28
28
|
#include <fcntl.h>
|
|
29
29
|
|
|
30
|
+
#ifdef W_ZLIB
|
|
31
|
+
#include <zlib.h>
|
|
32
|
+
#endif
|
|
30
33
|
|
|
31
|
-
|
|
34
|
+
extern config_t *Config;
|
|
32
35
|
|
|
33
|
-
#define MAP_SIZE 36
|
|
34
36
|
#define DEFAULT_EXPIRES "Headers/expires"
|
|
35
37
|
#define EXPIRES_BY_TYPE "Headers/expires_by_type"
|
|
36
38
|
#define EXPIRES_BY_TYPE_EXT "expires_by_type/ext"
|
|
@@ -52,7 +54,7 @@ typedef enum {
|
|
|
52
54
|
HTTP_STATUS_404
|
|
53
55
|
} resp_status_t;
|
|
54
56
|
|
|
55
|
-
typedef void (*resp_fun_t) (http_t
|
|
57
|
+
typedef void (*resp_fun_t) (http_t*);
|
|
56
58
|
|
|
57
59
|
typedef struct {
|
|
58
60
|
wr_u_short code;
|
|
@@ -61,10 +63,10 @@ typedef struct {
|
|
|
61
63
|
resp_fun_t fun;
|
|
62
64
|
} http_status_t;
|
|
63
65
|
|
|
64
|
-
void http_resp_200(http_t
|
|
65
|
-
void http_resp_304(http_t
|
|
66
|
-
void http_resp_403(http_t
|
|
67
|
-
void http_resp_404(http_t
|
|
66
|
+
void http_resp_200(http_t*);
|
|
67
|
+
void http_resp_304(http_t*);
|
|
68
|
+
void http_resp_403(http_t*);
|
|
69
|
+
void http_resp_404(http_t*);
|
|
68
70
|
|
|
69
71
|
static http_status_t http_status [] = {
|
|
70
72
|
{200, "200 OK", "", http_resp_200},
|
|
@@ -89,15 +91,12 @@ Content-Length: %d\r\n\r\n"
|
|
|
89
91
|
<br><hr>%s-%s\
|
|
90
92
|
</body></html>"
|
|
91
93
|
|
|
92
|
-
// Static mapping object
|
|
93
|
-
static static_file_t* map[MAP_SIZE + 1];
|
|
94
|
-
|
|
95
94
|
/**************************************
|
|
96
95
|
* Private Functions
|
|
97
96
|
*************************************/
|
|
98
97
|
|
|
99
98
|
/** Searches path backward and returns pointer to the first character of extension */
|
|
100
|
-
|
|
99
|
+
char* get_file_ext(const char *path) {
|
|
101
100
|
int len = strlen(path);
|
|
102
101
|
char *ext = path + len;
|
|
103
102
|
while (len) {
|
|
@@ -110,9 +109,9 @@ static char* get_file_ext(const char *path) {
|
|
|
110
109
|
}
|
|
111
110
|
|
|
112
111
|
/** Set expires time based on file type */
|
|
113
|
-
|
|
112
|
+
void set_expires_time(static_server_t * s, char *ext, long int expires) {
|
|
114
113
|
int index;
|
|
115
|
-
char tmp_ext[
|
|
114
|
+
char tmp_ext[STR_SIZE64], *p;
|
|
116
115
|
strcpy(tmp_ext, ext);
|
|
117
116
|
p = tmp_ext;
|
|
118
117
|
while(*p){
|
|
@@ -130,9 +129,10 @@ static void set_expires_time(char *ext, long int expires) {
|
|
|
130
129
|
}
|
|
131
130
|
|
|
132
131
|
if (index >= 0 && index < MAP_SIZE) {
|
|
133
|
-
static_file_t *e = map[index];
|
|
132
|
+
static_file_t *e = s->map[index];
|
|
134
133
|
while (e) {
|
|
135
134
|
if (strcmp(e->ext, tmp_ext) == 0) {
|
|
135
|
+
//HTTP/1.1 servers SHOULD NOT send Expires dates more than one year in the future.
|
|
136
136
|
e->expires = expires;
|
|
137
137
|
break;
|
|
138
138
|
}
|
|
@@ -142,9 +142,9 @@ static void set_expires_time(char *ext, long int expires) {
|
|
|
142
142
|
}
|
|
143
143
|
|
|
144
144
|
/* Get mime-type */
|
|
145
|
-
|
|
146
|
-
char *ext = get_file_ext(path);
|
|
147
|
-
char tmp_ext[
|
|
145
|
+
static_file_t* get_mime_type(static_server_t *s) {
|
|
146
|
+
char *ext = get_file_ext(s->path);
|
|
147
|
+
char tmp_ext[STR_SIZE64], *p;
|
|
148
148
|
strcpy(tmp_ext, ext);
|
|
149
149
|
p = tmp_ext;
|
|
150
150
|
while(*p){
|
|
@@ -164,7 +164,7 @@ static static_file_t* get_mime_type(const char *path) {
|
|
|
164
164
|
}
|
|
165
165
|
|
|
166
166
|
if (index >= 0 && index < MAP_SIZE) {
|
|
167
|
-
static_file_t *e = map[index];
|
|
167
|
+
static_file_t *e = s->map[index];
|
|
168
168
|
while (e) {
|
|
169
169
|
if (strcmp(e->ext, tmp_ext) == 0) {
|
|
170
170
|
return e;
|
|
@@ -173,39 +173,38 @@ static static_file_t* get_mime_type(const char *path) {
|
|
|
173
173
|
}
|
|
174
174
|
}
|
|
175
175
|
}
|
|
176
|
-
return map[MAP_SIZE];
|
|
176
|
+
return s->map[MAP_SIZE];
|
|
177
177
|
}
|
|
178
178
|
|
|
179
179
|
/** Get response code */
|
|
180
|
-
|
|
180
|
+
short get_resp_code(static_server_t *s) {
|
|
181
181
|
LOG_FUNCTION
|
|
182
|
-
const char *modify = scgi_header_value_get(h->req->scgi, HTTP_HEADER_IF_MODIFIED_SINCE);
|
|
183
182
|
time_t modify_tm;
|
|
184
183
|
|
|
185
|
-
if (path == NULL) {
|
|
184
|
+
if (s->path == NULL) {
|
|
186
185
|
LOG_ERROR(WARN, "Requested file path is NULL.");
|
|
187
186
|
return HTTP_STATUS_404;
|
|
188
187
|
}
|
|
189
188
|
|
|
190
|
-
if (stat(path, buf)) {
|
|
191
|
-
LOG_ERROR(WARN, "Requested file %s does not exist.", path);
|
|
189
|
+
if (stat(s->path, &(s->buf))) {
|
|
190
|
+
LOG_ERROR(WARN, "Requested file %s does not exist.", s->path);
|
|
192
191
|
return HTTP_STATUS_404;
|
|
193
192
|
}
|
|
194
193
|
|
|
195
|
-
if (S_ISDIR(buf
|
|
196
|
-
LOG_ERROR(WARN, "%s is a directory.", path)
|
|
194
|
+
if (S_ISDIR(s->buf.st_mode) != 0) {
|
|
195
|
+
LOG_ERROR(WARN, "%s is a directory.", s->path)
|
|
197
196
|
return HTTP_STATUS_404;
|
|
198
197
|
}
|
|
199
198
|
|
|
200
|
-
if (strstr(path, "..")) {
|
|
201
|
-
LOG_ERROR(WARN, "Requested file path %s is forbidden.", path);
|
|
199
|
+
if (strstr(s->path, "..")) {
|
|
200
|
+
LOG_ERROR(WARN, "Requested file path %s is forbidden.", s->path);
|
|
202
201
|
return HTTP_STATUS_403;
|
|
203
202
|
}
|
|
204
203
|
// Compare 'If-Modified-Since' time with file modication time
|
|
205
|
-
if (modify) {
|
|
204
|
+
if (s->modify) {
|
|
206
205
|
// Assume 'If-Modified-Since' date zone is GMT
|
|
207
|
-
modify_tm = httpdate_to_c_time(modify) - timezone;
|
|
208
|
-
long int diff = difftime(buf
|
|
206
|
+
modify_tm = httpdate_to_c_time(s->modify) - timezone;
|
|
207
|
+
long int diff = difftime(s->buf.st_mtime, modify_tm);
|
|
209
208
|
if (diff <= 0) {
|
|
210
209
|
return HTTP_STATUS_304;
|
|
211
210
|
}
|
|
@@ -213,7 +212,7 @@ static short get_resp_code(http_t *h, const char *path, struct stat *buf) {
|
|
|
213
212
|
return HTTP_STATUS_200;
|
|
214
213
|
}
|
|
215
214
|
|
|
216
|
-
|
|
215
|
+
long int get_default_expires(node_t *root) {
|
|
217
216
|
char *node_value = get_node_value(root, DEFAULT_EXPIRES);
|
|
218
217
|
|
|
219
218
|
if (node_value == NULL) {
|
|
@@ -226,21 +225,31 @@ static long int get_default_expires(node_t *root) {
|
|
|
226
225
|
}
|
|
227
226
|
}
|
|
228
227
|
|
|
229
|
-
|
|
228
|
+
/** Read 'mime_type.yml' file and create dictionary for supported Content-Type. */
|
|
229
|
+
int create_dictionary(static_server_t *s, const char *mapping_file, long int expires) {
|
|
230
230
|
node_t *root = yaml_parse(mapping_file), *node;
|
|
231
231
|
static_file_t *ext;
|
|
232
232
|
int index;
|
|
233
233
|
|
|
234
234
|
// Initialize map with NULL value
|
|
235
235
|
for (index = 0; index < MAP_SIZE; index++) {
|
|
236
|
-
map[index] = NULL;
|
|
236
|
+
s->map[index] = NULL;
|
|
237
237
|
}
|
|
238
238
|
|
|
239
239
|
if (root == NULL) {
|
|
240
240
|
LOG_ERROR(SEVERE, "Could not read the file %s", mapping_file);
|
|
241
241
|
return -1;
|
|
242
242
|
}
|
|
243
|
-
|
|
243
|
+
|
|
244
|
+
node = get_nodes(root, "File Extensions");
|
|
245
|
+
|
|
246
|
+
if (root == NULL || node->child == NULL) {
|
|
247
|
+
LOG_ERROR(SEVERE, "Could not read 'File Extensions' from the file %s", mapping_file);
|
|
248
|
+
return -1;
|
|
249
|
+
}
|
|
250
|
+
|
|
251
|
+
node = node->child;
|
|
252
|
+
|
|
244
253
|
while (node) {
|
|
245
254
|
ext = wr_malloc(static_file_t);
|
|
246
255
|
strcpy(ext->ext, node->name);
|
|
@@ -256,8 +265,8 @@ static int create_dictionary(const char *mapping_file, long int expires) {
|
|
|
256
265
|
}
|
|
257
266
|
|
|
258
267
|
if (index >= 0 && index < MAP_SIZE) {
|
|
259
|
-
ext->next = map[index];
|
|
260
|
-
map[index] = ext;
|
|
268
|
+
ext->next = s->map[index];
|
|
269
|
+
s->map[index] = ext;
|
|
261
270
|
}else {
|
|
262
271
|
LOG_ERROR(WARN, "Mapping index out of bound for extension = %s", ext->ext);
|
|
263
272
|
free(ext);
|
|
@@ -272,12 +281,12 @@ static int create_dictionary(const char *mapping_file, long int expires) {
|
|
|
272
281
|
strcpy(ext->mime_type, "text/plain");
|
|
273
282
|
ext->expires = expires;
|
|
274
283
|
ext->next = NULL;
|
|
275
|
-
map[MAP_SIZE] = ext;
|
|
284
|
+
s->map[MAP_SIZE] = ext;
|
|
276
285
|
|
|
277
286
|
return 0;
|
|
278
287
|
}
|
|
279
288
|
|
|
280
|
-
|
|
289
|
+
void set_expires_by_type(static_server_t *s, node_t *root) {
|
|
281
290
|
node_t *node = get_nodes(root, EXPIRES_BY_TYPE);
|
|
282
291
|
long int expires;
|
|
283
292
|
char *types, *expires_str, *type;
|
|
@@ -287,122 +296,207 @@ static void set_expires_by_type(node_t *root) {
|
|
|
287
296
|
expires = atol(expires_str);
|
|
288
297
|
type = strtok(types, " ,");
|
|
289
298
|
while (type != NULL) {
|
|
290
|
-
set_expires_time(type, expires);
|
|
299
|
+
set_expires_time(s, type, expires);
|
|
291
300
|
type = strtok(NULL, " ,");
|
|
292
301
|
}
|
|
293
302
|
node = NODE_NEXT(node);
|
|
294
303
|
}
|
|
295
304
|
}
|
|
296
305
|
|
|
297
|
-
|
|
306
|
+
|
|
307
|
+
#ifdef W_ZLIB
|
|
308
|
+
|
|
309
|
+
/** Compress file */
|
|
310
|
+
/* Compress file if its size is >10kb and < 1mb and its mime-type has either
|
|
311
|
+
* text or xml */
|
|
312
|
+
|
|
313
|
+
int file_compress(http_t *h, static_file_t *ext){
|
|
314
|
+
LOG_FUNCTION
|
|
315
|
+
h->stat->encoding = scgi_header_value_get(h->req->scgi, "HTTP_ACCEPT_ENCODING");
|
|
316
|
+
h->stat->user_agent = scgi_header_value_get(h->req->scgi, "HTTP_USER_AGENT");
|
|
317
|
+
|
|
318
|
+
if(h->stat->buf.st_size >= Config->Worker.Compress.lower_limit
|
|
319
|
+
&& h->stat->buf.st_size <= Config->Worker.Compress.upper_limit
|
|
320
|
+
&& h->stat->encoding && strstr(h->stat->encoding,"deflate")){
|
|
321
|
+
|
|
322
|
+
#ifdef W_REGEX
|
|
323
|
+
if(h->stat->r_content_type){
|
|
324
|
+
if(regexec(h->stat->r_content_type, ext->mime_type, 0, NULL, 0) !=0 ) return FALSE;
|
|
325
|
+
}
|
|
326
|
+
|
|
327
|
+
if(h->stat->r_user_agent && h->stat->user_agent){
|
|
328
|
+
if(regexec(h->stat->r_user_agent, h->stat->user_agent, 0, NULL, 0) !=0 ) return FALSE;
|
|
329
|
+
}
|
|
330
|
+
#else
|
|
331
|
+
// Encode assets having Content-Type either 'text' or 'xml'.
|
|
332
|
+
if(strstr(ext->mime_type, "text") == NULL && strstr(ext->mime_type, "xml") == NULL
|
|
333
|
+
&& strstr(ext->mime_type, "css") == NULL && strstr(ext->mime_type, "javascript") == NULL){
|
|
334
|
+
return FALSE;
|
|
335
|
+
}
|
|
336
|
+
#endif
|
|
337
|
+
|
|
338
|
+
wr_u_int read;
|
|
339
|
+
FILE *file;
|
|
340
|
+
wr_buffer_create(h->stat->buffer, h->stat->buf.st_size);
|
|
341
|
+
file = fopen(h->stat->path, "r");
|
|
342
|
+
|
|
343
|
+
if(file == NULL) return FALSE;
|
|
344
|
+
|
|
345
|
+
while(h->stat->buffer->len < h->stat->buf.st_size){
|
|
346
|
+
read = fread(h->stat->buffer->str + h->stat->buffer->len, sizeof(char),
|
|
347
|
+
h->stat->buf.st_size - h->stat->buffer->len, file);
|
|
348
|
+
if(read < 0){
|
|
349
|
+
fclose(file);
|
|
350
|
+
wr_buffer_null(h->stat->buffer);
|
|
351
|
+
return FALSE;
|
|
352
|
+
}
|
|
353
|
+
h->stat->buffer->len += read;
|
|
354
|
+
}
|
|
355
|
+
|
|
356
|
+
fclose(file);
|
|
357
|
+
|
|
358
|
+
//zlib states that the source buffer must be at least 0.1 times larger than
|
|
359
|
+
//the source buffer plus 12 bytes to cope with the overhead of zlib data streams
|
|
360
|
+
wr_buffer_create(h->resp->resp_body, h->stat->buf.st_size + h->stat->buf.st_size*0.1 + 12);
|
|
361
|
+
h->resp->resp_body->len = h->resp->resp_body->size;
|
|
362
|
+
//now compress the data
|
|
363
|
+
if(compress2((Bytef*)h->resp->resp_body->str, (uLongf*)&h->resp->resp_body->len,
|
|
364
|
+
(const Bytef*)h->stat->buffer->str, (uLongf)h->stat->buffer->len, Z_DEFAULT_COMPRESSION) != Z_OK){
|
|
365
|
+
wr_buffer_null(h->stat->buffer);
|
|
366
|
+
wr_buffer_null(h->resp->resp_body);
|
|
367
|
+
return FALSE;
|
|
368
|
+
}
|
|
369
|
+
wr_buffer_null(h->stat->buffer);
|
|
370
|
+
|
|
371
|
+
return TRUE;
|
|
372
|
+
}
|
|
373
|
+
return FALSE;
|
|
374
|
+
}
|
|
375
|
+
|
|
376
|
+
#endif
|
|
377
|
+
|
|
378
|
+
void http_resp_200(http_t *h) {
|
|
298
379
|
LOG_FUNCTION
|
|
299
|
-
char str[
|
|
380
|
+
char str[STR_SIZE512], expire_date[STR_SIZE64] = "", current_date[STR_SIZE64] = "", modify_date[STR_SIZE64] = "";
|
|
300
381
|
int len;
|
|
382
|
+
int ret_val;
|
|
301
383
|
time_t t;
|
|
302
384
|
|
|
303
|
-
static_file_t *ext = get_mime_type(
|
|
385
|
+
static_file_t *ext = get_mime_type(h->stat);
|
|
304
386
|
LOG_DEBUG(DEBUG,"File extension = %s, mimetype = %s, expires = %d ", ext->ext, ext->mime_type, ext->expires);
|
|
305
387
|
const char *conn_header = scgi_header_value_get(h->req->scgi, HTTP_HEADER_CONNECTION);
|
|
306
388
|
|
|
307
|
-
t = get_time(current_date,
|
|
308
|
-
time_to_httpdate(buf
|
|
389
|
+
t = get_time(current_date, STR_SIZE64);
|
|
390
|
+
time_to_httpdate(h->stat->buf.st_mtime, modify_date, STR_SIZE64);
|
|
391
|
+
|
|
392
|
+
#ifdef W_ZLIB
|
|
393
|
+
ret_val = file_compress(h, ext);
|
|
394
|
+
if(ret_val == FALSE){
|
|
395
|
+
#endif
|
|
396
|
+
h->resp->resp_body->len = h->stat->buf.st_size;
|
|
397
|
+
#ifdef _POSIX_C_SOURCE
|
|
398
|
+
h->resp->file = open(h->stat->path, O_RDONLY);
|
|
399
|
+
#else
|
|
400
|
+
h->resp->file = fopen(h->stat->path, "r");
|
|
401
|
+
#endif
|
|
402
|
+
#ifdef W_ZLIB
|
|
403
|
+
}
|
|
404
|
+
#endif
|
|
309
405
|
|
|
310
406
|
if (ext->expires > 0) {
|
|
311
407
|
t += ext->expires;
|
|
312
|
-
time_to_httpdate(t, expire_date,
|
|
313
|
-
len = sprintf(str, "HTTP/1.1 200 OK\r\nDate: %s\r\nServer: %s-%s\r\nLast-Modified: %s\r\nExpires: %s\r\
|
|
314
|
-
current_date,
|
|
315
|
-
(conn_header ? conn_header : CONNECTION_CLOSE),
|
|
408
|
+
time_to_httpdate(t, expire_date, STR_SIZE64);
|
|
409
|
+
len = sprintf(str, "HTTP/1.1 200 OK\r\nDate: %s\r\nServer: %s-%s\r\nLast-Modified: %s\r\nExpires: %s\r\nConnection: %s\r\n%sContent-Type: %s\r\nContent-Length: %d\r\n\r\n",
|
|
410
|
+
current_date, Config->Worker.Server.name.str, Config->Worker.Server.version.str, modify_date, expire_date,
|
|
411
|
+
(conn_header ? conn_header : CONNECTION_CLOSE),
|
|
412
|
+
(ret_val == TRUE ? "Content-Encoding: deflate\r\n" : ""),
|
|
413
|
+
ext->mime_type, h->resp->resp_body->len);
|
|
316
414
|
}else {
|
|
317
|
-
len = sprintf(str, "HTTP/1.1 200 OK\r\nDate: %s\r\nServer: %s-%s\r\nLast-Modified: %s\r\
|
|
318
|
-
current_date,
|
|
319
|
-
(conn_header ? conn_header : CONNECTION_CLOSE),
|
|
415
|
+
len = sprintf(str, "HTTP/1.1 200 OK\r\nDate: %s\r\nServer: %s-%s\r\nLast-Modified: %s\r\nConnection: %s\r\n%sContent-Type: %s\r\nContent-Length: %d\r\n\r\n",
|
|
416
|
+
current_date, Config->Worker.Server.name.str, Config->Worker.Server.version.str, modify_date,
|
|
417
|
+
(conn_header ? conn_header : CONNECTION_CLOSE),
|
|
418
|
+
(ret_val == TRUE ? "Content-Encoding: deflate\r\n" : ""),
|
|
419
|
+
ext->mime_type, h->resp->resp_body->len);
|
|
320
420
|
}
|
|
321
421
|
|
|
322
422
|
wr_string_new(h->resp->header, str, len);
|
|
323
|
-
h->resp->resp_body->len = buf->st_size;
|
|
324
423
|
h->resp->resp_code = http_status[HTTP_STATUS_200].code;
|
|
325
|
-
#ifdef _POSIX_C_SOURCE
|
|
326
|
-
h->resp->file = open(path, O_RDONLY);
|
|
327
|
-
#else
|
|
328
|
-
h->resp->file = fopen(path, "r");
|
|
329
|
-
#endif
|
|
330
424
|
}
|
|
331
425
|
|
|
332
|
-
void http_resp_304(http_t *h
|
|
426
|
+
void http_resp_304(http_t *h) {
|
|
333
427
|
LOG_FUNCTION
|
|
334
|
-
char str[
|
|
428
|
+
char str[STR_SIZE512], expire_date[STR_SIZE64] = "", current_date[STR_SIZE64] = "";
|
|
335
429
|
int len;
|
|
336
430
|
time_t t;
|
|
337
|
-
static_file_t *ext = get_mime_type(
|
|
431
|
+
static_file_t *ext = get_mime_type(h->stat);
|
|
338
432
|
LOG_DEBUG(DEBUG,"File extension = %s, mimetype = %s, expires = %d ", ext->ext, ext->mime_type, ext->expires);
|
|
339
433
|
const char *conn_header = scgi_header_value_get(h->req->scgi, HTTP_HEADER_CONNECTION);
|
|
340
434
|
|
|
341
|
-
t = get_time(current_date,
|
|
435
|
+
t = get_time(current_date, STR_SIZE64);
|
|
342
436
|
if (ext->expires > 0) {
|
|
343
437
|
t = t + ext->expires;
|
|
344
|
-
time_to_httpdate(t, expire_date,
|
|
345
|
-
len = sprintf(str, "HTTP/1.1 304 Not Modified\r\nDate: %s\r\nServer: %s-%s\r\nExpires: %s\r\
|
|
346
|
-
current_date,
|
|
438
|
+
time_to_httpdate(t, expire_date, STR_SIZE64);
|
|
439
|
+
len = sprintf(str, "HTTP/1.1 304 Not Modified\r\nDate: %s\r\nServer: %s-%s\r\nExpires: %s\r\nConnection: %s\r\n\r\n",
|
|
440
|
+
current_date, Config->Worker.Server.name.str, Config->Worker.Server.version.str, expire_date,
|
|
347
441
|
(conn_header ? conn_header : CONNECTION_CLOSE));
|
|
348
442
|
}else {
|
|
349
|
-
len = sprintf(str, "HTTP/1.1 304 Not Modified\r\nDate: %s\r\nServer: %s-%s\r\
|
|
350
|
-
current_date,
|
|
443
|
+
len = sprintf(str, "HTTP/1.1 304 Not Modified\r\nDate: %s\r\nServer: %s-%s\r\nConnection: %s\r\n\r\n",
|
|
444
|
+
current_date, Config->Worker.Server.name.str, Config->Worker.Server.version.str, (conn_header ? conn_header : CONNECTION_CLOSE));
|
|
351
445
|
}
|
|
352
446
|
|
|
353
447
|
wr_string_new(h->resp->header, str, len);
|
|
354
448
|
h->resp->resp_code = http_status[HTTP_STATUS_304].code;
|
|
355
449
|
}
|
|
356
450
|
|
|
357
|
-
void http_resp_403(http_t *h
|
|
451
|
+
void http_resp_403(http_t *h) {
|
|
358
452
|
LOG_FUNCTION
|
|
359
|
-
char str[
|
|
453
|
+
char str[STR_SIZE512], current_date[STR_SIZE64];
|
|
360
454
|
const char *conn_header = scgi_header_value_get(h->req->scgi, HTTP_HEADER_CONNECTION);
|
|
361
455
|
int len;
|
|
362
456
|
|
|
363
|
-
get_time(current_date,
|
|
457
|
+
get_time(current_date, STR_SIZE64);
|
|
364
458
|
|
|
365
459
|
len = sprintf(str, HTTP_RESP_ERR_BODY,
|
|
366
460
|
http_status[HTTP_STATUS_403].phrase, http_status[HTTP_STATUS_403].phrase + 4,
|
|
367
|
-
http_status[HTTP_STATUS_403].message,
|
|
461
|
+
http_status[HTTP_STATUS_403].message, Config->Worker.Server.name.str, Config->Worker.Server.version.str);
|
|
368
462
|
wr_buffer_create(h->resp->resp_body, len);
|
|
369
463
|
wr_buffer_add(h->resp->resp_body, str, len);
|
|
370
464
|
|
|
371
465
|
len = sprintf(str, HTTP_RESP_ERR_HEADERS,
|
|
372
|
-
current_date, http_status[HTTP_STATUS_403].phrase,
|
|
466
|
+
current_date, http_status[HTTP_STATUS_403].phrase, Config->Worker.Server.name.str, Config->Worker.Server.version.str,
|
|
373
467
|
(conn_header ? conn_header : CONNECTION_CLOSE), len);
|
|
374
468
|
wr_string_new(h->resp->header, str, len);
|
|
375
469
|
h->resp->resp_code = http_status[HTTP_STATUS_403].code;
|
|
376
470
|
}
|
|
377
471
|
|
|
378
|
-
void http_resp_404(http_t *h
|
|
472
|
+
void http_resp_404(http_t *h) {
|
|
379
473
|
LOG_FUNCTION
|
|
380
|
-
char str[
|
|
474
|
+
char str[STR_SIZE512], current_date[STR_SIZE64];
|
|
381
475
|
const char *conn_header = scgi_header_value_get(h->req->scgi, HTTP_HEADER_CONNECTION);
|
|
382
476
|
int len;
|
|
383
477
|
|
|
384
|
-
get_time(current_date,
|
|
478
|
+
get_time(current_date, STR_SIZE64);
|
|
385
479
|
|
|
386
480
|
len = sprintf(str, HTTP_RESP_ERR_BODY,
|
|
387
481
|
http_status[HTTP_STATUS_404].phrase, http_status[HTTP_STATUS_404].phrase + 4,
|
|
388
|
-
http_status[HTTP_STATUS_404].message,
|
|
482
|
+
http_status[HTTP_STATUS_404].message, Config->Worker.Server.name.str, Config->Worker.Server.version.str);
|
|
389
483
|
wr_buffer_create(h->resp->resp_body, len);
|
|
390
484
|
wr_buffer_add(h->resp->resp_body, str, len);
|
|
391
485
|
|
|
392
486
|
len = sprintf(str, HTTP_RESP_ERR_HEADERS,
|
|
393
|
-
current_date, http_status[HTTP_STATUS_404].phrase,
|
|
487
|
+
current_date, http_status[HTTP_STATUS_404].phrase, Config->Worker.Server.name.str, Config->Worker.Server.version.str,
|
|
394
488
|
(conn_header ? conn_header : CONNECTION_CLOSE), len);
|
|
395
489
|
wr_string_new(h->resp->header, str, len);
|
|
396
490
|
h->resp->resp_code = http_status[HTTP_STATUS_404].code;
|
|
397
491
|
}
|
|
398
492
|
|
|
399
|
-
void send_static_worker_pid(
|
|
493
|
+
void send_static_worker_pid() {
|
|
400
494
|
LOG_FUNCTION
|
|
401
495
|
node_t *root = NULL;
|
|
402
|
-
|
|
496
|
+
|
|
403
497
|
// Read pid queue related configuration
|
|
404
|
-
|
|
405
|
-
root = yaml_parse(
|
|
498
|
+
|
|
499
|
+
root = yaml_parse(Config->Worker.File.internal_config.str);
|
|
406
500
|
if(root == NULL) {
|
|
407
501
|
LOG_ERROR(SEVERE, "Could not parse server_internal_config.yml file. PID can not be sent to analyzer");
|
|
408
502
|
return;
|
|
@@ -410,7 +504,7 @@ void send_static_worker_pid(char *root_path) {
|
|
|
410
504
|
char *host = NULL, *port = NULL, *queue_name = NULL;
|
|
411
505
|
wr_msg_queue_server_t *msg_queue_server = NULL;
|
|
412
506
|
wr_msg_queue_conn_t *msg_queue_conn = NULL;
|
|
413
|
-
char msg_value[
|
|
507
|
+
char msg_value[STR_SIZE32];
|
|
414
508
|
int rv;
|
|
415
509
|
|
|
416
510
|
host = get_node_value(root, WR_MSG_QUEUE_SERVER_HOST);
|
|
@@ -435,7 +529,7 @@ void send_static_worker_pid(char *root_path) {
|
|
|
435
529
|
LOG_ERROR(WARN, "Error establising connection with message queue server");
|
|
436
530
|
goto err;
|
|
437
531
|
}
|
|
438
|
-
rv = sprintf(msg_value, "%s:%d",
|
|
532
|
+
rv = sprintf(msg_value, "%s:%d", Config->Worker.static_server.str, getpid());
|
|
439
533
|
rv = wr_msg_queue_set(msg_queue_conn, queue_name, msg_value, rv);
|
|
440
534
|
if (rv < 0) {
|
|
441
535
|
LOG_ERROR(SEVERE, "Failed to send PID to message queue");
|
|
@@ -450,47 +544,41 @@ err:
|
|
|
450
544
|
}
|
|
451
545
|
}
|
|
452
546
|
|
|
453
|
-
/**************************************
|
|
454
|
-
* Public Functions
|
|
455
|
-
*************************************/
|
|
456
547
|
|
|
457
548
|
/* Initialize extension and mime-type map */
|
|
458
|
-
int static_module_init(
|
|
549
|
+
int static_module_init(static_server_t *s) {
|
|
459
550
|
LOG_FUNCTION
|
|
460
551
|
node_t *root;
|
|
461
|
-
char file_name[100];
|
|
462
552
|
long int expires;
|
|
463
|
-
|
|
464
|
-
|
|
465
|
-
root = yaml_parse(file_name);
|
|
553
|
+
|
|
554
|
+
root = yaml_parse(Config->Worker.File.config.str);
|
|
466
555
|
if (root == NULL) {
|
|
467
556
|
LOG_ERROR(SEVERE, "Could not read config.yml file");
|
|
468
|
-
return
|
|
557
|
+
return FALSE;
|
|
469
558
|
}
|
|
470
559
|
expires = get_default_expires(root);
|
|
471
|
-
|
|
472
|
-
|
|
473
|
-
if (create_dictionary(file_name, expires) != 0) {
|
|
560
|
+
|
|
561
|
+
if (create_dictionary(s, Config->Worker.File.mime_type.str, expires) != 0) {
|
|
474
562
|
node_free(root);
|
|
475
|
-
return
|
|
563
|
+
return FALSE;
|
|
476
564
|
}
|
|
477
565
|
|
|
478
|
-
set_expires_by_type(root);
|
|
566
|
+
set_expires_by_type(s, root);
|
|
479
567
|
|
|
480
568
|
node_free(root);
|
|
481
569
|
|
|
482
|
-
send_static_worker_pid(
|
|
483
|
-
return
|
|
570
|
+
send_static_worker_pid();
|
|
571
|
+
return TRUE;
|
|
484
572
|
}
|
|
485
573
|
|
|
486
574
|
/* Free extension and mime-type map */
|
|
487
|
-
void static_module_free() {
|
|
575
|
+
void static_module_free(static_server_t *s) {
|
|
488
576
|
LOG_FUNCTION
|
|
489
577
|
int i;
|
|
490
578
|
static_file_t *ext, *next_ext;
|
|
491
579
|
|
|
492
580
|
for (i = 0; i <= MAP_SIZE; i++) {
|
|
493
|
-
ext = map[i];
|
|
581
|
+
ext = s->map[i];
|
|
494
582
|
while (ext) {
|
|
495
583
|
next_ext = ext->next;
|
|
496
584
|
free(ext);
|
|
@@ -499,17 +587,116 @@ void static_module_free() {
|
|
|
499
587
|
}
|
|
500
588
|
}
|
|
501
589
|
|
|
590
|
+
/**************************************
|
|
591
|
+
* Public Functions
|
|
592
|
+
*************************************/
|
|
593
|
+
|
|
594
|
+
/** Create new static server */
|
|
595
|
+
static_server_t * static_server_new(void* ptr){
|
|
596
|
+
LOG_FUNCTION
|
|
597
|
+
|
|
598
|
+
wkr_t* w = (wkr_t*)ptr;
|
|
599
|
+
|
|
600
|
+
static_server_t *s = wr_malloc(static_server_t);
|
|
601
|
+
if(s == NULL) return NULL;
|
|
602
|
+
|
|
603
|
+
#ifdef W_ZLIB
|
|
604
|
+
if(w->tmp->lower_limit > 0)
|
|
605
|
+
Config->Worker.Compress.lower_limit = w->tmp->lower_limit;
|
|
606
|
+
|
|
607
|
+
if(w->tmp->upper_limit > 0)
|
|
608
|
+
Config->Worker.Compress.upper_limit = w->tmp->upper_limit;
|
|
609
|
+
|
|
610
|
+
#ifdef W_REGEX
|
|
611
|
+
s->r_content_type = NULL;
|
|
612
|
+
if(!wr_string_is_empty(w->tmp->r_content_type)){
|
|
613
|
+
int err_no;
|
|
614
|
+
s->r_content_type = wr_malloc(regex_t);
|
|
615
|
+
// #define REG_EXTENDED 1
|
|
616
|
+
if((err_no = regcomp(s->r_content_type, w->tmp->r_content_type.str, 1))!=0){ /* Compile the regex */
|
|
617
|
+
size_t length;
|
|
618
|
+
char *buffer;
|
|
619
|
+
length = regerror (err_no, s->r_content_type, NULL, 0);
|
|
620
|
+
buffer = malloc(length);
|
|
621
|
+
regerror (err_no, s->r_content_type, buffer, length);
|
|
622
|
+
LOG_ERROR(SEVERE, "%s", buffer); /* Print the error */
|
|
623
|
+
LOG_ERROR(SEVERE, "Now Static Workers allow encoding for only 'text' and 'xml' Content-Type.");
|
|
624
|
+
free(buffer);
|
|
625
|
+
regfree(s->r_content_type);
|
|
626
|
+
if((err_no = regcomp(s->r_content_type, "text|xml", 1))!=0){
|
|
627
|
+
regfree(s->r_content_type);
|
|
628
|
+
free(s->r_content_type);
|
|
629
|
+
s->r_content_type = NULL;
|
|
630
|
+
}
|
|
631
|
+
}
|
|
632
|
+
}
|
|
633
|
+
|
|
634
|
+
s->r_user_agent = NULL;
|
|
635
|
+
// Do not apply validation on User-Agent if it is not given or it is '.*'(allow all).
|
|
636
|
+
if(!wr_string_is_empty(w->tmp->r_user_agent) && strcmp(w->tmp->r_user_agent.str,".*") != 0){
|
|
637
|
+
int err_no;
|
|
638
|
+
s->r_user_agent = wr_malloc(regex_t);
|
|
639
|
+
if((err_no = regcomp(s->r_user_agent, w->tmp->r_content_type.str, 1))!=0){ /* Compile the regex */
|
|
640
|
+
size_t length;
|
|
641
|
+
char *buffer;
|
|
642
|
+
length = regerror (err_no, s->r_user_agent, NULL, 0);
|
|
643
|
+
buffer = malloc(length);
|
|
644
|
+
regerror (err_no, s->r_user_agent, buffer, length);
|
|
645
|
+
LOG_ERROR(SEVERE, "%s", buffer); /* Print the error */
|
|
646
|
+
LOG_ERROR(SEVERE, "Now Static Workers serves encoded assets to all User-Agent.");
|
|
647
|
+
free(buffer);
|
|
648
|
+
regfree(s->r_user_agent);
|
|
649
|
+
free(s->r_user_agent);
|
|
650
|
+
s->r_user_agent = NULL;
|
|
651
|
+
}
|
|
652
|
+
}
|
|
653
|
+
#endif
|
|
654
|
+
|
|
655
|
+
#endif
|
|
656
|
+
|
|
657
|
+
if(static_module_init(s) == FALSE){
|
|
658
|
+
free(s);
|
|
659
|
+
return NULL;
|
|
660
|
+
}
|
|
661
|
+
wr_buffer_new(s->buffer);
|
|
662
|
+
|
|
663
|
+
return s;
|
|
664
|
+
}
|
|
665
|
+
|
|
666
|
+
/** Delete static server */
|
|
667
|
+
void static_server_free(static_server_t *s){
|
|
668
|
+
if(s){
|
|
669
|
+
if(s->buffer) wr_buffer_free(s->buffer);
|
|
670
|
+
static_module_free(s);
|
|
671
|
+
|
|
672
|
+
#if defined(W_ZLIB) && defined(W_REGEX)
|
|
673
|
+
if(s->r_user_agent){
|
|
674
|
+
regfree(s->r_user_agent);
|
|
675
|
+
free(s->r_user_agent);
|
|
676
|
+
}
|
|
677
|
+
if(s->r_content_type){
|
|
678
|
+
regfree(s->r_content_type);
|
|
679
|
+
free(s->r_content_type);
|
|
680
|
+
}
|
|
681
|
+
#endif
|
|
682
|
+
|
|
683
|
+
free(s);
|
|
684
|
+
}
|
|
685
|
+
}
|
|
686
|
+
|
|
502
687
|
/* Serve static file content */
|
|
503
|
-
void static_file_process(
|
|
688
|
+
void static_file_process(void *http) {
|
|
504
689
|
LOG_FUNCTION
|
|
690
|
+
http_t *h = (http_t*) http;
|
|
505
691
|
wkr_t *w = h->wkr;
|
|
506
692
|
short resp_code;
|
|
507
|
-
|
|
508
|
-
|
|
509
|
-
|
|
510
|
-
|
|
511
|
-
|
|
512
|
-
|
|
693
|
+
|
|
694
|
+
h->stat->path = scgi_header_value_get(h->req->scgi, Config->Worker.Header.file_path.str);
|
|
695
|
+
h->stat->modify = scgi_header_value_get(h->req->scgi, HTTP_HEADER_IF_MODIFIED_SINCE);
|
|
696
|
+
|
|
697
|
+
LOG_DEBUG(DEBUG, "Path = %s", h->stat->path);
|
|
698
|
+
resp_code = get_resp_code(h->stat);
|
|
699
|
+
http_status[resp_code].fun(h);
|
|
513
700
|
http_req_set(h->req);
|
|
514
701
|
http_resp_process(h->resp);
|
|
515
702
|
|