mirror of https://github.com/fafhrd91/actix-web
Merge branch 'master' into doc/actix-web-actors
This commit is contained in:
commit
f88ef5a026
|
@ -1,8 +1,14 @@
|
|||
# Changes
|
||||
|
||||
## Unreleased - 2022-xx-xx
|
||||
### Fixed
|
||||
- Websocket parser no longer throws endless overflow errors after receiving an oversized frame. [#2790]
|
||||
|
||||
### Changed
|
||||
- Minimum supported Rust version (MSRV) is now 1.57 due to transitive `time` dependency.
|
||||
|
||||
[#2790]: https://github.com/actix/actix-web/pull/2790
|
||||
|
||||
|
||||
## 3.1.0 - 2022-06-11
|
||||
### Changed
|
||||
|
|
|
@ -17,7 +17,6 @@ impl Parser {
|
|||
fn parse_metadata(
|
||||
src: &[u8],
|
||||
server: bool,
|
||||
max_size: usize,
|
||||
) -> Result<Option<(usize, bool, OpCode, usize, Option<[u8; 4]>)>, ProtocolError> {
|
||||
let chunk_len = src.len();
|
||||
|
||||
|
@ -60,20 +59,12 @@ impl Parser {
|
|||
return Ok(None);
|
||||
}
|
||||
let len = u64::from_be_bytes(TryFrom::try_from(&src[idx..idx + 8]).unwrap());
|
||||
if len > max_size as u64 {
|
||||
return Err(ProtocolError::Overflow);
|
||||
}
|
||||
idx += 8;
|
||||
len as usize
|
||||
} else {
|
||||
len as usize
|
||||
};
|
||||
|
||||
// check for max allowed size
|
||||
if length > max_size {
|
||||
return Err(ProtocolError::Overflow);
|
||||
}
|
||||
|
||||
let mask = if server {
|
||||
if chunk_len < idx + 4 {
|
||||
return Ok(None);
|
||||
|
@ -98,11 +89,10 @@ impl Parser {
|
|||
max_size: usize,
|
||||
) -> Result<Option<(bool, OpCode, Option<BytesMut>)>, ProtocolError> {
|
||||
// try to parse ws frame metadata
|
||||
let (idx, finished, opcode, length, mask) =
|
||||
match Parser::parse_metadata(src, server, max_size)? {
|
||||
None => return Ok(None),
|
||||
Some(res) => res,
|
||||
};
|
||||
let (idx, finished, opcode, length, mask) = match Parser::parse_metadata(src, server)? {
|
||||
None => return Ok(None),
|
||||
Some(res) => res,
|
||||
};
|
||||
|
||||
// not enough data
|
||||
if src.len() < idx + length {
|
||||
|
@ -112,6 +102,13 @@ impl Parser {
|
|||
// remove prefix
|
||||
src.advance(idx);
|
||||
|
||||
// check for max allowed size
|
||||
if length > max_size {
|
||||
// drop the payload
|
||||
src.advance(length);
|
||||
return Err(ProtocolError::Overflow);
|
||||
}
|
||||
|
||||
// no need for body
|
||||
if length == 0 {
|
||||
return Ok(Some((finished, opcode, None)));
|
||||
|
@ -339,6 +336,30 @@ mod tests {
|
|||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_parse_frame_max_size_recoverability() {
|
||||
let mut buf = BytesMut::new();
|
||||
// The first text frame with length == 2, payload doesn't matter.
|
||||
buf.extend(&[0b0000_0001u8, 0b0000_0010u8, 0b0000_0000u8, 0b0000_0000u8]);
|
||||
// Next binary frame with length == 2 and payload == `[0x1111_1111u8, 0x1111_1111u8]`.
|
||||
buf.extend(&[0b0000_0010u8, 0b0000_0010u8, 0b1111_1111u8, 0b1111_1111u8]);
|
||||
|
||||
assert_eq!(buf.len(), 8);
|
||||
assert!(matches!(
|
||||
Parser::parse(&mut buf, false, 1),
|
||||
Err(ProtocolError::Overflow)
|
||||
));
|
||||
assert_eq!(buf.len(), 4);
|
||||
let frame = extract(Parser::parse(&mut buf, false, 2));
|
||||
assert!(!frame.finished);
|
||||
assert_eq!(frame.opcode, OpCode::Binary);
|
||||
assert_eq!(
|
||||
frame.payload,
|
||||
Bytes::from(vec![0b1111_1111u8, 0b1111_1111u8])
|
||||
);
|
||||
assert_eq!(buf.len(), 0);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_ping_frame() {
|
||||
let mut buf = BytesMut::new();
|
||||
|
|
|
@ -2,7 +2,10 @@
|
|||
|
||||
## Unreleased - 2022-xx-xx
|
||||
- Minimum supported Rust version (MSRV) is now 1.57 due to transitive `time` dependency.
|
||||
### Added
|
||||
- Add `ServiceRequest::{parts, request}()` getter methods. [#2786]
|
||||
|
||||
[#2786]: https://github.com/actix/actix-web/pull/2786
|
||||
|
||||
## 4.1.0 - 2022-06-11
|
||||
### Added
|
||||
|
|
|
@ -60,7 +60,7 @@ where
|
|||
/// [`HttpRequest::app_data`](crate::HttpRequest::app_data) method at runtime.
|
||||
///
|
||||
/// # [`Data<T>`]
|
||||
/// Any [`Data<T>`] type added here can utilize it's extractor implementation in handlers.
|
||||
/// Any [`Data<T>`] type added here can utilize its extractor implementation in handlers.
|
||||
/// Types not wrapped in `Data<T>` cannot use this extractor. See [its docs](Data<T>) for more
|
||||
/// about its usage and patterns.
|
||||
///
|
||||
|
|
|
@ -257,7 +257,7 @@ impl ServiceFactory<ServiceRequest> for AppRoutingFactory {
|
|||
type Future = LocalBoxFuture<'static, Result<Self::Service, Self::InitError>>;
|
||||
|
||||
fn new_service(&self, _: ()) -> Self::Future {
|
||||
// construct all services factory future with it's resource def and guards.
|
||||
// construct all services factory future with its resource def and guards.
|
||||
let factory_fut = join_all(self.services.iter().map(|(path, factory, guards)| {
|
||||
let path = path.clone();
|
||||
let guards = guards.borrow_mut().take().unwrap_or_default();
|
||||
|
|
|
@ -153,6 +153,16 @@ impl AppConfig {
|
|||
}
|
||||
|
||||
impl Default for AppConfig {
|
||||
/// Returns the default AppConfig.
|
||||
/// Note: The included socket address is "127.0.0.1".
|
||||
///
|
||||
/// 127.0.0.1: non-routable meta address that denotes an unknown, invalid or non-applicable target.
|
||||
/// If you need a service only accessed by itself, use a loopback address.
|
||||
/// A loopback address for IPv4 is any loopback address that begins with "127".
|
||||
/// Loopback addresses should be only used to test your application locally.
|
||||
/// The default configuration provides a loopback address.
|
||||
///
|
||||
/// 0.0.0.0: if configured to use this special address, the application will listen to any IP address configured on the machine.
|
||||
fn default() -> Self {
|
||||
AppConfig::new(
|
||||
false,
|
||||
|
|
|
@ -254,7 +254,7 @@ impl Guard for AllGuard {
|
|||
}
|
||||
}
|
||||
|
||||
/// Wraps a guard and inverts the outcome of it's `Guard` implementation.
|
||||
/// Wraps a guard and inverts the outcome of its `Guard` implementation.
|
||||
///
|
||||
/// # Examples
|
||||
/// The handler below will be called for any request method apart from `GET`.
|
||||
|
@ -459,7 +459,7 @@ impl Guard for HostGuard {
|
|||
return scheme == req_host_uri_scheme;
|
||||
}
|
||||
|
||||
// TODO: is the the correct behavior?
|
||||
// TODO: is this the correct behavior?
|
||||
// falls through if scheme cannot be determined
|
||||
}
|
||||
|
||||
|
|
|
@ -37,7 +37,7 @@ use crate::{
|
|||
/// Thanks to Rust's type system, Actix Web can infer the function parameter types. During the
|
||||
/// extraction step, the parameter types are described as a tuple type, [`from_request`] is run on
|
||||
/// that tuple, and the `Handler::call` implementation for that particular function arity
|
||||
/// destructures the tuple into it's component types and calls your handler function with them.
|
||||
/// destructures the tuple into its component types and calls your handler function with them.
|
||||
///
|
||||
/// In pseudo-code the process looks something like this:
|
||||
/// ```ignore
|
||||
|
|
|
@ -343,7 +343,7 @@ mod response_fut_impl {
|
|||
|
||||
// Future is only implemented for BoxBody payload type because it's the most useful for making
|
||||
// simple handlers without async blocks. Making it generic over all MessageBody types requires a
|
||||
// future impl on Response which would cause it's body field to be, undesirably, Option<B>.
|
||||
// future impl on Response which would cause its body field to be, undesirably, Option<B>.
|
||||
//
|
||||
// This impl is not particularly efficient due to the Response construction and should probably
|
||||
// not be invoked if performance is important. Prefer an async fn/block in such cases.
|
||||
|
|
|
@ -95,6 +95,18 @@ impl ServiceRequest {
|
|||
(&mut self.req, &mut self.payload)
|
||||
}
|
||||
|
||||
/// Returns immutable accessors to inner parts.
|
||||
#[inline]
|
||||
pub fn parts(&self) -> (&HttpRequest, &Payload) {
|
||||
(&self.req, &self.payload)
|
||||
}
|
||||
|
||||
/// Returns immutable accessor to inner [`HttpRequest`].
|
||||
#[inline]
|
||||
pub fn request(&self) -> &HttpRequest {
|
||||
&self.req
|
||||
}
|
||||
|
||||
/// Derives a type from this request using an [extractor](crate::FromRequest).
|
||||
///
|
||||
/// Returns the `T` extractor's `Future` type which can be `await`ed. This is particularly handy
|
||||
|
|
Loading…
Reference in New Issue