-
HttpServer::start()
renamed toHttpServer::run()
. It also possible to.await
onrun
method result, in that case it awaits server exit. -
App::register_data()
renamed toApp::app_data()
and accepts any typeT: 'static
. Stored data is available viaHttpRequest::app_data()
method at runtime. -
Extractor configuration must be registered with
App::app_data()
instead ofApp::data()
-
Sync handlers has been removed.
.to_async()
method has been renamed to.to()
replacefn
withasync fn
to convert sync handler to async -
actix_http_test::TestServer
moved toactix_web::test
module. To start test server usetest::start()
ortest_start_with_config()
methods -
ResponseError
trait has been reafctored.ResponseError::error_response()
renders http response. -
Feature
rust-tls
renamed torustls
instead of
actix-web = { version = "2.0.0", features = ["rust-tls"] }
use
actix-web = { version = "2.0.0", features = ["rustls"] }
-
Feature
ssl
renamed toopenssl
instead of
actix-web = { version = "2.0.0", features = ["ssl"] }
use
actix-web = { version = "2.0.0", features = ["openssl"] }
-
Cors
builder now requires that you call.finish()
to construct the middleware
-
Cors middleware has been moved to
actix-cors
crateinstead of
use actix_web::middleware::cors::Cors;
use
use actix_cors::Cors;
-
Identity middleware has been moved to
actix-identity
crateinstead of
use actix_web::middleware::identity::{Identity, CookieIdentityPolicy, IdentityService};
use
use actix_identity::{Identity, CookieIdentityPolicy, IdentityService};
-
Extractor configuration. In version 1.0 this is handled with the new
Data
mechanism for both setting and retrieving the configurationinstead of
#[derive(Default)] struct ExtractorConfig { config: String, } impl FromRequest for YourExtractor { type Config = ExtractorConfig; type Result = Result<YourExtractor, Error>; fn from_request(req: &HttpRequest, cfg: &Self::Config) -> Self::Result { println!("use the config: {:?}", cfg.config); ... } } App::new().resource("/route_with_config", |r| { r.post().with_config(handler_fn, |cfg| { cfg.0.config = "test".to_string(); }) })
use the HttpRequest to get the configuration like any other
Data
withreq.app_data::<C>()
and set it with thedata()
method on theresource
#[derive(Default)] struct ExtractorConfig { config: String, } impl FromRequest for YourExtractor { type Error = Error; type Future = Result<Self, Self::Error>; type Config = ExtractorConfig; fn from_request(req: &HttpRequest, payload: &mut Payload) -> Self::Future { let cfg = req.app_data::<ExtractorConfig>(); println!("config data?: {:?}", cfg.unwrap().role); ... } } App::new().service( resource("/route_with_config") .data(ExtractorConfig { config: "test".to_string(), }) .route(post().to(handler_fn)), )
-
Resource registration. 1.0 version uses generalized resource registration via
.service()
method.instead of
App.new().resource("/welcome", |r| r.f(welcome))
use App's or Scope's
.service()
method..service()
method accepts object that implementsHttpServiceFactory
trait. By default actix-web providesResource
andScope
services.App.new().service( web::resource("/welcome") .route(web::get().to(welcome)) .route(web::post().to(post_handler))
-
Scope registration.
instead of
let app = App::new().scope("/{project_id}", |scope| { scope .resource("/path1", |r| r.f(|_| HttpResponse::Ok())) .resource("/path2", |r| r.f(|_| HttpResponse::Ok())) .resource("/path3", |r| r.f(|_| HttpResponse::MethodNotAllowed())) });
use
.service()
for registration andweb::scope()
as scope object factory.let app = App::new().service( web::scope("/{project_id}") .service(web::resource("/path1").to(|| HttpResponse::Ok())) .service(web::resource("/path2").to(|| HttpResponse::Ok())) .service(web::resource("/path3").to(|| HttpResponse::MethodNotAllowed())) );
-
.with()
,.with_async()
registration methods have been renamed to.to()
and.to_async()
.instead of
App.new().resource("/welcome", |r| r.with(welcome))
use
.to()
or.to_async()
methodsApp.new().service(web::resource("/welcome").to(welcome))
-
Passing arguments to handler with extractors, multiple arguments are allowed
instead of
fn welcome((body, req): (Bytes, HttpRequest)) -> ... { ... }
use multiple arguments
fn welcome(body: Bytes, req: HttpRequest) -> ... { ... }
-
.f()
,.a()
and.h()
handler registration methods have been removed. Use.to()
for handlers and.to_async()
for async handlers. Handler function must use extractors.instead of
App.new().resource("/welcome", |r| r.f(welcome))
use App's
to()
orto_async()
methodsApp.new().service(web::resource("/welcome").to(welcome))
-
HttpRequest
does not provide access to request's payload stream.instead of
fn index(req: &HttpRequest) -> Box<Future<Item=HttpResponse, Error=Error>> { req .payload() .from_err() .fold((), |_, chunk| { ... }) .map(|_| HttpResponse::Ok().finish()) .responder() }
use
Payload
extractorfn index(stream: web::Payload) -> impl Future<Item=HttpResponse, Error=Error> { stream .from_err() .fold((), |_, chunk| { ... }) .map(|_| HttpResponse::Ok().finish()) }
-
State
is nowData
. You register Data during the App initialization process and then access it from handlers either using a Data extractor or using HttpRequest's api.instead of
App.with_state(T)
use App's
data
methodApp.new() .data(T)
and either use the Data extractor within your handler
use actix_web::web::Data; fn endpoint_handler(Data<T>)){ ... }
.. or access your Data element from the HttpRequest
fn endpoint_handler(req: HttpRequest) { let data: Option<Data<T>> = req.app_data::<T>(); }
-
AsyncResponder is removed, use
.to_async()
registration method andimpl Future<>
as result type.instead of
use actix_web::AsyncResponder; fn endpoint_handler(...) -> impl Future<Item=HttpResponse, Error=Error>{ ... .responder() }
.. simply omit AsyncResponder and the corresponding responder() finish method
-
Middleware
instead of
let app = App::new() .middleware(middleware::Logger::default())
use
.wrap()
methodlet app = App::new() .wrap(middleware::Logger::default()) .route("/index.html", web::get().to(index));
-
HttpRequest::body()
,HttpRequest::urlencoded()
,HttpRequest::json()
,HttpRequest::multipart()
method have been removed. UseBytes
,String
,Form
,Json
,Multipart
extractors instead.instead of
fn index(req: &HttpRequest) -> Responder { req.body() .and_then(|body| { ... }) }
use
fn index(body: Bytes) -> Responder { ... }
-
actix_web::server
module has been removed. To start http server useactix_web::HttpServer
type -
StaticFiles and NamedFile has been move to separate create.
instead of
use actix_web::fs::StaticFile
use
use actix_files::Files
instead of
use actix_web::fs::Namedfile
use
use actix_files::NamedFile
-
Multipart has been move to separate create.
instead of
use actix_web::multipart::Multipart
use
use actix_multipart::Multipart
-
Response compression is not enabled by default. To enable, use
Compress
middleware,App::new().wrap(Compress::default())
. -
Session middleware moved to actix-session crate
-
Actors support have been moved to
actix-web-actors
crate -
Custom Error
Instead of error_response method alone, ResponseError now provides two methods: error_response and render_response respectively. Where, error_response creates the error response and render_response returns the error response to the caller.
Simplest migration from 0.7 to 1.0 shall include below method to the custom implementation of ResponseError:
fn render_response(&self) -> HttpResponse { self.error_response() }
-
The
' '
character is not percent decoded anymore before matching routes. If you need to use it in your routes, you should use%20
.instead of
fn main() { let app = App::new().resource("/my index", |r| { r.method(http::Method::GET) .with(index); }); }
use
fn main() { let app = App::new().resource("/my%20index", |r| { r.method(http::Method::GET) .with(index); }); }
-
If you used
AsyncResult::async
you need to replace it withAsyncResult::future
Route::with_config()
/Route::with_async_config()
always passes configuration objects as tuple even for handler with one parameter.
-
HttpRequest
does not implementStream
anymore. If you need to read request payload useHttpMessage::payload()
method.instead of
fn index(req: HttpRequest) -> impl Responder { req .from_err() .fold(...) .... }
use
.payload()
fn index(req: HttpRequest) -> impl Responder { req .payload() // <- get request payload stream .from_err() .fold(...) .... }
-
Middleware trait uses
&HttpRequest
instead of&mut HttpRequest
. -
Removed
Route::with2()
andRoute::with3()
use tuple of extractors instead.instead of
fn index(query: Query<..>, info: Json<MyStruct) -> impl Responder {}
use tuple of extractors and use
.with()
for registration:fn index((query, json): (Query<..>, Json<MyStruct)) -> impl Responder {}
-
Handler::handle()
uses&self
instead of&mut self
-
Handler::handle()
accepts reference toHttpRequest<_>
instead of value -
Removed deprecated
HttpServer::threads()
, use HttpServer::workers() instead. -
Renamed
client::ClientConnectorError::Connector
toclient::ClientConnectorError::Resolver
-
Route::with()
does not returnExtractorConfig
, to configure extractor useRoute::with_config()
instead of
fn main() { let app = App::new().resource("/index.html", |r| { r.method(http::Method::GET) .with(index) .limit(4096); // <- limit size of the payload }); }
use
fn main() { let app = App::new().resource("/index.html", |r| { r.method(http::Method::GET) .with_config(index, |cfg| { // <- register handler cfg.limit(4096); // <- limit size of the payload }) }); }
-
Route::with_async()
does not returnExtractorConfig
, to configure extractor useRoute::with_async_config()
-
Path<T>
extractor returnErrorNotFound
on failure instead ofErrorBadRequest
-
ws::Message::Close
now includes optional close reason.ws::CloseCode::Status
andws::CloseCode::Empty
have been removed. -
HttpServer::threads()
renamed toHttpServer::workers()
. -
HttpServer::start_ssl()
andHttpServer::start_tls()
deprecated. UseHttpServer::bind_ssl()
andHttpServer::bind_tls()
instead. -
HttpRequest::extensions()
returns read only reference to the request's ExtensionHttpRequest::extensions_mut()
returns mutable reference. -
Instead of
use actix_web::middleware::{ CookieSessionBackend, CookieSessionError, RequestSession, Session, SessionBackend, SessionImpl, SessionStorage};
use
actix_web::middleware::session
use actix_web::middleware::session{CookieSessionBackend, CookieSessionError, RequestSession, Session, SessionBackend, SessionImpl, SessionStorage};
-
FromRequest::from_request()
accepts mutable reference to a request -
FromRequest::Result
has to implementInto<Reply<Self>>
-
Responder::respond_to()
is generic overS
-
Use
Query
extractor instead of HttpRequest::query()`.fn index(q: Query<HashMap<String, String>>) -> Result<..> { ... }
or
let q = Query::<HashMap<String, String>>::extract(req);
-
Websocket operations are implemented as
WsWriter
trait. you need to useuse actix_web::ws::WsWriter
-
HttpResponseBuilder::body()
,.finish()
,.json()
methods returnHttpResponse
instead ofResult<HttpResponse>
-
actix_web::Method
,actix_web::StatusCode
,actix_web::Version
moved toactix_web::http
module -
actix_web::header
moved toactix_web::http::header
-
NormalizePath
moved toactix_web::http
module -
HttpServer
moved toactix_web::server
, added newactix_web::server::new()
function, shortcut foractix_web::server::HttpServer::new()
-
DefaultHeaders
middleware does not use separate builder, all builder methods moved to type itself -
StaticFiles::new()
's show_index parameter removed, useshow_files_listing()
method instead. -
CookieSessionBackendBuilder
removed, all methods moved toCookieSessionBackend
type -
actix_web::httpcodes
module is deprecated,HttpResponse::Ok()
,HttpResponse::Found()
and otherHttpResponse::XXX()
functions should be used instead -
ClientRequestBuilder::body()
returnsResult<_, actix_web::Error>
instead ofResult<_, http::Error>
-
Application
renamed to aApp
-
actix_web::Reply
,actix_web::Resource
moved toactix_web::dev