5.6 KiB
title | menu | weight |
---|---|---|
Extractors | docs_basics | 170 |
Type-safe information extraction
Actix-web provides a facility for type-safe request information access called extractors
(ie, impl FromRequest
). By default, actix-web provides several extractor implementations.
Extractors Within Handler Functions
An extractor can be accessed in a few different ways.
Option 1 - passed as a parameter to a handler function:
{{< include-example example="extractors" file="main.rs" section="option-one" >}}
Option 2 - accessed by calling extract()
on the Extractor
{{< include-example example="extractors" file="main.rs" section="option-two" >}}
Path
Path provides information that can be extracted from the Request's path. You can deserialize any variable segment from the path.
For instance, for resource that registered for the /users/{userid}/{friend}
path
two segments could be deserialized, userid
and friend
. These segments
could be extracted into a tuple
, i.e. Path<(u32, String)>
or any structure
that implements the Deserialize
trait from the serde crate.
{{< include-example example="extractors" file="path_one.rs" section="path-one" >}}
It is also possible to extract path information to a specific type that
implements the Deserialize
trait from serde. Here is an equivalent example that uses serde
instead of a tuple type.
{{< include-example example="extractors" file="path_two.rs" section="path-two" >}}
It is also possible to get
or query
the request for path parameters by name:
{{< include-example example="extractors" file="path_three.rs" section="path-three" >}}
Query
The Query type provides extraction functionality for the request's query parameters. Underneath it uses serde_urlencoded crate.
{{< include-example example="extractors" file="query.rs" section="query" >}}
Json
Json allows to deserialize
a request body into a struct. To extract typed information from a request's body,
the type T
must implement the Deserialize
trait from serde.
{{< include-example example="extractors" file="json_one.rs" section="json-one" >}}
Some extractors provide a way to configure the extraction process. Json extractor
JsonConfig type
for configuration. To configure an extractor, pass it's configuration object to the resource's
.data()
method. In case of a Json extractor it returns a JsonConfig. You can
configure the maximum size of the json payload as well as a custom error handler function.
The following example limits the size of the payload to 4kb and uses a custom error handler.
{{< include-example example="extractors" file="json_two.rs" section="json-two" >}}
Form
At the moment only url-encoded forms are supported. The url-encoded body
could be extracted to a specific type. This type must implement
the Deserialize
trait from the serde crate.
FormConfig allows configuring the extraction process.
{{< include-example example="extractors" file="form.rs" section="form" >}}
Multiple extractors
Actix-web provides extractor implementations for tuples (up to 10 elements)
whose elements implement FromRequest
.
For example we can use a path extractor and a query extractor at the same time.
{{< include-example example="extractors" file="multiple.rs" section="multi" >}}
Other
Actix-web also provides several other extractors:
- Data - If you need access to an application state.
- HttpRequest - HttpRequest itself is an extractor which returns self, in case you need access to the request.
- String - You can convert a request's payload to a String. Example is available in doc strings.
- bytes::Bytes - You can convert a request's payload into Bytes. Example is available in doc strings.
- Payload - You can access a request's payload. Example
Async Data Access
Application state is accessible from the handler with the web::Data
extractor;
however, state is accessible as a read-only reference. If you need mutable access to state,
it must be implemented.
Beware, actix creates multiple copies of the application state and the handlers, unique for each thread. If you run your application in several threads, actix will create the same amount as number of threads of application state objects and handler objects.
Here is an example of a handler that stores the number of processed requests:
{{< include-example example="request-handlers" file="main.rs" section="data" >}}
Although this handler will work, self.0
will be different depending on the number of threads and
number of requests processed per thread. A proper implementation would use Arc
and AtomicUsize
.
{{< include-example example="request-handlers" file="handlers_arc.rs" section="arc" >}}
Be careful with synchronization primitives like
Mutex
orRwLock
. Theactix-web
framework handles requests asynchronously. By blocking thread execution, all concurrent request handling processes would block. If you need to share or update some state from multiple threads, consider using the actix actor system.