pub struct RequestBodyRedactionBuilder<T> { /* private fields */ }redaction only.Expand description
Builder for redacting sensitive values in JSON request bodies.
This builder allows you to apply redactions to a JSON request body before it’s used in the OpenAPI documentation. The original (unredacted) value is sent in the actual HTTP request.
§Key Principle
- HTTP Request: Uses the original value with real data for testing
- OpenAPI Example: Uses the redacted value with stable placeholders
This separation allows you to:
- Test with realistic data (passwords, tokens, API keys)
- Generate stable OpenAPI documentation (no dynamic values)
- Hide sensitive information from documentation
§Path Syntax
Paths are auto-detected based on their prefix:
/...→ JSON Pointer (RFC 6901) for exact paths$...→ JSONPath (RFC 9535) for wildcards
§Example
use clawspec_core::ApiClient;
use serde::Serialize;
use utoipa::ToSchema;
#[derive(Clone, Serialize, ToSchema)]
struct LoginRequest {
email: String,
password: String,
}
let mut client = ApiClient::builder().build()?;
let request = LoginRequest {
email: "user@example.com".to_string(),
password: "my-secret-password".to_string(),
};
client
.post("/auth/login")?
.json_redacted(&request)?
.redact("/password", "[REDACTED]")?
.await?; // IntoFuture - no .finish() neededImplementations§
Source§impl<T> RequestBodyRedactionBuilder<T>
impl<T> RequestBodyRedactionBuilder<T>
Sourcepub fn redact<R: Redactor>(
self,
path: &str,
redactor: R,
) -> Result<Self, ApiClientError>
pub fn redact<R: Redactor>( self, path: &str, redactor: R, ) -> Result<Self, ApiClientError>
Redacts values at the specified path using a redactor.
The path can be either JSON Pointer (RFC 6901) or JSONPath (RFC 9535). The syntax is auto-detected based on the prefix:
$...→ JSONPath (supports wildcards)/...→ JSON Pointer (exact path)
The redactor can be:
- A static value:
"replacement"orserde_json::json!(...) - A closure:
|path, val| transform(path, val)
§Arguments
path- Path expression (e.g.,/password,$.users[*].token)redactor- The redactor to apply (static value or closure)
§Errors
Returns an error if:
- The path is invalid
- The path matches no values
§Example
// Static value
client.post("/api")?
.json_redacted(&Request { token: "secret".into() })?
.redact("/token", "[REDACTED]")?
.await?; // IntoFuture - no .finish() neededSourcepub fn redact_with_options<R: Redactor>(
self,
path: &str,
redactor: R,
options: RedactOptions,
) -> Result<Self, ApiClientError>
pub fn redact_with_options<R: Redactor>( self, path: &str, redactor: R, options: RedactOptions, ) -> Result<Self, ApiClientError>
Redacts values at the specified path with configurable options.
This is like redact but allows customizing
behavior through RedactOptions.
§Arguments
path- Path expression (e.g.,/password,$.users[*].token)redactor- The redactor to applyoptions- Configuration options
§Example
use clawspec_core::RedactOptions;
// Allow empty matches for optional fields
let options = RedactOptions { allow_empty_match: true };
builder
.redact_with_options("$.optional_field", "value", options)?
.await?; // IntoFuture - no .finish() neededSourcepub fn redact_remove(self, path: &str) -> Result<Self, ApiClientError>
pub fn redact_remove(self, path: &str) -> Result<Self, ApiClientError>
Removes values at the specified path from the OpenAPI example.
This completely removes the field from the OpenAPI documentation example,
unlike setting it to null. The original value is still sent in the HTTP request.
The path can be either JSON Pointer (RFC 6901) or JSONPath (RFC 9535).
§Arguments
path- Path expression to remove
§Errors
Returns an error if:
- The path is invalid
- The path matches no values
§Example
client.post("/api")?
.json_redacted(&Request {
password: "secret".into(),
internal_id: "internal-123".into(),
})?
.redact("/password", "[REDACTED]")?
.redact_remove("/internal_id")? // Remove entirely from docs
.await?; // IntoFuture - no .finish() neededSourcepub fn redact_remove_with(
self,
path: &str,
options: RedactOptions,
) -> Result<Self, ApiClientError>
pub fn redact_remove_with( self, path: &str, options: RedactOptions, ) -> Result<Self, ApiClientError>
Removes values at the specified path with configurable options.
This is like redact_remove but allows customizing
behavior through RedactOptions.
§Arguments
path- Path expression to removeoptions- Configuration options
§Example
use clawspec_core::RedactOptions;
// Allow empty matches for optional fields
let options = RedactOptions { allow_empty_match: true };
builder
.redact_remove_with("$.optional_field", options)?
.await?; // IntoFuture - no .finish() neededSourcepub fn finish(self) -> Result<ApiCall, ApiClientError>where
T: ToSchema + 'static,
pub fn finish(self) -> Result<ApiCall, ApiClientError>where
T: ToSchema + 'static,
Finalizes the redaction and returns the configured ApiCall.
This consumes the builder and returns the ApiCall with the request body
configured. The body will contain:
- HTTP data: The original (unredacted) serialized value
- OpenAPI example: The redacted value for documentation
After calling finish(), you can .await the ApiCall to execute
the HTTP request.
§Example
let response = client
.post("/api")?
.json_redacted(&Request { password: "secret".into() })?
.redact("/password", "[REDACTED]")?
.finish()? // Returns ApiCall
.await?; // Executes the HTTP requestSourcepub fn original_value(&self) -> &T
pub fn original_value(&self) -> &T
Returns a reference to the original (unredacted) value.
This can be useful if you need to inspect the original value while building the redactions.
Sourcepub fn redacted_value(&self) -> &Value
pub fn redacted_value(&self) -> &Value
Returns a reference to the current redacted JSON value.
This can be useful if you need to inspect the redacted state while building the redactions.
Trait Implementations§
Source§impl<T> Debug for RequestBodyRedactionBuilder<T>
impl<T> Debug for RequestBodyRedactionBuilder<T>
Source§impl<T> IntoFuture for RequestBodyRedactionBuilder<T>where
T: ToSchema + 'static,
Implements IntoFuture to allow direct .await on the builder.
impl<T> IntoFuture for RequestBodyRedactionBuilder<T>where
T: ToSchema + 'static,
Implements IntoFuture to allow direct .await on the builder.
This enables a more ergonomic API where you can write:
client
.post("/users")?
.json_redacted(&user)?
.redact("/password", "[REDACTED]")?
.await?; // No need for .finish()?Instead of:
client
.post("/users")?
.json_redacted(&user)?
.redact("/password", "[REDACTED]")?
.finish()?
.await?;