cache: add graphql query response caching

This commit is contained in:
a.tolmachev
2026-05-04 09:04:27 +00:00
parent 6cec445b4f
commit b2c5e28cba
9 changed files with 271 additions and 12 deletions
+80 -1
View File
@@ -5063,9 +5063,12 @@ fn validate_response_cache_policy(
match target {
Target::Rest(rest_target) if rest_target.method == crank_core::HttpMethod::Get => {}
Target::Graphql(graphql_target)
if graphql_target.operation_type == crank_core::GraphqlOperationType::Query => {}
_ => {
return Err(ApiError::validation_with_context(
"response cache is supported only for REST GET operations".to_owned(),
"response cache is supported only for REST GET and GraphQL query operations"
.to_owned(),
json!({
"field": "execution_config.response_cache",
}),
@@ -5085,6 +5088,82 @@ fn validate_response_cache_policy(
Ok(())
}
#[cfg(test)]
mod tests {
use std::collections::BTreeMap;
use crank_core::{
ExecutionConfig, GraphqlOperationType, GraphqlTarget, HttpMethod, ResponseCachePolicy,
RestTarget, Target,
};
use super::validate_response_cache_policy;
fn cacheable_execution_config() -> ExecutionConfig {
ExecutionConfig {
timeout_ms: 1_000,
retry_policy: None,
response_cache: Some(ResponseCachePolicy { ttl_ms: 5_000 }),
auth_profile_ref: None,
headers: BTreeMap::new(),
protocol_options: None,
streaming: None,
}
}
#[test]
fn accepts_response_cache_for_graphql_query() {
let target = Target::Graphql(GraphqlTarget {
endpoint: "http://example.invalid/graphql".to_owned(),
operation_type: GraphqlOperationType::Query,
operation_name: "LookupLead".to_owned(),
query_template:
"query LookupLead($email: String!) { lookupLead(email: $email) { id } }".to_owned(),
response_path: "$.response.body.data.lookupLead".to_owned(),
});
let result = validate_response_cache_policy(&target, &cacheable_execution_config());
assert!(result.is_ok());
}
#[test]
fn rejects_response_cache_for_graphql_mutation() {
let target = Target::Graphql(GraphqlTarget {
endpoint: "http://example.invalid/graphql".to_owned(),
operation_type: GraphqlOperationType::Mutation,
operation_name: "CreateLead".to_owned(),
query_template:
"mutation CreateLead($email: String!) { createLead(email: $email) { id } }"
.to_owned(),
response_path: "$.response.body.data.createLead".to_owned(),
});
let error =
validate_response_cache_policy(&target, &cacheable_execution_config()).unwrap_err();
assert!(matches!(error, crate::error::ApiError::Validation { .. }));
assert_eq!(
error.to_string(),
"response cache is supported only for REST GET and GraphQL query operations"
);
}
#[test]
fn accepts_response_cache_for_rest_get() {
let target = Target::Rest(RestTarget {
base_url: "http://example.invalid".to_owned(),
method: HttpMethod::Get,
path_template: "/catalog".to_owned(),
static_headers: BTreeMap::new(),
});
let result = validate_response_cache_policy(&target, &cacheable_execution_config());
assert!(result.is_ok());
}
}
fn enrich_operation_summary(
summary: OperationSummary,
usage_summary: OperationUsageSummaryView,