static nxweb_result download_on_request(nxweb_http_server_connection* conn, nxweb_http_request* req, nxweb_http_response* resp) { nxweb_parse_request_parameters( req, 0 ); const char *name_space = nx_simple_map_get_nocase( req->parameters, "namespace" ); char * url = malloc(strlen(req->path_info)+1); if (!url) {return NXWEB_ERROR;} strcpy(url, req->path_info); url[strlen(req->path_info)] = '\0'; nxweb_url_decode( url, 0 ); char *fname = url, *temp; while (temp = strstr(fname, "/")) {fname = temp + 1;} char *strip_args = strstr(fname, "?"); int fname_len = strip_args ? (strip_args - fname) : strlen(fname); char fname_with_space[1024] = {0}; if ( strlen(url) > sizeof(fname_with_space)-1 ) { char err_msg[1024] = {0}; snprintf( err_msg, sizeof(err_msg)-1, "<html><body>File not found<br/>namespace:%s<br/>filename:%.*s</body></html>", name_space, fname_len, fname ); nxweb_send_http_error(resp, 404, err_msg); resp->keep_alive=0; free(url); return NXWEB_MISS; } if( name_space ) {sprintf( fname_with_space, "%s:/", name_space);} else {strcpy( fname_with_space, ":/" );} strncat( fname_with_space, fname, fname_len ); size_t file_size = 0; char *pfile_data = kcdbget( g_kcdb, fname_with_space, strlen(fname_with_space), &file_size ); if ( pfile_data == NULL ) { char err_msg[1024] = {0}; snprintf( err_msg, sizeof(err_msg)-1, "<html><body>File not found<br/>namespace:%s<br/>filename:%.*s</body></html>", name_space, fname_len, fname ); nxweb_send_http_error(resp, 404, err_msg); resp->keep_alive=0; free(url); return NXWEB_MISS; } KC_DATA *ptmp = nxb_alloc_obj(req->nxb, sizeof(KC_DATA)); nxweb_set_request_data(req, UPLOAD_HANDLER_KEY, (nxe_data)(void *)ptmp, upload_request_data_finalize); ptmp->data_ptr = pfile_data; nxweb_send_data( resp, pfile_data + RECORD_HEADER_LEN, file_size - RECORD_HEADER_LEN, "application/octet-stream" ); free(url); return NXWEB_OK; }
static nxweb_result ssi_do_filter(nxweb_filter* filter, nxweb_http_server_connection* conn, nxweb_http_request* req, nxweb_http_response* resp, nxweb_filter_data* fdata) { ssi_filter_data* sfdata=(ssi_filter_data*)fdata; if (resp->status_code && resp->status_code!=200 && resp->status_code!=404) return NXWEB_OK; if (!resp->content_length) return NXWEB_OK; if (resp->gzip_encoded) { fdata->bypass=1; return NXWEB_NEXT; } if (!resp->ssi_on) { if (!resp->mtype && resp->content_type) { resp->mtype=nxweb_get_mime_type(resp->content_type); } if (!resp->mtype || !resp->mtype->ssi_on) { fdata->bypass=1; return NXWEB_NEXT; } } nxd_http_server_proto_setup_content_out(&conn->hsp, resp); // attach content_out to ssi_buffer ssi_buffer_init(&sfdata->ssib, conn, req); if (resp->content_length>0) ssi_buffer_make_room(&sfdata->ssib, min(MAX_SSI_SIZE, resp->content_length)); nxe_connect_streams(conn->tdata->loop, resp->content_out, &sfdata->ssib.data_in); nxweb_set_request_data(req, SSIB_REQ_KEY, (nxe_data)(void*)&sfdata->ssib, 0); // will be used for variable lookups in parent requests // replace content_out with composite stream nxweb_composite_stream* cs=nxweb_composite_stream_init(conn, req); nxweb_composite_stream_start(cs, resp); // reset previous response content resp->content=0; resp->sendfile_path=0; if (resp->sendfile_fd) { // save it to close on finalize sfdata->input_fd=resp->sendfile_fd; resp->sendfile_fd=0; } resp->last_modified=0; sfdata->ssib.cs=cs; return NXWEB_OK; }
static nxweb_result python_on_post_data(nxweb_http_server_connection* conn, nxweb_http_request* req, nxweb_http_response* resp) { if (req->content_length>0 && req->content_length<NXWEB_MAX_REQUEST_BODY_SIZE) { // fallback to default in-memory buffering return NXWEB_NEXT; } if (!conn->handler->dir) { nxweb_log_warning("python handler temp upload file dir not set => skipping file buffering for %s", req->uri); return NXWEB_NEXT; } nxe_ssize_t upload_size_limit=conn->handler->size? conn->handler->size : NXWEB_MAX_PYTHON_UPLOAD_SIZE; if (req->content_length > upload_size_limit) { nxweb_send_http_error(resp, 413, "Request Entity Too Large"); resp->keep_alive=0; // close connection nxweb_start_sending_response(conn, resp); return NXWEB_OK; } char* fname_template=nxb_alloc_obj(req->nxb, strlen(conn->handler->dir)+sizeof("/py_upload_tmp_XXXXXX")+1); strcat(strcpy(fname_template, conn->handler->dir), "/py_upload_tmp_XXXXXX"); if (nxweb_mkpath(fname_template, 0755)==-1) { nxweb_log_error("can't create path to temp upload file %s; check permissions", fname_template); nxweb_send_http_error(resp, 500, "Internal Server Error"); resp->keep_alive=0; // close connection nxweb_start_sending_response(conn, resp); return NXWEB_OK; } int fd=mkstemp(fname_template); if (fd==-1) { nxweb_log_error("can't open (mkstemp()) temp upload file for %s", req->uri); nxweb_send_http_error(resp, 500, "Internal Server Error"); resp->keep_alive=0; // close connection nxweb_start_sending_response(conn, resp); return NXWEB_OK; } unlink(fname_template); // auto-delete on close() nxd_fwbuffer* fwb=nxb_alloc_obj(req->nxb, sizeof(nxd_fwbuffer)); nxweb_set_request_data(req, PYTHON_HANDLER_KEY, (nxe_data)(void*)fwb, python_request_data_finalize); nxd_fwbuffer_init(fwb, fd, upload_size_limit); conn->hsp.cls->connect_request_body_out(&conn->hsp, &fwb->data_in); conn->hsp.cls->start_receiving_request_body(&conn->hsp); return NXWEB_OK; }