1 #ifndef AWS_HTTP_REQUEST_RESPONSE_H
2 #define AWS_HTTP_REQUEST_RESPONSE_H
3 
4 /**
5  * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
6  * SPDX-License-Identifier: Apache-2.0.
7  */
8 
9 #include <aws/http/http.h>
10 
11 struct aws_http_connection;
12 struct aws_input_stream;
13 
14 /**
15  * A stream exists for the duration of a request/response exchange.
16  * A client creates a stream to send a request and receive a response.
17  * A server creates a stream to receive a request and send a response.
18  * In http/2, a push-promise stream can be sent by a server and received by a client.
19  */
20 struct aws_http_stream;
21 
22 /**
23  * Controls whether a header's strings may be compressed by encoding the index of
24  * strings in a cache, rather than encoding the literal string.
25  *
26  * This setting has no effect on HTTP/1.x connections.
27  * On HTTP/2 connections this controls HPACK behavior.
28  * See RFC-7541 Section 7.1 for security considerations.
29  */
30 enum aws_http_header_compression {
31     /**
32      * Compress header by encoding the cached index of its strings,
33      * or by updating the cache to contain these strings for future reference.
34      * Best for headers that are sent repeatedly.
35      * This is the default setting.
36      */
37     AWS_HTTP_HEADER_COMPRESSION_USE_CACHE,
38 
39     /**
40      * Encode header strings literally.
41      * If an intermediary re-broadcasts the headers, it is permitted to use cache.
42      * Best for unique headers that are unlikely to repeat.
43      */
44     AWS_HTTP_HEADER_COMPRESSION_NO_CACHE,
45 
46     /**
47      * Encode header strings literally and forbid all intermediaries from using
48      * cache when re-broadcasting.
49      * Best for header fields that are highly valuable or sensitive to recovery.
50      */
51     AWS_HTTP_HEADER_COMPRESSION_NO_FORWARD_CACHE,
52 };
53 
54 /**
55  * A lightweight HTTP header struct.
56  * Note that the underlying strings are not owned by the byte cursors.
57  */
58 struct aws_http_header {
59     struct aws_byte_cursor name;
60     struct aws_byte_cursor value;
61 
62     /* Controls whether the header's strings may be compressed via caching. */
63     enum aws_http_header_compression compression;
64 };
65 
66 /**
67  * A transformable block of HTTP headers.
68  * Provides a nice API for getting/setting header names and values.
69  *
70  * All strings are copied and stored within this datastructure.
71  * The index of a given header may change any time headers are modified.
72  * When iterating headers, the following ordering rules apply:
73  *
74  * - Headers with the same name will always be in the same order, relative to one another.
75  *   If "A: one" is added before "A: two", then "A: one" will always precede "A: two".
76  *
77  * - Headers with different names could be in any order, relative to one another.
78  *   If "A: one" is seen before "B: bee" in one iteration, you might see "B: bee" before "A: one" on the next.
79  */
80 struct aws_http_headers;
81 
82 /**
83  * Header block type.
84  * INFORMATIONAL: Header block for 1xx informational (interim) responses.
85  * MAIN: Main header block sent with request or response.
86  * TRAILING: Headers sent after the body of a request or response.
87  */
88 enum aws_http_header_block {
89     AWS_HTTP_HEADER_BLOCK_MAIN,
90     AWS_HTTP_HEADER_BLOCK_INFORMATIONAL,
91     AWS_HTTP_HEADER_BLOCK_TRAILING,
92 };
93 
94 /**
95  * The definition for an outgoing HTTP request or response.
96  * The message may be transformed (ex: signing the request) before its data is eventually sent.
97  *
98  * The message keeps internal copies of its trivial strings (method, path, headers)
99  * but does NOT take ownership of its body stream.
100  *
101  * A language binding would likely present this as an HttpMessage base class with
102  * HttpRequest and HttpResponse subclasses.
103  */
104 struct aws_http_message;
105 
106 /**
107  * Function to invoke when a message transformation completes.
108  * This function MUST be invoked or the application will soft-lock.
109  * `message` and `complete_ctx` must be the same pointers provided to the `aws_http_message_transform_fn`.
110  * `error_code` should should be AWS_ERROR_SUCCESS if transformation was successful,
111  * otherwise pass a different AWS_ERROR_X value.
112  */
113 typedef void(
114     aws_http_message_transform_complete_fn)(struct aws_http_message *message, int error_code, void *complete_ctx);
115 
116 /**
117  * A function that may modify a request or response before it is sent.
118  * The transformation may be asynchronous or immediate.
119  * The user MUST invoke the `complete_fn` when transformation is complete or the application will soft-lock.
120  * When invoking the `complete_fn`, pass along the `message` and `complete_ctx` provided here and an error code.
121  * The error code should be AWS_ERROR_SUCCESS if transformation was successful,
122  * otherwise pass a different AWS_ERROR_X value.
123  */
124 typedef void(aws_http_message_transform_fn)(
125     struct aws_http_message *message,
126     void *user_data,
127     aws_http_message_transform_complete_fn *complete_fn,
128     void *complete_ctx);
129 
130 /**
131  * Invoked repeatedly times as headers are received.
132  * At this point, aws_http_stream_get_incoming_response_status() can be called for the client.
133  * And aws_http_stream_get_incoming_request_method() and aws_http_stream_get_incoming_request_uri() can be called for
134  * the server.
135  * This is always invoked on the HTTP connection's event-loop thread.
136  *
137  * Return AWS_OP_SUCCESS to continue processing the stream.
138  * Return AWS_OP_ERR to indicate failure and cancel the stream.
139  */
140 typedef int(aws_http_on_incoming_headers_fn)(
141     struct aws_http_stream *stream,
142     enum aws_http_header_block header_block,
143     const struct aws_http_header *header_array,
144     size_t num_headers,
145     void *user_data);
146 
147 /**
148  * Invoked when the incoming header block of this type(informational/main/trailing) has been completely read.
149  * This is always invoked on the HTTP connection's event-loop thread.
150  *
151  * Return AWS_OP_SUCCESS to continue processing the stream.
152  * Return AWS_OP_ERR to indicate failure and cancel the stream.
153  */
154 typedef int(aws_http_on_incoming_header_block_done_fn)(
155     struct aws_http_stream *stream,
156     enum aws_http_header_block header_block,
157     void *user_data);
158 
159 /**
160  * Called repeatedly as body data is received.
161  * The data must be copied immediately if you wish to preserve it.
162  * This is always invoked on the HTTP connection's event-loop thread.
163  *
164  * Note that, if the connection is using manual_window_management then the window
165  * size has shrunk by the amount of body data received. If the window size
166  * reaches 0 no further data will be received. Increment the window size with
167  * aws_http_stream_update_window().
168  *
169  * Return AWS_OP_SUCCESS to continue processing the stream.
170  * Return AWS_OP_ERR to indicate failure and cancel the stream.
171  */
172 typedef int(
173     aws_http_on_incoming_body_fn)(struct aws_http_stream *stream, const struct aws_byte_cursor *data, void *user_data);
174 
175 /**
176  * Invoked when request has been completely read.
177  * This is always invoked on the HTTP connection's event-loop thread.
178  *
179  * Return AWS_OP_SUCCESS to continue processing the stream.
180  * Return AWS_OP_ERR to indicate failure and cancel the stream.
181  */
182 typedef int(aws_http_on_incoming_request_done_fn)(struct aws_http_stream *stream, void *user_data);
183 
184 /**
185  * Invoked when request/response stream is complete, whether successful or unsuccessful
186  * This is always invoked on the HTTP connection's event-loop thread.
187  */
188 typedef void(aws_http_on_stream_complete_fn)(struct aws_http_stream *stream, int error_code, void *user_data);
189 
190 /**
191  * Options for creating a stream which sends a request from the client and receives a response from the server.
192  */
193 struct aws_http_make_request_options {
194     /**
195      * The sizeof() this struct, used for versioning.
196      * Required.
197      */
198     size_t self_size;
199 
200     /**
201      * Definition for outgoing request.
202      * Required.
203      * This object must stay alive at least until on_complete is called.
204      */
205     struct aws_http_message *request;
206 
207     void *user_data;
208 
209     /**
210      * Invoked repeatedly times as headers are received.
211      * Optional.
212      * See `aws_http_on_incoming_headers_fn`.
213      */
214     aws_http_on_incoming_headers_fn *on_response_headers;
215 
216     /**
217      * Invoked when response header block has been completely read.
218      * Optional.
219      * See `aws_http_on_incoming_header_block_done_fn`.
220      */
221     aws_http_on_incoming_header_block_done_fn *on_response_header_block_done;
222 
223     /**
224      * Invoked repeatedly as body data is received.
225      * Optional.
226      * See `aws_http_on_incoming_body_fn`.
227      */
228     aws_http_on_incoming_body_fn *on_response_body;
229 
230     /**
231      * Invoked when request/response stream is complete, whether successful or unsuccessful
232      * Optional.
233      * See `aws_http_on_stream_complete_fn`.
234      */
235     aws_http_on_stream_complete_fn *on_complete;
236 };
237 
238 struct aws_http_request_handler_options {
239     /* Set to sizeof() this struct, used for versioning. */
240     size_t self_size;
241 
242     /**
243      * Required.
244      */
245     struct aws_http_connection *server_connection;
246 
247     /**
248      * user_data passed to callbacks.
249      * Optional.
250      */
251     void *user_data;
252 
253     /**
254      * Invoked repeatedly times as headers are received.
255      * Optional.
256      * See `aws_http_on_incoming_headers_fn`.
257      */
258     aws_http_on_incoming_headers_fn *on_request_headers;
259 
260     /**
261      * Invoked when the request header block has been completely read.
262      * Optional.
263      * See `aws_http_on_incoming_header_block_done_fn`.
264      */
265     aws_http_on_incoming_header_block_done_fn *on_request_header_block_done;
266 
267     /**
268      * Invoked as body data is received.
269      * Optional.
270      * See `aws_http_on_incoming_body_fn`.
271      */
272     aws_http_on_incoming_body_fn *on_request_body;
273 
274     /**
275      * Invoked when request has been completely read.
276      * Optional.
277      * See `aws_http_on_incoming_request_done_fn`.
278      */
279     aws_http_on_incoming_request_done_fn *on_request_done;
280 
281     /**
282      * Invoked when request/response stream is complete, whether successful or unsuccessful
283      * Optional.
284      * See `aws_http_on_stream_complete_fn`.
285      */
286     aws_http_on_stream_complete_fn *on_complete;
287 };
288 
289 /**
290  * Invoked when the data of an outgoing HTTP/1.1 chunk is no longer in use.
291  * This is always invoked on the HTTP connection's event-loop thread.
292  *
293  * @param stream        HTTP-stream this chunk was submitted to.
294  * @param error_code    If error_code is AWS_ERROR_SUCCESS (0), the data was successfully sent.
295  *                      Any other error_code indicates that the HTTP-stream is in the process of terminating.
296  *                      If the error_code is AWS_ERROR_HTTP_STREAM_HAS_COMPLETED,
297  *                      the stream's termination has nothing to do with this chunk.
298  *                      Any other non-zero error code indicates a problem with this particular chunk's data.
299  * @param user_data     User data for this chunk.
300  */
301 typedef void aws_http1_stream_write_chunk_complete_fn(struct aws_http_stream *stream, int error_code, void *user_data);
302 
303 /**
304  * HTTP/1.1 chunk extension for chunked encoding.
305  * Note that the underlying strings are not owned by the byte cursors.
306  */
307 struct aws_http1_chunk_extension {
308     struct aws_byte_cursor key;
309     struct aws_byte_cursor value;
310 };
311 
312 /**
313  * Encoding options for an HTTP/1.1 chunked transfer encoding chunk.
314  */
315 struct aws_http1_chunk_options {
316     /*
317      * The data stream to be sent in a single chunk.
318      * The aws_input_stream must remain valid until on_complete is invoked.
319      * May be NULL in the final chunk with size 0.
320      *
321      * Note that, for Transfer-Encodings other than "chunked", the data is
322      * expected to already have that encoding applied. For example, if
323      * "Transfer-Encoding: gzip, chunked" then the data from aws_input_stream
324      * should already be in gzip format.
325      */
326     struct aws_input_stream *chunk_data;
327 
328     /*
329      * Size of the chunk_data input stream in bytes.
330      */
331     uint64_t chunk_data_size;
332 
333     /**
334      * A pointer to an array of chunked extensions.
335      * The num_extensions must match the length of the array.
336      * This data is deep-copied by aws_http1_stream_write_chunk(),
337      * it does not need to remain valid until on_complete is invoked.
338      */
339     struct aws_http1_chunk_extension *extensions;
340 
341     /**
342      * The number of elements defined in the extensions array.
343      */
344     size_t num_extensions;
345 
346     /**
347      * Invoked when the chunk data is no longer in use, whether or not it was successfully sent.
348      * Optional.
349      * See `aws_http1_stream_write_chunk_complete_fn`.
350      */
351     aws_http1_stream_write_chunk_complete_fn *on_complete;
352 
353     /**
354      * User provided data passed to the on_complete callback on its invocation.
355      */
356     void *user_data;
357 };
358 
359 #define AWS_HTTP_REQUEST_HANDLER_OPTIONS_INIT                                                                          \
360     { .self_size = sizeof(struct aws_http_request_handler_options), }
361 
362 AWS_EXTERN_C_BEGIN
363 
364 /**
365  * Return whether both names are equivalent.
366  * This is a case-insensitive string comparison.
367  *
368  * Example Matches:
369  * "Content-Length" == "content-length" // upper or lower case ok
370 
371  * Example Mismatches:
372  * "Content-Length" != " Content-Length" // leading whitespace bad
373  */
374 AWS_HTTP_API
375 bool aws_http_header_name_eq(struct aws_byte_cursor name_a, struct aws_byte_cursor name_b);
376 
377 /**
378  * Create a new headers object.
379  * The caller has a hold on the object and must call aws_http_headers_release() when they are done with it.
380  */
381 AWS_HTTP_API
382 struct aws_http_headers *aws_http_headers_new(struct aws_allocator *allocator);
383 
384 /**
385  * Acquire a hold on the object, preventing it from being deleted until
386  * aws_http_headers_release() is called by all those with a hold on it.
387  */
388 AWS_HTTP_API
389 void aws_http_headers_acquire(struct aws_http_headers *headers);
390 
391 /**
392  * Release a hold on the object.
393  * The object is deleted when all holds on it are released.
394  */
395 AWS_HTTP_API
396 void aws_http_headers_release(struct aws_http_headers *headers);
397 
398 /**
399  * Add a header.
400  * The underlying strings are copied.
401  */
402 AWS_HTTP_API
403 int aws_http_headers_add_header(struct aws_http_headers *headers, const struct aws_http_header *header);
404 
405 /**
406  * Add a header.
407  * The underlying strings are copied.
408  */
409 AWS_HTTP_API
410 int aws_http_headers_add(struct aws_http_headers *headers, struct aws_byte_cursor name, struct aws_byte_cursor value);
411 
412 /**
413  * Add an array of headers.
414  * The underlying strings are copied.
415  */
416 AWS_HTTP_API
417 int aws_http_headers_add_array(struct aws_http_headers *headers, const struct aws_http_header *array, size_t count);
418 
419 /**
420  * Set a header value.
421  * The header is added if necessary and any existing values for this name are removed.
422  * The underlying strings are copied.
423  */
424 AWS_HTTP_API
425 int aws_http_headers_set(struct aws_http_headers *headers, struct aws_byte_cursor name, struct aws_byte_cursor value);
426 
427 /**
428  * Get the total number of headers.
429  */
430 AWS_HTTP_API
431 size_t aws_http_headers_count(const struct aws_http_headers *headers);
432 
433 /**
434  * Get the header at the specified index.
435  * The index of a given header may change any time headers are modified.
436  * When iterating headers, the following ordering rules apply:
437  *
438  * - Headers with the same name will always be in the same order, relative to one another.
439  *   If "A: one" is added before "A: two", then "A: one" will always precede "A: two".
440  *
441  * - Headers with different names could be in any order, relative to one another.
442  *   If "A: one" is seen before "B: bee" in one iteration, you might see "B: bee" before "A: one" on the next.
443  *
444  * AWS_ERROR_INVALID_INDEX is raised if the index is invalid.
445  */
446 AWS_HTTP_API
447 int aws_http_headers_get_index(
448     const struct aws_http_headers *headers,
449     size_t index,
450     struct aws_http_header *out_header);
451 
452 /**
453  * Get the first value for this name, ignoring any additional values.
454  * AWS_ERROR_HTTP_HEADER_NOT_FOUND is raised if the name is not found.
455  */
456 AWS_HTTP_API
457 int aws_http_headers_get(
458     const struct aws_http_headers *headers,
459     struct aws_byte_cursor name,
460     struct aws_byte_cursor *out_value);
461 
462 /**
463  * Test if header name exists or not in headers
464  */
465 AWS_HTTP_API
466 bool aws_http_headers_has(const struct aws_http_headers *headers, struct aws_byte_cursor name);
467 
468 /**
469  * Remove all headers with this name.
470  * AWS_ERROR_HTTP_HEADER_NOT_FOUND is raised if no headers with this name are found.
471  */
472 AWS_HTTP_API
473 int aws_http_headers_erase(struct aws_http_headers *headers, struct aws_byte_cursor name);
474 
475 /**
476  * Remove the first header found with this name and value.
477  * AWS_ERROR_HTTP_HEADER_NOT_FOUND is raised if no such header is found.
478  */
479 AWS_HTTP_API
480 int aws_http_headers_erase_value(
481     struct aws_http_headers *headers,
482     struct aws_byte_cursor name,
483     struct aws_byte_cursor value);
484 
485 /**
486  * Remove the header at the specified index.
487  *
488  * AWS_ERROR_INVALID_INDEX is raised if the index is invalid.
489  */
490 AWS_HTTP_API
491 int aws_http_headers_erase_index(struct aws_http_headers *headers, size_t index);
492 
493 /**
494  * Clear all headers.
495  */
496 AWS_HTTP_API
497 void aws_http_headers_clear(struct aws_http_headers *headers);
498 
499 /**
500  * Create a new request message.
501  * The message is blank, all properties (method, path, etc) must be set individually.
502  *
503  * The caller has a hold on the object and must call aws_http_message_release() when they are done with it.
504  */
505 AWS_HTTP_API
506 struct aws_http_message *aws_http_message_new_request(struct aws_allocator *allocator);
507 
508 /**
509  * Like aws_http_message_new_request(), but uses existing aws_http_headers instead of creating a new one.
510  * Acquires a hold on the headers, and releases it when the request is destroyed.
511  */
512 AWS_HTTP_API
513 struct aws_http_message *aws_http_message_new_request_with_headers(
514     struct aws_allocator *allocator,
515     struct aws_http_headers *existing_headers);
516 
517 /**
518  * Create a new response message.
519  * The message is blank, all properties (status, headers, etc) must be set individually.
520  *
521  * The caller has a hold on the object and must call aws_http_message_release() when they are done with it.
522  */
523 AWS_HTTP_API
524 struct aws_http_message *aws_http_message_new_response(struct aws_allocator *allocator);
525 
526 /**
527  * Acquire a hold on the object, preventing it from being deleted until
528  * aws_http_message_release() is called by all those with a hold on it.
529  */
530 AWS_HTTP_API
531 void aws_http_message_acquire(struct aws_http_message *message);
532 
533 /**
534  * Release a hold on the object.
535  * The object is deleted when all holds on it are released.
536  */
537 AWS_HTTP_API
538 void aws_http_message_release(struct aws_http_message *message);
539 
540 /**
541  * Deprecated. This is equivalent to aws_http_message_release().
542  */
543 AWS_HTTP_API
544 void aws_http_message_destroy(struct aws_http_message *message);
545 
546 AWS_HTTP_API
547 bool aws_http_message_is_request(const struct aws_http_message *message);
548 
549 AWS_HTTP_API
550 bool aws_http_message_is_response(const struct aws_http_message *message);
551 
552 /**
553  * Get the method (request messages only).
554  */
555 AWS_HTTP_API
556 int aws_http_message_get_request_method(
557     const struct aws_http_message *request_message,
558     struct aws_byte_cursor *out_method);
559 
560 /**
561  * Set the method (request messages only).
562  * The request makes its own copy of the underlying string.
563  */
564 AWS_HTTP_API
565 int aws_http_message_set_request_method(struct aws_http_message *request_message, struct aws_byte_cursor method);
566 
567 /*
568  * Get the path-and-query value (request messages only).
569  */
570 AWS_HTTP_API
571 int aws_http_message_get_request_path(const struct aws_http_message *request_message, struct aws_byte_cursor *out_path);
572 
573 /**
574  * Set the path-and-query value (request messages only).
575  * The request makes its own copy of the underlying string.
576  */
577 AWS_HTTP_API
578 int aws_http_message_set_request_path(struct aws_http_message *request_message, struct aws_byte_cursor path);
579 
580 /**
581  * Get the status code (response messages only).
582  * If no status is set, AWS_ERROR_HTTP_DATA_NOT_AVAILABLE is raised.
583  */
584 AWS_HTTP_API
585 int aws_http_message_get_response_status(const struct aws_http_message *response_message, int *out_status_code);
586 
587 /**
588  * Set the status code (response messages only).
589  */
590 AWS_HTTP_API
591 int aws_http_message_set_response_status(struct aws_http_message *response_message, int status_code);
592 
593 /**
594  * Get the body stream.
595  * Returns NULL if no body stream is set.
596  */
597 AWS_HTTP_API
598 struct aws_input_stream *aws_http_message_get_body_stream(const struct aws_http_message *message);
599 
600 /**
601  * Set the body stream.
602  * NULL is an acceptable value for messages with no body.
603  * Note: The message does NOT take ownership of the body stream.
604  * The stream must not be destroyed until the message is complete.
605  */
606 AWS_HTTP_API
607 void aws_http_message_set_body_stream(struct aws_http_message *message, struct aws_input_stream *body_stream);
608 
609 /**
610  * Submit a chunk of data to be sent on an HTTP/1.1 stream.
611  * The stream must have specified "chunked" in a "transfer-encoding" header.
612  * For client streams, activate() must be called before any chunks are submitted.
613  * For server streams, the response must be submitted before any chunks.
614  * A final chunk with size 0 must be submitted to successfully complete the HTTP-stream.
615  *
616  * Returns AWS_OP_SUCCESS if the chunk has been submitted. The chunk's completion
617  * callback will be invoked when the HTTP-stream is done with the chunk data,
618  * whether or not it was successfully sent (see `aws_http1_stream_write_chunk_complete_fn`).
619  * The chunk data must remain valid until the completion callback is invoked.
620  *
621  * Returns AWS_OP_ERR and raises an error if the chunk could not be submitted.
622  * In this case, the chunk's completion callback will never be invoked.
623  * Note that it is always possible for the HTTP-stream to terminate unexpectedly
624  * prior to this call being made, in which case the error raised is
625  * AWS_ERROR_HTTP_STREAM_HAS_COMPLETED.
626  */
627 AWS_HTTP_API int aws_http1_stream_write_chunk(
628     struct aws_http_stream *http1_stream,
629     const struct aws_http1_chunk_options *options);
630 
631 /**
632  * Get the message's aws_http_headers.
633  *
634  * This datastructure has more functions for inspecting and modifying headers than
635  * are available on the aws_http_message datastructure.
636  */
637 AWS_HTTP_API
638 struct aws_http_headers *aws_http_message_get_headers(struct aws_http_message *message);
639 
640 /**
641  * Get the message's const aws_http_headers.
642  */
643 AWS_HTTP_API
644 const struct aws_http_headers *aws_http_message_get_const_headers(const struct aws_http_message *message);
645 
646 /**
647  * Get the number of headers.
648  */
649 AWS_HTTP_API
650 size_t aws_http_message_get_header_count(const struct aws_http_message *message);
651 
652 /**
653  * Get the header at the specified index.
654  * This function cannot fail if a valid index is provided.
655  * Otherwise, AWS_ERROR_INVALID_INDEX will be raised.
656  *
657  * The underlying strings are stored within the message.
658  */
659 AWS_HTTP_API
660 int aws_http_message_get_header(
661     const struct aws_http_message *message,
662     struct aws_http_header *out_header,
663     size_t index);
664 
665 /**
666  * Add a header to the end of the array.
667  * The message makes its own copy of the underlying strings.
668  */
669 AWS_HTTP_API
670 int aws_http_message_add_header(struct aws_http_message *message, struct aws_http_header header);
671 
672 /**
673  * Add an array of headers to the end of the header array.
674  * The message makes its own copy of the underlying strings.
675  *
676  * This is a helper function useful when it's easier to define headers as a stack array, rather than calling add_header
677  * repeatedly.
678  */
679 AWS_HTTP_API
680 int aws_http_message_add_header_array(
681     struct aws_http_message *message,
682     const struct aws_http_header *headers,
683     size_t num_headers);
684 
685 /**
686  * Remove the header at the specified index.
687  * Headers after this index are all shifted back one position.
688  *
689  * This function cannot fail if a valid index is provided.
690  * Otherwise, AWS_ERROR_INVALID_INDEX will be raised.
691  */
692 AWS_HTTP_API
693 int aws_http_message_erase_header(struct aws_http_message *message, size_t index);
694 
695 /**
696  * Create a stream, with a client connection sending a request.
697  * The request does not start sending automatically once the stream is created. You must call
698  * aws_http_stream_activate to begin execution of the request.
699  *
700  * The `options` are copied during this call.
701  *
702  * Tip for language bindings: Do not bind the `options` struct. Use something more natural for your language,
703  * such as Builder Pattern in Java, or Python's ability to take many optional arguments by name.
704  */
705 AWS_HTTP_API
706 struct aws_http_stream *aws_http_connection_make_request(
707     struct aws_http_connection *client_connection,
708     const struct aws_http_make_request_options *options);
709 
710 /**
711  * Create a stream, with a server connection receiving and responding to a request.
712  * This function can only be called from the `aws_http_on_incoming_request_fn` callback.
713  * aws_http_stream_send_response() should be used to send a response.
714  */
715 AWS_HTTP_API
716 struct aws_http_stream *aws_http_stream_new_server_request_handler(
717     const struct aws_http_request_handler_options *options);
718 
719 /**
720  * Users must release the stream when they are done with it, or its memory will never be cleaned up.
721  * This will not cancel the stream, its callbacks will still fire if the stream is still in progress.
722  *
723  * Tips for language bindings:
724  * - Invoke this from the wrapper class's finalizer/destructor.
725  * - Do not let the wrapper class be destroyed until on_complete() has fired.
726  */
727 AWS_HTTP_API
728 void aws_http_stream_release(struct aws_http_stream *stream);
729 
730 /**
731  * Only used for client initiated streams (immediately following a call to aws_http_connection_make_request).
732  *
733  * Activates the request's outgoing stream processing.
734  */
735 AWS_HTTP_API int aws_http_stream_activate(struct aws_http_stream *stream);
736 
737 AWS_HTTP_API
738 struct aws_http_connection *aws_http_stream_get_connection(const struct aws_http_stream *stream);
739 
740 /* Only valid in "request" streams, once response headers start arriving */
741 AWS_HTTP_API
742 int aws_http_stream_get_incoming_response_status(const struct aws_http_stream *stream, int *out_status);
743 
744 /* Only valid in "request handler" streams, once request headers start arriving */
745 AWS_HTTP_API
746 int aws_http_stream_get_incoming_request_method(
747     const struct aws_http_stream *stream,
748     struct aws_byte_cursor *out_method);
749 
750 AWS_HTTP_API
751 int aws_http_stream_get_incoming_request_uri(const struct aws_http_stream *stream, struct aws_byte_cursor *out_uri);
752 
753 /**
754  * Send response (only callable from "request handler" streams)
755  * The response object must stay alive at least until the stream's on_complete is called.
756  */
757 AWS_HTTP_API
758 int aws_http_stream_send_response(struct aws_http_stream *stream, struct aws_http_message *response);
759 
760 /**
761  * Increment the stream's flow-control window to keep data flowing.
762  *
763  * If the connection was created with `manual_window_management` set true,
764  * the flow-control window of each stream will shrink as body data is received
765  * (headers, padding, and other metadata do not affect the window).
766  * The connection's `initial_window_size` determines the starting size of each stream's window.
767  * If a stream's flow-control window reaches 0, no further data will be received.
768  *
769  * If `manual_window_management` is false, this call will have no effect.
770  * The connection maintains its flow-control windows such that
771  * no back-pressure is applied and data arrives as fast as possible.
772  */
773 AWS_HTTP_API
774 void aws_http_stream_update_window(struct aws_http_stream *stream, size_t increment_size);
775 
776 /**
777  * Gets the HTTP/2 id associated with a stream.  Even h1 streams have an id (using the same allocation procedure
778  * as http/2) for easier tracking purposes. For client streams, this will only be non-zero after a successful call
779  * to aws_http_stream_activate()
780  */
781 AWS_HTTP_API
782 uint32_t aws_http_stream_get_id(const struct aws_http_stream *stream);
783 
784 /**
785  * Reset the HTTP/2 stream (HTTP/2 only).
786  * Note that if the stream closes before this async call is fully processed, the RST_STREAM frame will not be sent.
787  *
788  * @param http2_stream HTTP/2 stream.
789  * @param http2_error aws_http2_error_code. Reason to reset the stream.
790  */
791 AWS_HTTP_API
792 int aws_http2_stream_reset(struct aws_http_stream *http2_stream, uint32_t http2_error);
793 
794 /**
795  * Get the error code received in rst_stream.
796  * Only valid if the stream has completed, and an RST_STREAM frame has received.
797  *
798  * @param http2_stream HTTP/2 stream.
799  * @param out_http2_error Gets to set to HTTP/2 error code received in rst_stream.
800  */
801 AWS_HTTP_API
802 int aws_http2_stream_get_received_reset_error_code(struct aws_http_stream *http2_stream, uint32_t *out_http2_error);
803 
804 /**
805  * Get the HTTP/2 error code sent in the RST_STREAM frame (HTTP/2 only).
806  * Only valid if the stream has completed, and has sent an RST_STREAM frame.
807  *
808  * @param http2_stream HTTP/2 stream.
809  * @param out_http2_error Gets to set to HTTP/2 error code sent in rst_stream.
810  */
811 AWS_HTTP_API
812 int aws_http2_stream_get_sent_reset_error_code(struct aws_http_stream *http2_stream, uint32_t *out_http2_error);
813 
814 AWS_EXTERN_C_END
815 
816 #endif /* AWS_HTTP_REQUEST_RESPONSE_H */
817