pub struct RequestPlugins { /* private fields */ }Expand description
The per-request plugin execution state (DW-157): the unified chain
plus the fail-closed helpers that drive it. Constructed by
RequestPlugins::build only on routes that reference plugins;
Drop runs the on_done cleanup callback on every exit path
(early short-circuits, failures, and the natural tail alike).
Implementations§
Source§impl RequestPlugins
impl RequestPlugins
Sourcepub fn build(
lifecycle: &PluginLifecycle,
configs: &HashMap<String, PluginConfig>,
registry: &NativeRegistry,
route: &Route,
obs: &Observability,
rid: &str,
ssrf: SsrfFilter,
) -> Result<Option<Self>, PluginExit>
pub fn build( lifecycle: &PluginLifecycle, configs: &HashMap<String, PluginConfig>, registry: &NativeRegistry, route: &Route, obs: &Observability, rid: &str, ssrf: SsrfFilter, ) -> Result<Option<Self>, PluginExit>
Build the per-request chain for route. Ok(None) — with zero
allocations — when the route references no plugins (the fast
path). Err(response) is the fail-closed 500 a caller returns
immediately: a referenced plugin is Crashed/Disabled/not loaded,
a native name is missing from the registry, a native factory
errors while the chain is built, or per-request WASM
instantiation failed or did not cover every WASM plugin.
Sourcepub fn needs_request_body(&self) -> bool
pub fn needs_request_body(&self) -> bool
Whether the chain has any plugin declaring request_body
(buffers the request body when true — see the module docs).
Sourcepub fn needs_response_body(&self) -> bool
pub fn needs_response_body(&self) -> bool
Whether the chain has any plugin declaring response_body
(buffers the response body when true — see the module docs).
Sourcepub async fn request_headers_phase(
&mut self,
method: &Method,
path_and_query: &str,
headers: &mut HeaderMap,
obs: &Observability,
rid: &str,
route: &str,
) -> Result<PluginTargetRewrite, PluginExit>
pub async fn request_headers_phase( &mut self, method: &Method, path_and_query: &str, headers: &mut HeaderMap, obs: &Observability, rid: &str, route: &str, ) -> Result<PluginTargetRewrite, PluginExit>
Run the request_headers phase: after route resolution, before
authn (the documented contract — authn sees plugin-modified
headers). path_and_query is the full request target (path
including any query string). On Ok the (possibly rewritten)
header map is in place and the returned PluginTargetRewrite
carries the chain’s validated :path/:method/:authority
writes (see the module’s “Header conventions” section) for the
caller to apply at the forward build; on Err the caller
returns the response immediately. Async because a plugin may
dispatch HTTP callouts here (DW-167): the phase pauses, the
callouts are performed off-thread, and the chain resumes with
the plugin’s post-callout output.
Sourcepub async fn request_body_phase<B>(
&mut self,
req: Request<B>,
cap: u64,
obs: &Observability,
rid: &str,
route: &str,
) -> Result<Request<Full<Bytes>>, PluginExit>
pub async fn request_body_phase<B>( &mut self, req: Request<B>, cap: u64, obs: &Observability, rid: &str, route: &str, ) -> Result<Request<Full<Bytes>>, PluginExit>
Run the request_body phase: buffer the request body (capped —
over-cap answers 500 plugin_body_too_large, fail-closed), let
the chain rewrite it, and hand the action a fully-buffered
Full<Bytes> body with a rewritten Content-Length. Runs after
authz/rate-limit, before the route action (and before request
validation, which then sees the post-plugin bytes).
Sourcepub async fn response_headers_phase(
&mut self,
status: StatusCode,
headers: &mut HeaderMap,
obs: &Observability,
rid: &str,
route: &str,
) -> Result<(), PluginExit>
pub async fn response_headers_phase( &mut self, status: StatusCode, headers: &mut HeaderMap, obs: &Observability, rid: &str, route: &str, ) -> Result<(), PluginExit>
Run the response_headers phase: after the response arrives
(any action: proxy, mock, respond, redirect alike — plugins are
route-level), before masking. :status rides the map for
visibility; plugin writes to it are IGNORED — a deliberate
asymmetry with the request-side target rewrite: by the time
this phase runs the status is bound to the response’s framing
(204/304/101 carry no body, and Content-Length already
matches the upstream bytes a later phase may rewrite), so a
mid-pipeline flip would desynchronize both. A plugin that
wants to DECIDE the answer has send_http_response at the
request phases. Async for the callout pause/resume path
(DW-167), like every phase method.
Sourcepub async fn response_body_phase(
&mut self,
resp: Response<ProxyBody>,
cap: u64,
obs: &Observability,
rid: &str,
route: &str,
) -> Result<Response<ProxyBody>, PluginExit>
pub async fn response_body_phase( &mut self, resp: Response<ProxyBody>, cap: u64, obs: &Observability, rid: &str, route: &str, ) -> Result<Response<ProxyBody>, PluginExit>
Run the response_body phase: after masking, before the
operator transforms and compression. Bodiless statuses
(informational, 101, 204, 304) have nothing to inspect and pass
through untouched, exactly like masking; STREAMING bodies
(text/event-stream, or a body of unknown length — chunked or
otherwise un-framed) and CONTENT-ENCODED bodies are skipped,
documented and logged once per response: buffering an endless
SSE stream would stall the route, and an encoded body is opaque
bytes to the plugin (dwara never decompresses on this path —
compression is applied downstream, after this phase). Every
other response on a chain with a response_body plugin is
buffered up to cap (over-cap answers 500
plugin_body_too_large, fail-closed), the chain may rewrite the
bytes, and the response is rebuilt with a Full body and a
rewritten Content-Length. When masking already buffered the
body (its fail-closed path) this rides the same buffered bytes.
Trait Implementations§
Auto Trait Implementations§
impl Freeze for RequestPlugins
impl !RefUnwindSafe for RequestPlugins
impl Send for RequestPlugins
impl Sync for RequestPlugins
impl Unpin for RequestPlugins
impl !UnwindSafe for RequestPlugins
Blanket Implementations§
§impl<T> AnyExt for T
impl<T> AnyExt for T
§fn downcast_ref<T>(this: &Self) -> Option<&T>where
T: Any,
fn downcast_ref<T>(this: &Self) -> Option<&T>where
T: Any,
T behind reference§fn downcast_mut<T>(this: &mut Self) -> Option<&mut T>where
T: Any,
fn downcast_mut<T>(this: &mut Self) -> Option<&mut T>where
T: Any,
T behind mutable reference§fn downcast_rc<T>(this: Rc<Self>) -> Result<Rc<T>, Rc<Self>>where
T: Any,
fn downcast_rc<T>(this: Rc<Self>) -> Result<Rc<T>, Rc<Self>>where
T: Any,
T behind Rc pointer§fn downcast_arc<T>(this: Arc<Self>) -> Result<Arc<T>, Arc<Self>>where
T: Any,
fn downcast_arc<T>(this: Arc<Self>) -> Result<Arc<T>, Arc<Self>>where
T: Any,
T behind Arc pointer§fn downcast_box<T>(this: Box<Self>) -> Result<Box<T>, Box<Self>>where
T: Any,
fn downcast_box<T>(this: Box<Self>) -> Result<Box<T>, Box<Self>>where
T: Any,
T behind Box pointer§fn downcast_move<T>(this: Self) -> Option<T>
fn downcast_move<T>(this: Self) -> Option<T>
Self to T,
useful only in generic context as a workaround for specializationSource§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
§impl<T, X> CoerceTo<T> for Xwhere
T: CoerceFrom<X> + ?Sized,
impl<T, X> CoerceTo<T> for Xwhere
T: CoerceFrom<X> + ?Sized,
fn coerce_rc_to(self: Rc<X>) -> Rc<T>
fn coerce_box_to(self: Box<X>) -> Box<T>
fn coerce_ref_to(&self) -> &T
fn coerce_mut_to(&mut self) -> &mut T
§impl<T> Instrument for T
impl<T> Instrument for T
§fn instrument(self, span: Span) -> Instrumented<Self>
fn instrument(self, span: Span) -> Instrumented<Self>
§fn in_current_span(self) -> Instrumented<Self>
fn in_current_span(self) -> Instrumented<Self>
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self>
fn into_either(self, into_left: bool) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read more