Skip to content

Commit

Permalink
fix(pact_consumer): Plugin config needs to be stored for both the req…
Browse files Browse the repository at this point in the history
…uest and response part of HTTP interactions
  • Loading branch information
rholshausen committed Aug 27, 2024
1 parent dae427a commit 941e445
Show file tree
Hide file tree
Showing 3 changed files with 95 additions and 8 deletions.
73 changes: 69 additions & 4 deletions rust/pact_consumer/src/builders/interaction_builder.rs
Original file line number Diff line number Diff line change
@@ -1,11 +1,12 @@
use std::collections::HashMap;

use maplit::hashmap;
use serde_json::{json, Value};
use tracing::debug;
use pact_models::json_utils::json_deep_merge;
use pact_models::provider_states::ProviderState;
use pact_models::sync_interaction::RequestResponseInteraction;
use pact_models::v4::synch_http::SynchronousHttp;
use serde_json::{json, Value};
use tracing::debug;

use super::request_builder::RequestBuilder;
use super::response_builder::ResponseBuilder;
Expand Down Expand Up @@ -162,13 +163,23 @@ impl InteractionBuilder {
let request_config = self.request.plugin_config();
if !request_config.is_empty() {
for (key, value) in request_config {
config.insert(key.clone(), value.interaction_configuration.clone());
config.insert(key, value.interaction_configuration);
}
}
let response_config = self.response.plugin_config();
if !response_config.is_empty() {
for (key, value) in response_config {
config.insert(key.clone(), value.interaction_configuration.clone());
let value_config = value.interaction_configuration.clone();
config.entry(key)
.and_modify(|entry| {
for (k, v) in value_config {
entry
.entry(k)
.and_modify(|e| *e = json_deep_merge(e, &v))
.or_insert(v);
}
})
.or_insert(value.interaction_configuration);
}
}
}
Expand All @@ -195,3 +206,57 @@ impl InteractionBuilder {
config
}
}

#[cfg(all(test, feature = "plugins"))]
mod plugin_tests {
use expectest::prelude::*;
use maplit::hashmap;
use pact_plugin_driver::content::PluginConfiguration;
use serde_json::json;

use crate::builders::InteractionBuilder;

#[test]
fn plugin_config_merges_config_from_request_and_response_parts() {
let mut builder = InteractionBuilder::new("test", "");
builder.request.plugin_config = hashmap!{
"plugin1".to_string() => PluginConfiguration {
interaction_configuration: hashmap!{
"other".to_string() => json!(100),
"request".to_string() => json!({
"descriptorKey": "d58838959e37498cddf51805bedf4dca",
"message": ".area_calculator.ShapeMessage"
})
},
pact_configuration: Default::default()
}
};
builder.response.plugin_config = hashmap!{
"plugin1".to_string() => PluginConfiguration {
interaction_configuration: hashmap!{
"other".to_string() => json!(200),
"response".to_string() => json!({
"descriptorKey": "d58838959e37498cddf51805bedf4dca",
"message": ".area_calculator.AreaResponse"
})
},
pact_configuration: Default::default()
}
};

let config = builder.plugin_config();
expect!(config).to(be_equal_to(hashmap!{
"plugin1".to_string() => hashmap!{
"other".to_string() => json!(200),
"request".to_string() => json!({
"descriptorKey": "d58838959e37498cddf51805bedf4dca",
"message": ".area_calculator.ShapeMessage"
}),
"response".to_string() => json!({
"descriptorKey": "d58838959e37498cddf51805bedf4dca",
"message": ".area_calculator.AreaResponse"
})
}
}));
}
}
15 changes: 13 additions & 2 deletions rust/pact_consumer/src/builders/request_builder.rs
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ struct PluginConfiguration {}
#[derive(Clone, Debug)]
pub struct RequestBuilder {
request: HttpRequest,
#[allow(dead_code)] plugin_config: HashMap<String, PluginConfiguration>,
#[allow(dead_code)] pub(crate) plugin_config: HashMap<String, PluginConfiguration>,
interaction_markup: InteractionMarkup
}

Expand Down Expand Up @@ -208,7 +208,18 @@ impl RequestBuilder {
request.generators.add_generators(generators.clone());
}
if !contents.plugin_config.is_empty() {
self.plugin_config.insert(matcher.plugin_name(), contents.plugin_config.clone());
let plugin_config = PluginConfiguration {
interaction_configuration: hashmap!{
"request".to_string() => Value::Object(
contents.plugin_config.interaction_configuration
.iter()
.map(|(k, v)| (k.clone(), v.clone()))
.collect()
)
},
pact_configuration: contents.plugin_config.pact_configuration.clone(),
};
self.plugin_config.insert(matcher.plugin_name(), plugin_config);
}
self.interaction_markup = InteractionMarkup {
markup: contents.interaction_markup.clone(),
Expand Down
15 changes: 13 additions & 2 deletions rust/pact_consumer/src/builders/response_builder.rs
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ struct PluginConfiguration {}
#[derive(Clone, Debug)]
pub struct ResponseBuilder {
response: HttpResponse,
#[allow(dead_code)] plugin_config: HashMap<String, PluginConfiguration>,
#[allow(dead_code)] pub(crate) plugin_config: HashMap<String, PluginConfiguration>,
interaction_markup: InteractionMarkup
}

Expand Down Expand Up @@ -138,7 +138,18 @@ impl ResponseBuilder {
response.generators.add_generators(generators.clone());
}
if !contents.plugin_config.is_empty() {
self.plugin_config.insert(matcher.plugin_name(), contents.plugin_config.clone());
let plugin_config = PluginConfiguration {
interaction_configuration: hashmap!{
"response".to_string() => Value::Object(
contents.plugin_config.interaction_configuration
.iter()
.map(|(k, v)| (k.clone(), v.clone()))
.collect()
)
},
pact_configuration: contents.plugin_config.pact_configuration.clone(),
};
self.plugin_config.insert(matcher.plugin_name(), plugin_config);
}
self.interaction_markup = InteractionMarkup {
markup: contents.interaction_markup.clone(),
Expand Down

0 comments on commit 941e445

Please sign in to comment.