test-http-payload.c revision 38af46387e565053adf6c47f7f6871676d685de8
bcb4e51a409d94ae670de96afb8483a4f7855294Stephan Bosch/* Copyright (c) 2013-2017 Dovecot authors, see the included COPYING file */
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainenstatic enum payload_handling server_payload_handling =
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainenstatic unsigned int client_ioloop_nesting = 0;
091a2dea9d89734a7c1225eed511b3851693a757Timo Sirainenstatic unsigned ioloop_nested_first = 0;
091a2dea9d89734a7c1225eed511b3851693a757Timo Sirainenstatic unsigned ioloop_nested_last = 0;
091a2dea9d89734a7c1225eed511b3851693a757Timo Sirainenstatic unsigned ioloop_nested_depth = 0;
091a2dea9d89734a7c1225eed511b3851693a757Timo Sirainenstatic void test_files_read_dir(const char *path)
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen /* open the directory */
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen /* read entries */
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen /* Close the directory */
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainenstatic void test_files_init(void)
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen /* initialize file array */
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen /* obtain all filenames */
a5b64f1abb1cb0a9718d5bf7f0ae808072237259Timo Sirainenstatic void test_files_deinit(void)
c85f67cfb8e1cef2de2b681debf4703d5818dc01Stephan Boschstatic struct istream *
c85f67cfb8e1cef2de2b681debf4703d5818dc01Stephan Bosch unsigned int *status_r, const char **reason_r)
fa33df8230c2f27ae863ff83d4251923428d53c7Aki Tuomi * Test server
ed567dac7e55ab3e8dd53d9c86c31ebb2032d4dfTimo Sirainenstatic const struct http_server_callbacks http_callbacks;
ed567dac7e55ab3e8dd53d9c86c31ebb2032d4dfTimo Sirainen/* location: /succes */
7db7fbea5d8a07463b625f93d69166d56018dadfTimo Sirainenclient_handle_success_request(struct client_request *creq)
7db7fbea5d8a07463b625f93d69166d56018dadfTimo Sirainen struct http_server_request *req = creq->server_req;
7db7fbea5d8a07463b625f93d69166d56018dadfTimo Sirainen resp = http_server_response_create(req, 200, "OK");
4b9e7a8752803928aa0897f8cc1fc34592452f07Stephan Bosch/* location: /download/... */
4b9e7a8752803928aa0897f8cc1fc34592452f07Stephan Bosch struct http_server_request *req = creq->server_req;
4b9e7a8752803928aa0897f8cc1fc34592452f07Stephan Bosch unsigned int status;
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen fstream = test_file_open(fpath, &status, &reason);
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen http_server_request_fail(req, status, reason);
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen resp = http_server_response_create(req, 200, "OK");
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen http_server_response_add_header(resp, "Content-Type", "text/plain");
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen output = http_server_response_get_payload_output(resp, TRUE);
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen if (o_stream_send_istream(output, fstream) != OSTREAM_SEND_ISTREAM_RESULT_FINISHED) {
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen "failed to send blocking file payload");
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen "finished sending blocking payload for %s"
67e0afe62b26d222614b8d817155bf5c74bd7fe0Stephan Bosch/* location: /echo */
4b9e7a8752803928aa0897f8cc1fc34592452f07Stephan Boschclient_request_finish_payload_in(struct client_request *creq)
67e0afe62b26d222614b8d817155bf5c74bd7fe0Stephan Bosch payload_input = iostream_temp_finish(&creq->payload_output, 4096);
67e0afe62b26d222614b8d817155bf5c74bd7fe0Stephan Bosch http_server_response_add_header(resp, "Content-Type", "text/plain");
67e0afe62b26d222614b8d817155bf5c74bd7fe0Stephan Bosch http_server_response_set_payload(resp, payload_input);
67e0afe62b26d222614b8d817155bf5c74bd7fe0Stephan Boschclient_request_read_echo(struct client_request *creq)
67e0afe62b26d222614b8d817155bf5c74bd7fe0Stephan Bosch o_stream_set_max_buffer_size(creq->payload_output, IO_BLOCK_SIZE);
67e0afe62b26d222614b8d817155bf5c74bd7fe0Stephan Bosch res = o_stream_send_istream(creq->payload_output, creq->payload_input);
c85f67cfb8e1cef2de2b681debf4703d5818dc01Stephan Bosch o_stream_set_max_buffer_size(creq->payload_output, (size_t)-1);
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen "Failed to read all echo payload [%s]", creq->path);
7db7fbea5d8a07463b625f93d69166d56018dadfTimo Sirainen case OSTREAM_SEND_ISTREAM_RESULT_ERROR_OUTPUT:
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen "Failed to write all echo payload [%s]", creq->path);
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainenclient_request_read_echo_more(struct client_request *creq)
2c5c70e12365d7910848259f88eb237ce3a15947Timo Sirainen "finished receiving payload for %s", creq->path);
086b73efd1a5812a64acc951366a499d325509a6Stephan Boschclient_handle_echo_request(struct client_request *creq,
086b73efd1a5812a64acc951366a499d325509a6Stephan Bosch struct http_server_request *req = creq->server_req;
9a84b90d894a741ae6e090de104d31382a41d0aaJosef 'Jeff' Sipek (void)http_request_get_payload_size(hreq, &size);
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen http_server_response_add_header(resp, "Content-Type", "text/plain");
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen http_server_request_get_payload_input(req, TRUE);
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen i_stream_create_limit(payload_input, read_server_partial);
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen if (o_stream_send_istream(payload_output, payload_input) != OSTREAM_SEND_ISTREAM_RESULT_FINISHED) {
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen "failed to receive blocking echo payload");
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen payload_input = iostream_temp_finish(&payload_output, 4096);
48325adac125d7ff275ec69b05b7a92be9637630Timo Sirainen "finished receiving blocking payload for %s", path);
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen resp = http_server_response_create(req, 200, "OK");
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen http_server_response_add_header(resp, "Content-Type", "text/plain");
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen payload_output = http_server_response_get_payload_output(resp, TRUE);
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen if (o_stream_send_istream(payload_output, payload_input) != OSTREAM_SEND_ISTREAM_RESULT_FINISHED) {
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen "failed to send blocking echo payload");
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen "finished sending blocking payload for %s", path);
c61779cfa45c1684b1f7c462011088bad0b8318cTimo Sirainen http_server_request_get_payload_input(req, FALSE);
c61779cfa45c1684b1f7c462011088bad0b8318cTimo Sirainen i_stream_create_limit(creq->payload_input, read_server_partial);
c61779cfa45c1684b1f7c462011088bad0b8318cTimo Sirainen creq->io = io_add_istream(creq->payload_input,
d951320d498ae0800b677b754dde71574102123bTimo Sirainen http_server_request_get_payload_input(req, FALSE);
ddaf416216a83e71bc1bfc1b6faf2ead9d774613Stephan Boschhttp_server_request_destroyed(struct client_request *creq);
ddaf416216a83e71bc1bfc1b6faf2ead9d774613Stephan Bosch pool_t pool = http_server_request_get_pool(req);
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainenstatic void client_request_deinit(struct client_request **_creq)
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen struct http_server_request *req = creq->server_req;
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainenhttp_server_request_destroyed(struct client_request *creq)
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen const char *path = hreq->target.url->path, *p;
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen struct client *client = (struct client *)context;
96f89d51e8315f644f46804a9f0fc4f685ac48bfTimo Sirainen "request method=`%s' path=`%s'", hreq->method, path);
int fd;
static void test_server_deinit(void)
struct test_client_request {
unsigned int files_idx;
static struct test_client_request *
test_client_request_new(void)
return tcreq;
static void test_client_download_continue(void);
const char **paths;
unsigned int count;
if (debug) {
if (ret == 0) {
if (debug) {
fsize = 0;
} else if (debug) {
const char **paths;
const char *path;
const char *reason;
if (debug) {
if (debug) {
if (debug) {
if (debug) {
if (read_client_partial == 0) {
static void test_client_download_continue(void)
const char *const *paths;
unsigned int count;
if (debug) {
client_files_last++) {
if (debug) {
static void test_client_echo_continue(void);
const char **paths;
unsigned int count;
if (debug) {
if (ret == 0) {
if (debug) {
fsize = 0;
} else if (debug) {
const char **paths;
const char *path;
if (debug) {
if (debug) {
if (read_server_partial > 0) {
if (debug) {
static void test_client_echo_continue(void)
const char **paths;
if (debug) {
client_files_last++) {
if (debug) {
if (debug) {
if (debug) {
if (i == ioloop_nested_last)
} else if (client_ioloop_nesting > 0 &&
if (debug) {
if (debug) {
static void test_client_deinit(void)
static void test_open_server_fd(void)
static void test_server_kill(void)
static void test_run_client_server(
if (server_pid == 0) {
hostpid_init();
if (debug)
ioloop_nested_depth = 0;
if (debug)
ioloop_nested_depth = 0;
static void test_run_sequential(
static void test_run_pipeline(
static void test_run_parallel(
static void test_download_server_nonblocking(void)
read_server_partial = 0;
test_end();
static void test_download_server_blocking(void)
read_server_partial = 0;
test_end();
static void test_echo_server_nonblocking(void)
read_server_partial = 0;
test_end();
read_server_partial = 0;
test_end();
read_server_partial = 0;
test_end();
static void test_echo_server_blocking(void)
read_server_partial = 0;
test_end();
static void test_echo_server_nonblocking_sync(void)
read_server_partial = 0;
test_end();
read_server_partial = 0;
test_end();
read_server_partial = 0;
test_end();
static void test_echo_server_blocking_sync(void)
read_server_partial = 0;
test_end();
static void test_echo_server_nonblocking_partial(void)
test_end();
test_end();
test_end();
test_end();
test_end();
test_end();
static void test_echo_server_blocking_partial(void)
test_end();
test_end();
static void test_download_client_partial(void)
read_server_partial = 0;
test_end();
read_server_partial = 0;
test_end();
static void test_download_client_nested_ioloop(void)
read_server_partial = 0;
read_client_partial = 0;
test_end();
static void (*const test_functions[])(void) = {
if (terminating != 0)
static void test_atexit(void)