refactor(business_profile): use concrete types for JSON fields (#5531)

This commit is contained in:
Sanchith Hegde
2024-08-07 13:57:35 +05:30
committed by GitHub
parent 52cada015e
commit a8ba21c1d1
18 changed files with 751 additions and 606 deletions

View File

@ -48,7 +48,7 @@ use crate::{
types::{self as domain_types, AsyncLift},
},
storage::{self, enums::MerchantStorageScheme},
transformers::{ForeignTryFrom, ForeignTryInto},
transformers::{ForeignInto, ForeignTryFrom, ForeignTryInto},
},
utils,
};
@ -289,11 +289,7 @@ impl MerchantAccountCreateBridge for api::MerchantAccountCreate {
},
)?;
let webhook_details = self.get_webhook_details_as_value().change_context(
errors::ApiErrorResponse::InvalidDataValue {
field_name: "webhook details",
},
)?;
let webhook_details = self.webhook_details.clone().map(ForeignInto::foreign_into);
let pm_collect_link_config = self.get_pm_link_config_as_value().change_context(
errors::ApiErrorResponse::InvalidDataValue {
@ -871,11 +867,7 @@ impl MerchantAccountUpdateBridge for api::MerchantAccountUpdate {
},
)?;
let webhook_details = self.get_webhook_details_as_value().change_context(
errors::ApiErrorResponse::InvalidDataValue {
field_name: "webhook_details",
},
)?;
let webhook_details = self.webhook_details.map(ForeignInto::foreign_into);
let parent_merchant_id = get_parent_merchant(
state,
@ -3375,17 +3367,7 @@ pub async fn update_business_profile(
helpers::validate_intent_fulfillment_expiry(intent_fulfillment_expiry.to_owned())?;
}
let webhook_details = request
.webhook_details
.as_ref()
.map(|webhook_details| {
webhook_details.encode_to_value().change_context(
errors::ApiErrorResponse::InvalidDataValue {
field_name: "webhook details",
},
)
})
.transpose()?;
let webhook_details = request.webhook_details.map(ForeignInto::foreign_into);
if let Some(ref routing_algorithm) = request.routing_algorithm {
let _: api_models::routing::RoutingAlgorithm = routing_algorithm
@ -3399,13 +3381,8 @@ pub async fn update_business_profile(
let payment_link_config = request
.payment_link_config
.as_ref()
.map(|payment_link_conf| match payment_link_conf.validate() {
Ok(_) => payment_link_conf.encode_to_value().change_context(
errors::ApiErrorResponse::InvalidDataValue {
field_name: "payment_link_config",
},
),
Ok(_) => Ok(payment_link_conf.foreign_into()),
Err(e) => Err(report!(errors::ApiErrorResponse::InvalidRequestData {
message: e.to_string()
})),
@ -3434,56 +3411,48 @@ pub async fn update_business_profile(
let payout_link_config = request
.payout_link_config
.as_ref()
.map(|payout_conf| match payout_conf.config.validate() {
Ok(_) => payout_conf.encode_to_value().change_context(
errors::ApiErrorResponse::InvalidDataValue {
field_name: "payout_link_config",
},
),
Ok(_) => Ok(payout_conf.foreign_into()),
Err(e) => Err(report!(errors::ApiErrorResponse::InvalidRequestData {
message: e.to_string()
})),
})
.transpose()?;
let business_profile_update = storage::business_profile::BusinessProfileUpdate::Update {
profile_name: request.profile_name,
return_url: request.return_url.map(|return_url| return_url.to_string()),
enable_payment_response_hash: request.enable_payment_response_hash,
payment_response_hash_key: request.payment_response_hash_key,
redirect_to_merchant_with_http_post: request.redirect_to_merchant_with_http_post,
webhook_details,
metadata: request.metadata,
routing_algorithm: request.routing_algorithm,
intent_fulfillment_time: request.intent_fulfillment_time.map(i64::from),
frm_routing_algorithm: request.frm_routing_algorithm,
#[cfg(feature = "payouts")]
payout_routing_algorithm: request.payout_routing_algorithm,
#[cfg(not(feature = "payouts"))]
payout_routing_algorithm: None,
is_recon_enabled: None,
applepay_verified_domains: request.applepay_verified_domains,
payment_link_config,
session_expiry: request.session_expiry.map(i64::from),
authentication_connector_details: request
.authentication_connector_details
.as_ref()
.map(Encode::encode_to_value)
.transpose()
.change_context(errors::ApiErrorResponse::InvalidDataValue {
field_name: "authentication_connector_details",
})?,
payout_link_config,
extended_card_info_config,
use_billing_as_payment_method_billing: request.use_billing_as_payment_method_billing,
collect_shipping_details_from_wallet_connector: request
.collect_shipping_details_from_wallet_connector,
collect_billing_details_from_wallet_connector: request
.collect_billing_details_from_wallet_connector,
is_connector_agnostic_mit_enabled: request.is_connector_agnostic_mit_enabled,
outgoing_webhook_custom_http_headers: outgoing_webhook_custom_http_headers.map(Into::into),
};
let business_profile_update =
storage::BusinessProfileUpdate::Update(Box::new(storage::BusinessProfileGeneralUpdate {
profile_name: request.profile_name,
return_url: request.return_url.map(|return_url| return_url.to_string()),
enable_payment_response_hash: request.enable_payment_response_hash,
payment_response_hash_key: request.payment_response_hash_key,
redirect_to_merchant_with_http_post: request.redirect_to_merchant_with_http_post,
webhook_details,
metadata: request.metadata,
routing_algorithm: request.routing_algorithm,
intent_fulfillment_time: request.intent_fulfillment_time.map(i64::from),
frm_routing_algorithm: request.frm_routing_algorithm,
#[cfg(feature = "payouts")]
payout_routing_algorithm: request.payout_routing_algorithm,
#[cfg(not(feature = "payouts"))]
payout_routing_algorithm: None,
is_recon_enabled: None,
applepay_verified_domains: request.applepay_verified_domains,
payment_link_config,
session_expiry: request.session_expiry.map(i64::from),
authentication_connector_details: request
.authentication_connector_details
.map(ForeignInto::foreign_into),
payout_link_config,
extended_card_info_config,
use_billing_as_payment_method_billing: request.use_billing_as_payment_method_billing,
collect_shipping_details_from_wallet_connector: request
.collect_shipping_details_from_wallet_connector,
collect_billing_details_from_wallet_connector: request
.collect_billing_details_from_wallet_connector,
is_connector_agnostic_mit_enabled: request.is_connector_agnostic_mit_enabled,
outgoing_webhook_custom_http_headers: outgoing_webhook_custom_http_headers
.map(Into::into),
}));
let updated_business_profile = db
.update_business_profile_by_profile_id(business_profile, business_profile_update)

View File

@ -1,4 +1,3 @@
use common_utils::ext_traits::ValueExt;
use error_stack::ResultExt;
use hyperswitch_domain_models::router_data_v2::ExternalAuthenticationFlowData;
@ -269,24 +268,17 @@ pub async fn get_authentication_connector_data(
key_store: &domain::MerchantKeyStore,
business_profile: &storage::BusinessProfile,
) -> RouterResult<(
api_models::enums::AuthenticationConnectors,
common_enums::AuthenticationConnectors,
payments::helpers::MerchantConnectorAccountType,
)> {
let authentication_details: api_models::admin::AuthenticationConnectorDetails =
business_profile
.authentication_connector_details
.clone()
.get_required_value("authentication_details")
.change_context(errors::ApiErrorResponse::UnprocessableEntity {
message: "authentication_connector_details is not available in business profile"
.into(),
})
.attach_printable("authentication_connector_details not configured by the merchant")?
.parse_value("AuthenticationConnectorDetails")
.change_context(errors::ApiErrorResponse::InternalServerError)
.attach_printable(
"Error while parsing authentication_connector_details from business_profile",
)?;
let authentication_details = business_profile
.authentication_connector_details
.clone()
.get_required_value("authentication_details")
.change_context(errors::ApiErrorResponse::UnprocessableEntity {
message: "authentication_connector_details is not available in business profile".into(),
})
.attach_printable("authentication_connector_details not configured by the merchant")?;
let authentication_connector = authentication_details
.authentication_connectors
.first()

View File

@ -526,39 +526,33 @@ pub fn extract_payment_link_config(
pub fn get_payment_link_config_based_on_priority(
payment_create_link_config: Option<api_models::payments::PaymentCreatePaymentLinkConfig>,
business_link_config: Option<serde_json::Value>,
business_link_config: Option<diesel_models::business_profile::BusinessPaymentLinkConfig>,
merchant_name: String,
default_domain_name: String,
payment_link_config_id: Option<String>,
) -> Result<(PaymentLinkConfig, String), error_stack::Report<errors::ApiErrorResponse>> {
let (domain_name, business_theme_configs, allowed_domains) =
if let Some(business_config) = business_link_config {
let extracted_value: api_models::admin::BusinessPaymentLinkConfig = business_config
.parse_value("BusinessPaymentLinkConfig")
.change_context(errors::ApiErrorResponse::InvalidDataValue {
field_name: "payment_link_config",
})
.attach_printable("Invalid payment_link_config given in business config")?;
logger::info!(
"domain name set to custom domain https://{:?}",
extracted_value.domain_name
business_config.domain_name
);
(
extracted_value
business_config
.domain_name
.clone()
.map(|d_name| format!("https://{}", d_name))
.unwrap_or_else(|| default_domain_name.clone()),
payment_link_config_id
.and_then(|id| {
extracted_value
business_config
.business_specific_configs
.as_ref()
.and_then(|specific_configs| specific_configs.get(&id).cloned())
})
.or(extracted_value.default_config),
extracted_value.allowed_domains,
.or(business_config.default_config),
business_config.allowed_domains,
)
} else {
(default_domain_name, None, None)

View File

@ -4156,19 +4156,11 @@ pub async fn payment_external_authentication(
id: profile_id.to_string(),
})?;
let authentication_details: api_models::admin::AuthenticationConnectorDetails =
business_profile
.authentication_connector_details
.clone()
.get_required_value("authentication_connector_details")
.attach_printable("authentication_connector_details not configured by the merchant")?
.parse_value("AuthenticationConnectorDetails")
.change_context(errors::ApiErrorResponse::UnprocessableEntity {
message: "Invalid data format found for authentication_connector_details".into(),
})
.attach_printable(
"Error while parsing authentication_connector_details from business_profile",
)?;
let authentication_details = business_profile
.authentication_connector_details
.clone()
.get_required_value("authentication_connector_details")
.attach_printable("authentication_connector_details not configured by the merchant")?;
let authentication_response = Box::pin(authentication_core::perform_authentication(
&state,

View File

@ -5,7 +5,7 @@ pub mod retry;
pub mod validator;
use std::vec::IntoIter;
use api_models::{self, admin, enums as api_enums, payouts::PayoutLinkResponse};
use api_models::{self, enums as api_enums, payouts::PayoutLinkResponse};
#[cfg(feature = "payout_retry")]
use common_enums::PayoutRetryType;
use common_utils::{
@ -2505,18 +2505,7 @@ pub async fn create_payout_link(
// Fetch all configs
let default_config = &state.conf.generic_link.payout_link;
let profile_config = business_profile
.payout_link_config
.as_ref()
.map(|config| {
config
.clone()
.parse_value::<admin::BusinessPayoutLinkConfig>("BusinessPayoutLinkConfig")
})
.transpose()
.change_context(errors::ApiErrorResponse::InvalidDataValue {
field_name: "payout_link_config in business_profile",
})?;
let profile_config = &business_profile.payout_link_config;
let profile_ui_config = profile_config.as_ref().map(|c| c.config.ui_config.clone());
let ui_config = payout_link_config_req
.as_ref()

View File

@ -536,17 +536,12 @@ pub(crate) async fn add_outgoing_webhook_retry_task_to_process_tracker(
fn get_webhook_url_from_business_profile(
business_profile: &diesel_models::business_profile::BusinessProfile,
) -> CustomResult<String, errors::WebhooksFlowError> {
let webhook_details_json = business_profile
let webhook_details = business_profile
.webhook_details
.clone()
.get_required_value("webhook_details")
.change_context(errors::WebhooksFlowError::MerchantWebhookDetailsNotFound)?;
let webhook_details: api::WebhookDetails =
webhook_details_json
.parse_value("WebhookDetails")
.change_context(errors::WebhooksFlowError::MerchantWebhookDetailsNotFound)?;
webhook_details
.webhook_url
.get_required_value("webhook_url")