diff --git a/crates/api_models/src/payments.rs b/crates/api_models/src/payments.rs index 3888d6d1d2..14bbf705ab 100644 --- a/crates/api_models/src/payments.rs +++ b/crates/api_models/src/payments.rs @@ -301,11 +301,21 @@ pub struct PaymentsRequest { /// associated with the merchant account will be used. pub profile_id: Option, + /// surcharge_details for this payment + #[schema(value_type = Option)] + pub surcharge_details: Option, + /// The type of the payment that differentiates between normal and various types of mandate payments #[schema(value_type = Option)] pub payment_type: Option, } +#[derive(Default, Debug, Clone, serde::Serialize, serde::Deserialize, Copy, ToSchema)] +pub struct RequestSurchargeDetails { + pub surcharge_amount: i64, + pub tax_amount: Option, +} + #[derive(Default, Debug, Clone, Copy)] pub struct HeaderPayload { pub payment_confirm_source: Option, diff --git a/crates/router/src/connector/trustpay.rs b/crates/router/src/connector/trustpay.rs index d059741217..fd2d369a7c 100644 --- a/crates/router/src/connector/trustpay.rs +++ b/crates/router/src/connector/trustpay.rs @@ -430,8 +430,13 @@ impl &self, req: &types::PaymentsPreProcessingRouterData, ) -> CustomResult, errors::ConnectorError> { - let amount = req.request.get_amount()?; let currency = req.request.get_currency()?; + let amount = req + .request + .surcharge_details + .as_ref() + .map(|surcharge_details| surcharge_details.final_amount) + .unwrap_or(req.request.get_amount()?); let connector_router_data = trustpay::TrustpayRouterData::try_from(( &self.get_currency_unit(), currency, @@ -542,10 +547,16 @@ impl ConnectorIntegration CustomResult, errors::ConnectorError> { + let amount = req + .request + .surcharge_details + .as_ref() + .map(|surcharge_details| surcharge_details.final_amount) + .unwrap_or(req.request.amount); let connector_router_data = trustpay::TrustpayRouterData::try_from(( &self.get_currency_unit(), req.request.currency, - req.request.amount, + amount, req, ))?; let connector_req = trustpay::TrustpayPaymentsRequest::try_from(&connector_router_data)?; diff --git a/crates/router/src/core/payments/flows/authorize_flow.rs b/crates/router/src/core/payments/flows/authorize_flow.rs index 330ef6efe1..a727914758 100644 --- a/crates/router/src/core/payments/flows/authorize_flow.rs +++ b/crates/router/src/core/payments/flows/authorize_flow.rs @@ -381,6 +381,7 @@ impl TryFrom for types::PaymentsPreProcessingData webhook_url: data.webhook_url, complete_authorize_url: data.complete_authorize_url, browser_info: data.browser_info, + surcharge_details: data.surcharge_details, }) } } diff --git a/crates/router/src/core/payments/operations/payment_response.rs b/crates/router/src/core/payments/operations/payment_response.rs index 712515b2e8..6863af7ee5 100644 --- a/crates/router/src/core/payments/operations/payment_response.rs +++ b/crates/router/src/core/payments/operations/payment_response.rs @@ -549,7 +549,7 @@ async fn payment_response_update_tracker( multiple_capture_data.update_capture(updated_capture); } - let authorized_amount = payment_data.payment_attempt.amount; + let authorized_amount = payment_data.payment_attempt.get_total_amount(); payment_attempt_update = Some(storage::PaymentAttemptUpdate::AmountToCaptureUpdate { status: multiple_capture_data.get_attempt_status(authorized_amount), diff --git a/crates/router/src/core/payments/transformers.rs b/crates/router/src/core/payments/transformers.rs index 23fbf1ea42..c34008d527 100644 --- a/crates/router/src/core/payments/transformers.rs +++ b/crates/router/src/core/payments/transformers.rs @@ -1418,6 +1418,7 @@ impl TryFrom> for types::PaymentsPreProce webhook_url, complete_authorize_url, browser_info, + surcharge_details: payment_data.surcharge_details, }) } } diff --git a/crates/router/src/lib.rs b/crates/router/src/lib.rs index 5a9e246032..5cea2a0123 100644 --- a/crates/router/src/lib.rs +++ b/crates/router/src/lib.rs @@ -6,7 +6,7 @@ pub mod compatibility; pub mod configs; pub mod connection; pub mod connector; -pub(crate) mod consts; +pub mod consts; pub mod core; pub mod cors; pub mod db; diff --git a/crates/router/src/openapi.rs b/crates/router/src/openapi.rs index 0b36c5b3a3..cb30edd5c1 100644 --- a/crates/router/src/openapi.rs +++ b/crates/router/src/openapi.rs @@ -297,6 +297,7 @@ Never share your secret api keys. Keep them guarded and secure. api_models::payments::SepaBankTransferInstructions, api_models::payments::BacsBankTransferInstructions, api_models::payments::RedirectResponse, + api_models::payments::RequestSurchargeDetails, api_models::payments::PaymentAttemptResponse, api_models::payments::CaptureResponse, api_models::payment_methods::RequiredFieldInfo, diff --git a/crates/router/src/types.rs b/crates/router/src/types.rs index 298b83faf1..2f1bce49e0 100644 --- a/crates/router/src/types.rs +++ b/crates/router/src/types.rs @@ -439,6 +439,7 @@ pub struct PaymentsPreProcessingData { pub router_return_url: Option, pub webhook_url: Option, pub complete_authorize_url: Option, + pub surcharge_details: Option, pub browser_info: Option, } diff --git a/crates/router/src/types/storage/payment_attempt.rs b/crates/router/src/types/storage/payment_attempt.rs index b1f53a285e..0b415e7165 100644 --- a/crates/router/src/types/storage/payment_attempt.rs +++ b/crates/router/src/types/storage/payment_attempt.rs @@ -17,6 +17,7 @@ pub trait PaymentAttemptExt { fn get_next_capture_id(&self) -> String; fn get_intent_status(&self, amount_captured: Option) -> enums::IntentStatus; + fn get_total_amount(&self) -> i64; } impl PaymentAttemptExt for PaymentAttempt { @@ -67,6 +68,10 @@ impl PaymentAttemptExt for PaymentAttempt { intent_status } } + + fn get_total_amount(&self) -> i64 { + self.amount + self.surcharge_amount.unwrap_or(0) + self.tax_amount.unwrap_or(0) + } } pub trait AttemptStatusExt { diff --git a/openapi/openapi_spec.json b/openapi/openapi_spec.json index d46f55efb0..34c71c1610 100644 --- a/openapi/openapi_spec.json +++ b/openapi/openapi_spec.json @@ -8900,6 +8900,14 @@ "description": "The business profile to use for this payment, if not passed the default business profile\nassociated with the merchant account will be used.", "nullable": true }, + "surcharge_details": { + "allOf": [ + { + "$ref": "#/components/schemas/RequestSurchargeDetails" + } + ], + "nullable": true + }, "payment_type": { "allOf": [ { @@ -9256,6 +9264,14 @@ "description": "The business profile to use for this payment, if not passed the default business profile\nassociated with the merchant account will be used.", "nullable": true }, + "surcharge_details": { + "allOf": [ + { + "$ref": "#/components/schemas/RequestSurchargeDetails" + } + ], + "nullable": true + }, "payment_type": { "allOf": [ { @@ -10644,6 +10660,23 @@ } } }, + "RequestSurchargeDetails": { + "type": "object", + "required": [ + "surcharge_amount" + ], + "properties": { + "surcharge_amount": { + "type": "integer", + "format": "int64" + }, + "tax_amount": { + "type": "integer", + "format": "int64", + "nullable": true + } + } + }, "RequiredFieldInfo": { "type": "object", "description": "Required fields info used while listing the payment_method_data",