1
0
mirror of https://github.com/actix/actix-website synced 2025-02-02 12:19:04 +01:00

First pass at Responses section.

This commit is contained in:
Cameron Dershem 2019-06-17 15:15:33 -04:00
parent 507842bf1c
commit ea1600c417
10 changed files with 135 additions and 96 deletions

View File

@ -17,17 +17,7 @@ The methods `.body`, `.finish`, and `.json` finalize response creation and
return a constructed *HttpResponse* instance. If this methods is called on the same
builder instance multiple times, the builder will panic.
```rust
use actix_web::{HttpRequest, HttpResponse, http::ContentEncoding};
fn index(req: &HttpRequest) -> HttpResponse {
HttpResponse::Ok()
.content_encoding(ContentEncoding::Br)
.content_type("plain/text")
.header("X-Hdr", "sample")
.body("data")
}
```
{{< include-example example="responses" file="main.rs" section="builder" >}}
# Content encoding
@ -38,80 +28,34 @@ Actix automatically *compresses* payloads. The following codecs are supported:
* Deflate
* Identity
Response payload is compressed based on the *content_encoding* parameter.
By default, `ContentEncoding::Auto` is used. If `ContentEncoding::Auto` is selected,
then the compression depends on the request's `Accept-Encoding` header.
Response payload is compressed based on the *encoding* parameter from the
`middleware::BodyEncoding` trait. By default, `ContentEncoding::Auto` is
used. If `ContentEncoding::Auto` is selected, then the compression depends
on the request's `Accept-Encoding` header.
> `ContentEncoding::Identity` can be used to disable compression.
> If another content encoding is selected, the compression is enforced for that codec.
For example, to enable `brotli` use `ContentEncoding::Br`:
```rust
use actix_web::{HttpRequest, HttpResponse, http::ContentEncoding};
fn index(req: HttpRequest) -> HttpResponse {
HttpResponse::Ok()
.content_encoding(ContentEncoding::Br)
.body("data")
}
```
{{< include-example example="responses" file="brotli.rs" section="brotli" >}}
In this case we explicitly disable content compression
by setting content encoding to a `Identity` value:
```rust
use actix_web::{HttpRequest, HttpResponse, http::ContentEncoding};
fn index(req: HttpRequest) -> HttpResponse {
HttpResponse::Ok()
// v- disable compression
.content_encoding(ContentEncoding::Identity)
.body("data")
}
```
{{< include-example example="responses" file="identity.rs" section="identity" >}}
When dealing with an already compressed body (for example when serving assets),
set the content encoding to `Identity` to avoid compressing the already compressed
data and set the `content-encoding` header manually:
```rust
use actix_web::{HttpRequest, HttpResponse, http::ContentEncoding};
static HELLO_WORLD: &[u8] = &[
0x1f,0x8b,0x08,0x00,0xa2,0x30,0x10,0x5c,
0x00,0x03,0xcb,0x48,0xcd,0xc9,0xc9,0x57,
0x28,0xcf,0x2f,0xca,0x49,0xe1,0x02,0x00,
0x2d,0x3b,0x08,0xaf,0x0c,0x00,0x00,0x00
];
pub fn index(req: HttpRequest) -> HttpResponse {
HttpResponse::Ok()
.content_encoding(ContentEncoding::Identity)
.header("content-encoding", "gzip")
.body(HELLO_WORLD)
}
```
{{< include-example example="responses" file="identity_two.rs" section="identity-two" >}}
Also it is possible to set default content encoding on application level, by
default `ContentEncoding::Auto` is used, which implies automatic content compression
negotiation.
```rust
use actix_web::{App, HttpRequest, HttpResponse, http::ContentEncoding};
fn index(req: HttpRequest) -> HttpResponse {
HttpResponse::Ok()
.body("data")
}
fn main() {
let app = App::new()
// v- disable compression for all routes
.default_encoding(ContentEncoding::Identity)
.resource("/index.html", |r| r.with(index));
}
```
{{< include-example example="responses" file="auto.rs" section="auto" >}}
# JSON Response
@ -119,26 +63,7 @@ The `Json` type allows to respond with well-formed JSON data: simply return a va
type Json<T> where `T` is the type of a structure to serialize into *JSON*.
The type `T` must implement the `Serialize` trait from *serde*.
```rust
# extern crate actix_web;
#[macro_use] extern crate serde_derive;
use actix_web::{App, HttpRequest, Json, Result, http::Method};
#[derive(Serialize)]
struct MyObj {
name: String,
}
fn index(req: &HttpRequest) -> Result<Json<MyObj>> {
Ok(Json(MyObj{name: req.match_info().query("name")?}))
}
fn main() {
App::new()
.resource(r"/a/{name}", |r| r.method(Method::GET).f(index))
.finish();
}
```
{{< include-example example="responses" file="json_resp.rs" section="json-resp" >}}
# Chunked transfer encoding
@ -149,14 +74,4 @@ is enabled automatically.
> Enabling chunked encoding for *HTTP/2.0* responses is forbidden.
```rust
use actix_web::*;
use bytes::Bytes;
use futures::stream::once;
fn index(req: HttpRequest) -> HttpResponse {
HttpResponse::Ok()
.chunked()
.body(Body::Streaming(Box::new(once(Ok(Bytes::from_static(b"data"))))))
}
```
{{< include-example example="responses" file="chunked.rs" section="chunked" >}}

View File

@ -19,4 +19,5 @@ exclude = [
"autoreload",
"errors",
"requests",
"responses",
]

View File

@ -0,0 +1,10 @@
[package]
name = "responses"
version = "0.1.0"
edition = "2018"
[dependencies]
actix-web = "1.0"
serde = "1.0"
futures = "0.1"
bytes = "0.4"

View File

@ -0,0 +1,16 @@
// <auto>
use actix_web::{
http::ContentEncoding, middleware, web, App, HttpRequest, HttpResponse,
};
fn index(req: HttpRequest) -> HttpResponse {
HttpResponse::Ok().body("data")
}
fn main() {
let app = App::new()
// v- disable compression for all routes
.wrap(middleware::Compress::new(ContentEncoding::Identity))
.route("/", web::get().to(index));
}
// </auto>

View File

@ -0,0 +1,13 @@
// <brotli>
use actix_web::{
http::ContentEncoding, middleware::BodyEncoding, HttpRequest, HttpResponse,
};
fn index_br(req: HttpRequest) -> HttpResponse {
HttpResponse::Ok()
.encoding(ContentEncoding::Br)
.body("data")
}
// </brotli>
fn main() {}

View File

@ -0,0 +1,14 @@
// <chunked>
// use actix_web::{web, HttpRequest, HttpResponse};
// use bytes::Bytes;
// use futures::stream::once;
// fn index(req: HttpRequest) -> HttpResponse {
// HttpResponse::Ok()
// .chunked()
// .body(Body::Streaming(Box::new(once(Ok(Bytes::from_static(
// b"data",
// ))))))
// }
// </chunked>
fn main() {}

View File

@ -0,0 +1,12 @@
// <identity>
use actix_web::{
http::ContentEncoding, middleware::BodyEncoding, HttpRequest, HttpResponse,
};
fn index(req: HttpRequest) -> HttpResponse {
HttpResponse::Ok()
// v- disable compression
.encoding(ContentEncoding::Identity)
.body("data")
}
// </identity>

View File

@ -0,0 +1,18 @@
// <identity-two>
use actix_web::{
http::ContentEncoding, middleware::BodyEncoding, HttpRequest, HttpResponse,
};
static HELLO_WORLD: &[u8] = &[
0x1f, 0x8b, 0x08, 0x00, 0xa2, 0x30, 0x10, 0x5c, 0x00, 0x03, 0xcb, 0x48, 0xcd, 0xc9,
0xc9, 0x57, 0x28, 0xcf, 0x2f, 0xca, 0x49, 0xe1, 0x02, 0x00, 0x2d, 0x3b, 0x08, 0xaf,
0x0c, 0x00, 0x00, 0x00,
];
pub fn index(_req: HttpRequest) -> HttpResponse {
HttpResponse::Ok()
.encoding(ContentEncoding::Identity)
.header("content-encoding", "gzip")
.body(HELLO_WORLD)
}
// </identity-two>

View File

@ -0,0 +1,19 @@
// <json-resp>
use actix_web::{web, App, HttpRequest, Result};
use serde::Serialize;
#[derive(Serialize)]
struct MyObj {
name: String,
}
fn index(req: HttpRequest) -> Result<web::Json<MyObj>> {
Ok(web::Json(MyObj {
name: req.match_info().query("name").to_string(),
}))
}
fn main() {
App::new().route(r"/a/{name}", web::get().to(index));
}
// </json-resp>

View File

@ -0,0 +1,21 @@
mod auto;
mod brotli;
mod chunked;
mod identity;
mod identity_two;
mod json_resp;
// <builder>
use actix_web::{
http::ContentEncoding, middleware::BodyEncoding, HttpRequest, HttpResponse,
};
fn index(_req: HttpRequest) -> HttpResponse {
HttpResponse::Ok()
.encoding(ContentEncoding::Br)
.content_type("plain/text")
.header("X-Hdr", "sample")
.body("data")
}
// </builder>
fn main() {}