pub struct TestConn(/* private fields */);
Expand description

A wrapper around a trillium::Conn for testing

Stability note: this may be replaced by an extension trait at some point.

Implementations§

source§

impl TestConn

source

pub fn build<M>( method: M, path: impl Into<String>, body: impl Into<Synthetic> ) -> Self
where M: TryInto<Method>, <M as TryInto<Method>>::Error: Debug,

constructs a new TestConn with the provided method, path, and body.

use trillium_testing::{prelude::*, TestConn};
let mut conn = TestConn::build("get", "/", "body");
assert_eq!(conn.method(), Method::Get);
assert_eq!(conn.path(), "/");
assert_eq!(conn.take_request_body_string(), "body");
source

pub fn with_request_header( self, header_name: impl Into<HeaderName<'static>>, header_value: impl Into<HeaderValues> ) -> Self

chainable constructor to append a request header to the TestConn

use trillium_testing::TestConn;
let conn = TestConn::build("get", "/", "body")
    .with_request_header("some-header", "value");
assert_eq!(conn.headers().get_str("some-header"), Some("value"));
source

pub fn with_request_body(self, body: impl Into<Synthetic>) -> Self

chainable constructor to replace the request body. this is useful when chaining with a trillium_testing::methods builder, as they do not provide a way to specify the body.

use trillium_testing::{methods::post, TestConn};
let mut conn = post("/").with_request_body("some body");
assert_eq!(conn.take_request_body_string(), "some body");

let mut conn = TestConn::build("post", "/", "some body")
    .with_request_body("once told me");
assert_eq!(conn.take_request_body_string(), "once told me");
source

pub fn with_peer_ip(self, ip: IpAddr) -> Self

sets the peer ip for this test conn

source

pub fn secure(self) -> Self

set the test conn to be secure

source

pub fn with_state<S>(self, state: S) -> Self
where S: Send + Sync + 'static,

set state on the test conn

source

pub fn run(self, handler: &impl Handler) -> Self

blocks on running this conn against a handler and finalizes response headers. also aliased as TestConn::on

use trillium_testing::prelude::*;

async fn handler(conn: Conn) -> Conn {
    conn.ok("hello trillium")
}

let conn = get("/").run(&handler);
assert_ok!(conn, "hello trillium", "content-length" => "14");
source

pub async fn run_async(self, handler: &impl Handler) -> Self

runs this conn against a handler and finalizes response headers.

use trillium_testing::prelude::*;

async fn handler(conn: Conn) -> Conn {
    conn.ok("hello trillium")
}

block_on(async move {
    let conn = get("/").run_async(&handler).await;
    assert_ok!(conn, "hello trillium", "content-length" => "14");
});
source

pub fn on(self, handler: &impl Handler) -> Self

blocks on running this conn against a handler and finalizes response headers. also aliased as TestConn::run.

use trillium_testing::prelude::*;

async fn handler(conn: Conn) -> Conn {
    conn.ok("hello trillium")
}

let conn = get("/").on(&handler);
assert_ok!(conn, "hello trillium", "content-length" => "14");
source

pub fn take_response_body_string(&mut self) -> Option<String>

Reads the response body to string and returns it, if set. This is used internally to [assert_body] which is the preferred interface

source

pub fn take_request_body_string(&mut self) -> String

Reads the request body to string and returns it

Methods from Deref<Target = Conn>§

pub fn status(&self) -> Option<Status>

returns the response status for this Conn, if it has been set.

use trillium_testing::prelude::*;
let mut conn = get("/").on(&());
assert!(conn.status().is_none());
conn.set_status(200);
assert_eq!(conn.status().unwrap(), Status::Ok);

pub fn set_status(&mut self, status: impl TryInto<Status>)

assigns a status to this response. see Conn::status for example usage

pub fn set_body(&mut self, body: impl Into<Body>)

Sets the response body from any impl Into<Body>. Note that this does not set the response status or halted.

use trillium_testing::prelude::*;
let mut conn = get("/").on(&());
conn.set_body("hello");
assert_eq!(conn.response_len(), Some(5));

pub fn take_response_body(&mut self) -> Option<Body>

Removes the response body from the Conn

use trillium_testing::prelude::*;
let mut conn = get("/").on(&());

conn.set_body("hello");
let mut body = conn.take_response_body().unwrap();
assert_eq!(body.len(), Some(5));
assert_eq!(conn.response_len(), None);

pub fn response_body(&self) -> Option<&Body>

Borrows the response body from the Conn

use trillium_testing::prelude::*;
let mut conn = get("/").on(&());

conn.set_body("hello");
let body = conn.response_body().unwrap();
assert_eq!(body.len(), Some(5));
assert!(body.is_static());
assert_eq!(body.static_bytes(), Some(&b"hello"[..]));

pub fn state<T>(&self) -> Option<&T>
where T: 'static,

Attempts to retrieve a &T from the state set

use trillium_testing::prelude::*;

struct Hello;
let mut conn = get("/").on(&());
assert!(conn.state::<Hello>().is_none());
conn.set_state(Hello);
assert!(conn.state::<Hello>().is_some());

pub fn state_mut<T>(&mut self) -> Option<&mut T>
where T: 'static,

Attempts to retrieve a &mut T from the state set

pub fn set_state<T>(&mut self, val: T) -> Option<T>
where T: Send + Sync + 'static,

Puts a new type into the state set. see Conn::state for an example. returns the previous instance of this type, if any

pub fn take_state<T>(&mut self) -> Option<T>
where T: Send + Sync + 'static,

Removes a type from the state set and returns it, if present

pub fn mut_state_or_insert_with<T, F>(&mut self, default: F) -> &mut T
where T: Send + Sync + 'static, F: FnOnce() -> T,

Either returns the current &mut T from the state set, or inserts a new one with the provided default function and returns a mutable reference to it

pub async fn request_body(&mut self) -> ReceivedBody<'_, BoxedTransport>

Returns a [ReceivedBody] that references this Conn. The Conn retains all data and holds the singular transport, but the [ReceivedBody] provides an interface to read body content.

See also: Conn::request_body_string for a convenience function when the content is expected to be utf8.

Examples
use trillium_testing::prelude::*;
let mut conn = get("/").with_request_body("request body").on(&());

let request_body = conn.request_body().await;
assert_eq!(request_body.content_length(), Some(12));
assert_eq!(request_body.read_string().await.unwrap(), "request body");

pub async fn request_body_string(&mut self) -> Result<String, Error>

Convenience function to read the content of a request body as a String.

Errors

This will return an error variant if either there is an IO failure on the underlying transport or if the body content is not a utf8 string.

Examples
use trillium_testing::prelude::*;
let mut conn = get("/").with_request_body("request body").on(&());

assert_eq!(conn.request_body_string().await.unwrap(), "request body");

pub fn response_len(&self) -> Option<u64>

if there is a response body for this conn and it has a known fixed length, it is returned from this function

use trillium_testing::prelude::*;
let mut conn = get("/").on(&|conn: trillium::Conn| async move {
    conn.with_body("hello")
});

assert_eq!(conn.response_len(), Some(5));

pub fn method(&self) -> Method

returns the request method for this conn.

use trillium_testing::prelude::*;
let mut conn = get("/").on(&());

assert_eq!(conn.method(), Method::Get);

pub fn headers(&self) -> &Headers

borrows the request headers

this is aliased as Conn::request_headers

pub fn headers_mut(&mut self) -> &mut Headers

mutably borrows response headers

this is aliased as Conn::response_headers_mut

pub fn response_headers(&self) -> &Headers

borrow the response headers

pub fn response_headers_mut(&mut self) -> &mut Headers

mutably borrow the response headers

this is aliased as Conn::headers_mut

pub fn request_headers(&self) -> &Headers

borrow the request headers

pub fn request_headers_mut(&mut self) -> &mut Headers

mutably borrow request headers

pub fn path(&self) -> &str

returns the path for this request. note that this may not represent the entire http request path if running nested routers.

pub fn querystring(&self) -> &str

returns query part of the request path

use trillium_testing::prelude::*;
let conn = get("/a/b?c&d=e").on(&());
assert_eq!(conn.querystring(), "c&d=e");

let conn = get("/a/b").on(&());
assert_eq!(conn.querystring(), "");
Parsing

Trillium does not include a querystring parsing library, as there is no universal standard for querystring encodings of arrays, but several library options exist, inluding:

pub fn set_halted(&mut self, halted: bool)

sets the halted attribute of this conn. see Conn::halt.

use trillium_testing::prelude::*;
let mut conn = get("/").on(&());
assert!(!conn.is_halted());
conn.set_halted(true);
assert!(conn.is_halted());

pub fn is_halted(&self) -> bool

retrieves the halted state of this conn. see Conn::halt.

pub fn is_secure(&self) -> bool

predicate function to indicate whether the connection is secure. note that this does not necessarily indicate that the transport itself is secure, as it may indicate that trillium_http is behind a trusted reverse proxy that has terminated tls and provided appropriate headers to indicate this.

pub fn start_time(&self) -> Instant

The [Instant] that the first header bytes for this conn were received, before any processing or parsing has been performed.

pub fn inner(&self) -> &Conn<BoxedTransport>

returns an immutable reference to the inner [trillium_http::Conn]. please open an issue if you need to do this in application code.

stability note: hopefully this can go away at some point, but for now is an escape hatch in case trillium_http::Conn presents interfaces that cannot be reached otherwise.

pub fn inner_mut(&mut self) -> &mut Conn<BoxedTransport>

returns a mutable reference to the inner [trillium_http::Conn]. please open an issue if you need to do this in application code.

stability note: hopefully this can go away at some point, but for now is an escape hatch in case trillium_http::Conn presents interfaces that cannot be reached otherwise.

pub fn peer_ip(&self) -> Option<IpAddr>

retrieves the remote ip address for this conn, if available.

pub fn set_peer_ip(&mut self, peer_ip: Option<IpAddr>)

sets the remote ip address for this conn.

pub fn push_path(&mut self, path: String)

for router implementations. pushes a route segment onto the path

pub fn pop_path(&mut self)

for router implementations. removes a route segment onto the path

Trait Implementations§

source§

impl Debug for TestConn

source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
source§

impl Deref for TestConn

§

type Target = Conn

The resulting type after dereferencing.
source§

fn deref(&self) -> &Self::Target

Dereferences the value.
source§

impl DerefMut for TestConn

source§

fn deref_mut(&mut self) -> &mut Self::Target

Mutably dereferences the value.
source§

impl From<Conn> for TestConn

source§

fn from(conn: Conn) -> Self

Converts to this type from the input type.
source§

impl From<TestConn> for Conn

source§

fn from(tc: TestConn) -> Self

Converts to this type from the input type.
source§

impl From<TestConn> for Conn<Synthetic>

source§

fn from(tc: TestConn) -> Self

Converts to this type from the input type.

Auto Trait Implementations§

Blanket Implementations§

source§

impl<T> Any for T
where T: 'static + ?Sized,

source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
source§

impl<T> Borrow<T> for T
where T: ?Sized,

source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
source§

impl<T> From<T> for T

source§

fn from(t: T) -> T

Returns the argument unchanged.

§

impl<T> Instrument for T

§

fn instrument(self, span: Span) -> Instrumented<Self>

Instruments this type with the provided [Span], returning an Instrumented wrapper. Read more
§

fn in_current_span(self) -> Instrumented<Self>

Instruments this type with the current Span, returning an Instrumented wrapper. Read more
source§

impl<T, U> Into<U> for T
where U: From<T>,

source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

§

type Error = Infallible

The type returned in the event of a conversion error.
source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
§

impl<V, T> VZip<V> for T
where V: MultiLane<T>,

§

fn vzip(self) -> V

§

impl<T> WithSubscriber for T

§

fn with_subscriber<S>(self, subscriber: S) -> WithDispatch<Self>
where S: Into<Dispatch>,

Attaches the provided Subscriber to this type, returning a [WithDispatch] wrapper. Read more
§

fn with_current_subscriber(self) -> WithDispatch<Self>

Attaches the current default Subscriber to this type, returning a [WithDispatch] wrapper. Read more