mirror of
https://github.com/juspay/hyperswitch.git
synced 2025-10-30 01:27:31 +08:00
feat(subscription): Add support to estimate for a subscription in chargebee (#9336)
Co-authored-by: Spriti Aneja <spriti.aneja@juspay.in> Co-authored-by: hyperswitch-bot[bot] <148525504+hyperswitch-bot[bot]@users.noreply.github.com> Co-authored-by: spritianeja03 <146620839+spritianeja03@users.noreply.github.com>
This commit is contained in:
@ -22,14 +22,17 @@ use hyperswitch_domain_models::{
|
|||||||
payments::{Authorize, Capture, PSync, PaymentMethodToken, Session, SetupMandate, Void},
|
payments::{Authorize, Capture, PSync, PaymentMethodToken, Session, SetupMandate, Void},
|
||||||
refunds::{Execute, RSync},
|
refunds::{Execute, RSync},
|
||||||
revenue_recovery::InvoiceRecordBack,
|
revenue_recovery::InvoiceRecordBack,
|
||||||
subscriptions::{GetSubscriptionPlanPrices, GetSubscriptionPlans, SubscriptionCreate},
|
subscriptions::{
|
||||||
|
GetSubscriptionEstimate, GetSubscriptionPlanPrices, GetSubscriptionPlans,
|
||||||
|
SubscriptionCreate,
|
||||||
|
},
|
||||||
CreateConnectorCustomer,
|
CreateConnectorCustomer,
|
||||||
},
|
},
|
||||||
router_request_types::{
|
router_request_types::{
|
||||||
revenue_recovery::InvoiceRecordBackRequest,
|
revenue_recovery::InvoiceRecordBackRequest,
|
||||||
subscriptions::{
|
subscriptions::{
|
||||||
GetSubscriptionPlanPricesRequest, GetSubscriptionPlansRequest,
|
GetSubscriptionEstimateRequest, GetSubscriptionPlanPricesRequest,
|
||||||
SubscriptionCreateRequest,
|
GetSubscriptionPlansRequest, SubscriptionCreateRequest,
|
||||||
},
|
},
|
||||||
AccessTokenRequestData, ConnectorCustomerData, PaymentMethodTokenizationData,
|
AccessTokenRequestData, ConnectorCustomerData, PaymentMethodTokenizationData,
|
||||||
PaymentsAuthorizeData, PaymentsCancelData, PaymentsCaptureData, PaymentsSessionData,
|
PaymentsAuthorizeData, PaymentsCancelData, PaymentsCaptureData, PaymentsSessionData,
|
||||||
@ -38,15 +41,16 @@ use hyperswitch_domain_models::{
|
|||||||
router_response_types::{
|
router_response_types::{
|
||||||
revenue_recovery::InvoiceRecordBackResponse,
|
revenue_recovery::InvoiceRecordBackResponse,
|
||||||
subscriptions::{
|
subscriptions::{
|
||||||
GetSubscriptionPlanPricesResponse, GetSubscriptionPlansResponse,
|
GetSubscriptionEstimateResponse, GetSubscriptionPlanPricesResponse,
|
||||||
SubscriptionCreateResponse,
|
GetSubscriptionPlansResponse, SubscriptionCreateResponse,
|
||||||
},
|
},
|
||||||
ConnectorInfo, PaymentsResponseData, RefundsResponseData,
|
ConnectorInfo, PaymentsResponseData, RefundsResponseData,
|
||||||
},
|
},
|
||||||
types::{
|
types::{
|
||||||
ConnectorCustomerRouterData, GetSubscriptionPlanPricesRouterData,
|
ConnectorCustomerRouterData, GetSubscriptionEstimateRouterData,
|
||||||
GetSubscriptionPlansRouterData, InvoiceRecordBackRouterData, PaymentsAuthorizeRouterData,
|
GetSubscriptionPlanPricesRouterData, GetSubscriptionPlansRouterData,
|
||||||
PaymentsCaptureRouterData, PaymentsSyncRouterData, RefundSyncRouterData, RefundsRouterData,
|
InvoiceRecordBackRouterData, PaymentsAuthorizeRouterData, PaymentsCaptureRouterData,
|
||||||
|
PaymentsSyncRouterData, RefundSyncRouterData, RefundsRouterData,
|
||||||
SubscriptionCreateRouterData,
|
SubscriptionCreateRouterData,
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
@ -1139,6 +1143,94 @@ impl
|
|||||||
// TODO: implement functions when support enabled
|
// TODO: implement functions when support enabled
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl api::subscriptions::GetSubscriptionEstimateFlow for Chargebee {}
|
||||||
|
|
||||||
|
impl
|
||||||
|
ConnectorIntegration<
|
||||||
|
GetSubscriptionEstimate,
|
||||||
|
GetSubscriptionEstimateRequest,
|
||||||
|
GetSubscriptionEstimateResponse,
|
||||||
|
> for Chargebee
|
||||||
|
{
|
||||||
|
fn get_headers(
|
||||||
|
&self,
|
||||||
|
req: &GetSubscriptionEstimateRouterData,
|
||||||
|
connectors: &Connectors,
|
||||||
|
) -> CustomResult<Vec<(String, masking::Maskable<String>)>, errors::ConnectorError> {
|
||||||
|
self.build_headers(req, connectors)
|
||||||
|
}
|
||||||
|
fn get_url(
|
||||||
|
&self,
|
||||||
|
req: &GetSubscriptionEstimateRouterData,
|
||||||
|
connectors: &Connectors,
|
||||||
|
) -> CustomResult<String, errors::ConnectorError> {
|
||||||
|
let metadata: chargebee::ChargebeeMetadata =
|
||||||
|
utils::to_connector_meta_from_secret(req.connector_meta_data.clone())?;
|
||||||
|
let url = self
|
||||||
|
.base_url(connectors)
|
||||||
|
.to_string()
|
||||||
|
.replace("{{merchant_endpoint_prefix}}", metadata.site.peek());
|
||||||
|
Ok(format!("{url}v2/estimates/create_subscription_for_items"))
|
||||||
|
}
|
||||||
|
fn get_content_type(&self) -> &'static str {
|
||||||
|
self.common_get_content_type()
|
||||||
|
}
|
||||||
|
fn get_request_body(
|
||||||
|
&self,
|
||||||
|
req: &GetSubscriptionEstimateRouterData,
|
||||||
|
_connectors: &Connectors,
|
||||||
|
) -> CustomResult<RequestContent, errors::ConnectorError> {
|
||||||
|
let connector_req = chargebee::ChargebeeSubscriptionEstimateRequest::try_from(req)?;
|
||||||
|
Ok(RequestContent::FormUrlEncoded(Box::new(connector_req)))
|
||||||
|
}
|
||||||
|
fn build_request(
|
||||||
|
&self,
|
||||||
|
req: &GetSubscriptionEstimateRouterData,
|
||||||
|
connectors: &Connectors,
|
||||||
|
) -> CustomResult<Option<Request>, errors::ConnectorError> {
|
||||||
|
Ok(Some(
|
||||||
|
RequestBuilder::new()
|
||||||
|
.method(Method::Post)
|
||||||
|
.url(&types::GetSubscriptionEstimateType::get_url(
|
||||||
|
self, req, connectors,
|
||||||
|
)?)
|
||||||
|
.attach_default_headers()
|
||||||
|
.headers(types::GetSubscriptionEstimateType::get_headers(
|
||||||
|
self, req, connectors,
|
||||||
|
)?)
|
||||||
|
.set_body(types::GetSubscriptionEstimateType::get_request_body(
|
||||||
|
self, req, connectors,
|
||||||
|
)?)
|
||||||
|
.build(),
|
||||||
|
))
|
||||||
|
}
|
||||||
|
fn handle_response(
|
||||||
|
&self,
|
||||||
|
data: &GetSubscriptionEstimateRouterData,
|
||||||
|
event_builder: Option<&mut ConnectorEvent>,
|
||||||
|
res: Response,
|
||||||
|
) -> CustomResult<GetSubscriptionEstimateRouterData, errors::ConnectorError> {
|
||||||
|
let response: chargebee::SubscriptionEstimateResponse = res
|
||||||
|
.response
|
||||||
|
.parse_struct("chargebee SubscriptionEstimateResponse")
|
||||||
|
.change_context(errors::ConnectorError::ResponseDeserializationFailed)?;
|
||||||
|
event_builder.map(|i| i.set_response_body(&response));
|
||||||
|
router_env::logger::info!(connector_response=?response);
|
||||||
|
RouterData::try_from(ResponseRouterData {
|
||||||
|
response,
|
||||||
|
data: data.clone(),
|
||||||
|
http_code: res.status_code,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
fn get_error_response(
|
||||||
|
&self,
|
||||||
|
res: Response,
|
||||||
|
event_builder: Option<&mut ConnectorEvent>,
|
||||||
|
) -> CustomResult<ErrorResponse, errors::ConnectorError> {
|
||||||
|
self.build_error_response(res, event_builder)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#[async_trait::async_trait]
|
#[async_trait::async_trait]
|
||||||
impl webhooks::IncomingWebhook for Chargebee {
|
impl webhooks::IncomingWebhook for Chargebee {
|
||||||
fn get_webhook_source_verification_signature(
|
fn get_webhook_source_verification_signature(
|
||||||
|
|||||||
@ -28,12 +28,16 @@ use hyperswitch_domain_models::{
|
|||||||
router_response_types::{
|
router_response_types::{
|
||||||
revenue_recovery::InvoiceRecordBackResponse,
|
revenue_recovery::InvoiceRecordBackResponse,
|
||||||
subscriptions::{
|
subscriptions::{
|
||||||
self, GetSubscriptionPlanPricesResponse, GetSubscriptionPlansResponse,
|
self, GetSubscriptionEstimateResponse, GetSubscriptionPlanPricesResponse,
|
||||||
SubscriptionCreateResponse, SubscriptionStatus,
|
GetSubscriptionPlansResponse, SubscriptionCreateResponse, SubscriptionLineItem,
|
||||||
|
SubscriptionStatus,
|
||||||
},
|
},
|
||||||
ConnectorCustomerResponseData, PaymentsResponseData, RefundsResponseData,
|
ConnectorCustomerResponseData, PaymentsResponseData, RefundsResponseData,
|
||||||
},
|
},
|
||||||
types::{InvoiceRecordBackRouterData, PaymentsAuthorizeRouterData, RefundsRouterData},
|
types::{
|
||||||
|
GetSubscriptionEstimateRouterData, InvoiceRecordBackRouterData,
|
||||||
|
PaymentsAuthorizeRouterData, RefundsRouterData,
|
||||||
|
},
|
||||||
};
|
};
|
||||||
use hyperswitch_interfaces::errors;
|
use hyperswitch_interfaces::errors;
|
||||||
use masking::{ExposeInterface, Secret};
|
use masking::{ExposeInterface, Secret};
|
||||||
@ -959,6 +963,50 @@ pub struct ChargebeeItem {
|
|||||||
pub description: Option<String>,
|
pub description: Option<String>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl<F, T>
|
||||||
|
TryFrom<ResponseRouterData<F, SubscriptionEstimateResponse, T, GetSubscriptionEstimateResponse>>
|
||||||
|
for RouterData<F, T, GetSubscriptionEstimateResponse>
|
||||||
|
{
|
||||||
|
type Error = error_stack::Report<errors::ConnectorError>;
|
||||||
|
fn try_from(
|
||||||
|
item: ResponseRouterData<
|
||||||
|
F,
|
||||||
|
SubscriptionEstimateResponse,
|
||||||
|
T,
|
||||||
|
GetSubscriptionEstimateResponse,
|
||||||
|
>,
|
||||||
|
) -> Result<Self, Self::Error> {
|
||||||
|
let estimate = item.response.estimate;
|
||||||
|
Ok(Self {
|
||||||
|
response: Ok(GetSubscriptionEstimateResponse {
|
||||||
|
sub_total: estimate.invoice_estimate.sub_total,
|
||||||
|
total: estimate.invoice_estimate.total,
|
||||||
|
amount_paid: Some(estimate.invoice_estimate.amount_paid),
|
||||||
|
amount_due: Some(estimate.invoice_estimate.amount_due),
|
||||||
|
currency: estimate.subscription_estimate.currency_code,
|
||||||
|
next_billing_at: estimate.subscription_estimate.next_billing_at,
|
||||||
|
credits_applied: Some(estimate.invoice_estimate.credits_applied),
|
||||||
|
line_items: estimate
|
||||||
|
.invoice_estimate
|
||||||
|
.line_items
|
||||||
|
.into_iter()
|
||||||
|
.map(|line_item| SubscriptionLineItem {
|
||||||
|
item_id: line_item.entity_id,
|
||||||
|
item_type: line_item.entity_type,
|
||||||
|
description: line_item.description,
|
||||||
|
amount: line_item.amount,
|
||||||
|
currency: estimate.invoice_estimate.currency_code,
|
||||||
|
unit_amount: Some(line_item.unit_amount),
|
||||||
|
quantity: line_item.quantity,
|
||||||
|
pricing_model: Some(line_item.pricing_model),
|
||||||
|
})
|
||||||
|
.collect(),
|
||||||
|
}),
|
||||||
|
..item.data
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
impl<F, T>
|
impl<F, T>
|
||||||
TryFrom<ResponseRouterData<F, ChargebeeListPlansResponse, T, GetSubscriptionPlansResponse>>
|
TryFrom<ResponseRouterData<F, ChargebeeListPlansResponse, T, GetSubscriptionPlansResponse>>
|
||||||
for RouterData<F, T, GetSubscriptionPlansResponse>
|
for RouterData<F, T, GetSubscriptionPlansResponse>
|
||||||
@ -1075,6 +1123,18 @@ impl
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Debug, Clone, Serialize, Deserialize)]
|
||||||
|
pub struct ChargebeeSubscriptionEstimateRequest {
|
||||||
|
pub price_id: String,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl TryFrom<&GetSubscriptionEstimateRouterData> for ChargebeeSubscriptionEstimateRequest {
|
||||||
|
type Error = error_stack::Report<errors::ConnectorError>;
|
||||||
|
fn try_from(item: &GetSubscriptionEstimateRouterData) -> Result<Self, Self::Error> {
|
||||||
|
let price_id = item.request.price_id.to_owned();
|
||||||
|
Ok(Self { price_id })
|
||||||
|
}
|
||||||
|
}
|
||||||
#[derive(Debug, Clone, Serialize, Deserialize)]
|
#[derive(Debug, Clone, Serialize, Deserialize)]
|
||||||
pub struct ChargebeeGetPlanPricesResponse {
|
pub struct ChargebeeGetPlanPricesResponse {
|
||||||
pub list: Vec<ChargebeeGetPlanPriceList>,
|
pub list: Vec<ChargebeeGetPlanPriceList>,
|
||||||
@ -1169,3 +1229,69 @@ impl<F, T>
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Debug, Clone, Serialize, Deserialize)]
|
||||||
|
pub struct SubscriptionEstimateResponse {
|
||||||
|
pub estimate: ChargebeeEstimate,
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Debug, Clone, Serialize, Deserialize)]
|
||||||
|
pub struct ChargebeeEstimate {
|
||||||
|
pub created_at: i64,
|
||||||
|
/// type of the object will be `estimate`
|
||||||
|
pub object: String,
|
||||||
|
pub subscription_estimate: SubscriptionEstimate,
|
||||||
|
pub invoice_estimate: InvoiceEstimate,
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Debug, Clone, Serialize, Deserialize)]
|
||||||
|
pub struct SubscriptionEstimate {
|
||||||
|
pub status: String,
|
||||||
|
#[serde(default, with = "common_utils::custom_serde::timestamp::option")]
|
||||||
|
pub next_billing_at: Option<PrimitiveDateTime>,
|
||||||
|
/// type of the object will be `subscription_estimate`
|
||||||
|
pub object: String,
|
||||||
|
pub currency_code: enums::Currency,
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Debug, Clone, Serialize, Deserialize)]
|
||||||
|
pub struct InvoiceEstimate {
|
||||||
|
pub recurring: bool,
|
||||||
|
#[serde(with = "common_utils::custom_serde::iso8601")]
|
||||||
|
pub date: PrimitiveDateTime,
|
||||||
|
pub price_type: String,
|
||||||
|
pub sub_total: MinorUnit,
|
||||||
|
pub total: MinorUnit,
|
||||||
|
pub credits_applied: MinorUnit,
|
||||||
|
pub amount_paid: MinorUnit,
|
||||||
|
pub amount_due: MinorUnit,
|
||||||
|
/// type of the object will be `invoice_estimate`
|
||||||
|
pub object: String,
|
||||||
|
pub customer_id: String,
|
||||||
|
pub line_items: Vec<LineItem>,
|
||||||
|
pub currency_code: enums::Currency,
|
||||||
|
pub round_off_amount: MinorUnit,
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Debug, Clone, Serialize, Deserialize)]
|
||||||
|
pub struct LineItem {
|
||||||
|
pub id: String,
|
||||||
|
#[serde(with = "common_utils::custom_serde::iso8601")]
|
||||||
|
pub date_from: PrimitiveDateTime,
|
||||||
|
#[serde(with = "common_utils::custom_serde::iso8601")]
|
||||||
|
pub date_to: PrimitiveDateTime,
|
||||||
|
pub unit_amount: MinorUnit,
|
||||||
|
pub quantity: i64,
|
||||||
|
pub amount: MinorUnit,
|
||||||
|
pub pricing_model: String,
|
||||||
|
pub is_taxed: bool,
|
||||||
|
pub tax_amount: MinorUnit,
|
||||||
|
/// type of the object will be `line_item`
|
||||||
|
pub object: String,
|
||||||
|
pub customer_id: String,
|
||||||
|
pub description: String,
|
||||||
|
pub entity_type: String,
|
||||||
|
pub entity_id: String,
|
||||||
|
pub discount_amount: MinorUnit,
|
||||||
|
pub item_level_discount_amount: MinorUnit,
|
||||||
|
}
|
||||||
|
|||||||
@ -11,20 +11,24 @@ use hyperswitch_domain_models::{
|
|||||||
router_data::{ConnectorAuthType, ErrorResponse},
|
router_data::{ConnectorAuthType, ErrorResponse},
|
||||||
router_data_v2::{
|
router_data_v2::{
|
||||||
flow_common_types::{
|
flow_common_types::{
|
||||||
GetSubscriptionPlanPricesData, GetSubscriptionPlansData, SubscriptionCreateData,
|
GetSubscriptionEstimateData, GetSubscriptionPlanPricesData, GetSubscriptionPlansData,
|
||||||
|
SubscriptionCreateData,
|
||||||
},
|
},
|
||||||
UasFlowData,
|
UasFlowData,
|
||||||
},
|
},
|
||||||
router_flow_types::{
|
router_flow_types::{
|
||||||
subscriptions::{GetSubscriptionPlanPrices, GetSubscriptionPlans, SubscriptionCreate},
|
subscriptions::{
|
||||||
|
GetSubscriptionEstimate, GetSubscriptionPlanPrices, GetSubscriptionPlans,
|
||||||
|
SubscriptionCreate,
|
||||||
|
},
|
||||||
unified_authentication_service::{
|
unified_authentication_service::{
|
||||||
Authenticate, AuthenticationConfirmation, PostAuthenticate, PreAuthenticate,
|
Authenticate, AuthenticationConfirmation, PostAuthenticate, PreAuthenticate,
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
router_request_types::{
|
router_request_types::{
|
||||||
subscriptions::{
|
subscriptions::{
|
||||||
GetSubscriptionPlanPricesRequest, GetSubscriptionPlansRequest,
|
GetSubscriptionEstimateRequest, GetSubscriptionPlanPricesRequest,
|
||||||
SubscriptionCreateRequest,
|
GetSubscriptionPlansRequest, SubscriptionCreateRequest,
|
||||||
},
|
},
|
||||||
unified_authentication_service::{
|
unified_authentication_service::{
|
||||||
UasAuthenticationRequestData, UasAuthenticationResponseData,
|
UasAuthenticationRequestData, UasAuthenticationResponseData,
|
||||||
@ -33,7 +37,8 @@ use hyperswitch_domain_models::{
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
router_response_types::subscriptions::{
|
router_response_types::subscriptions::{
|
||||||
GetSubscriptionPlanPricesResponse, GetSubscriptionPlansResponse, SubscriptionCreateResponse,
|
GetSubscriptionEstimateResponse, GetSubscriptionPlanPricesResponse,
|
||||||
|
GetSubscriptionPlansResponse, SubscriptionCreateResponse,
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
#[cfg(all(feature = "v2", feature = "revenue_recovery"))]
|
#[cfg(all(feature = "v2", feature = "revenue_recovery"))]
|
||||||
@ -183,6 +188,18 @@ impl
|
|||||||
> for Recurly
|
> for Recurly
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl api::subscriptions_v2::GetSubscriptionEstimateV2 for Recurly {}
|
||||||
|
impl
|
||||||
|
ConnectorIntegrationV2<
|
||||||
|
GetSubscriptionEstimate,
|
||||||
|
GetSubscriptionEstimateData,
|
||||||
|
GetSubscriptionEstimateRequest,
|
||||||
|
GetSubscriptionEstimateResponse,
|
||||||
|
> for Recurly
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
#[cfg(all(feature = "v2", feature = "revenue_recovery"))]
|
#[cfg(all(feature = "v2", feature = "revenue_recovery"))]
|
||||||
impl api::revenue_recovery_v2::RevenueRecoveryRecordBackV2 for Recurly {}
|
impl api::revenue_recovery_v2::RevenueRecoveryRecordBackV2 for Recurly {}
|
||||||
#[cfg(all(feature = "v2", feature = "revenue_recovery"))]
|
#[cfg(all(feature = "v2", feature = "revenue_recovery"))]
|
||||||
|
|||||||
@ -39,7 +39,7 @@ use hyperswitch_domain_models::{
|
|||||||
PostCaptureVoid, PostProcessing, PostSessionTokens, PreProcessing, Reject,
|
PostCaptureVoid, PostProcessing, PostSessionTokens, PreProcessing, Reject,
|
||||||
SdkSessionUpdate, UpdateMetadata,
|
SdkSessionUpdate, UpdateMetadata,
|
||||||
},
|
},
|
||||||
subscriptions::{GetSubscriptionPlanPrices, GetSubscriptionPlans},
|
subscriptions::{GetSubscriptionEstimate, GetSubscriptionPlanPrices, GetSubscriptionPlans},
|
||||||
webhooks::VerifyWebhookSource,
|
webhooks::VerifyWebhookSource,
|
||||||
AccessTokenAuthentication, Authenticate, AuthenticationConfirmation,
|
AccessTokenAuthentication, Authenticate, AuthenticationConfirmation,
|
||||||
ExternalVaultCreateFlow, ExternalVaultDeleteFlow, ExternalVaultInsertFlow,
|
ExternalVaultCreateFlow, ExternalVaultDeleteFlow, ExternalVaultInsertFlow,
|
||||||
@ -49,8 +49,8 @@ use hyperswitch_domain_models::{
|
|||||||
router_request_types::{
|
router_request_types::{
|
||||||
authentication,
|
authentication,
|
||||||
subscriptions::{
|
subscriptions::{
|
||||||
GetSubscriptionPlanPricesRequest, GetSubscriptionPlansRequest,
|
GetSubscriptionEstimateRequest, GetSubscriptionPlanPricesRequest,
|
||||||
SubscriptionCreateRequest,
|
GetSubscriptionPlansRequest, SubscriptionCreateRequest,
|
||||||
},
|
},
|
||||||
unified_authentication_service::{
|
unified_authentication_service::{
|
||||||
UasAuthenticationRequestData, UasAuthenticationResponseData,
|
UasAuthenticationRequestData, UasAuthenticationResponseData,
|
||||||
@ -71,8 +71,8 @@ use hyperswitch_domain_models::{
|
|||||||
},
|
},
|
||||||
router_response_types::{
|
router_response_types::{
|
||||||
subscriptions::{
|
subscriptions::{
|
||||||
GetSubscriptionPlanPricesResponse, GetSubscriptionPlansResponse,
|
GetSubscriptionEstimateResponse, GetSubscriptionPlanPricesResponse,
|
||||||
SubscriptionCreateResponse,
|
GetSubscriptionPlansResponse, SubscriptionCreateResponse,
|
||||||
},
|
},
|
||||||
AcceptDisputeResponse, AuthenticationResponseData, DefendDisputeResponse,
|
AcceptDisputeResponse, AuthenticationResponseData, DefendDisputeResponse,
|
||||||
DisputeSyncResponse, FetchDisputesResponse, GiftCardBalanceCheckResponseData,
|
DisputeSyncResponse, FetchDisputesResponse, GiftCardBalanceCheckResponseData,
|
||||||
@ -138,8 +138,8 @@ use hyperswitch_interfaces::{
|
|||||||
},
|
},
|
||||||
revenue_recovery::RevenueRecovery,
|
revenue_recovery::RevenueRecovery,
|
||||||
subscriptions::{
|
subscriptions::{
|
||||||
GetSubscriptionPlanPricesFlow, GetSubscriptionPlansFlow, SubscriptionCreate,
|
GetSubscriptionEstimateFlow, GetSubscriptionPlanPricesFlow, GetSubscriptionPlansFlow,
|
||||||
Subscriptions,
|
SubscriptionCreate, Subscriptions,
|
||||||
},
|
},
|
||||||
vault::{
|
vault::{
|
||||||
ExternalVault, ExternalVaultCreate, ExternalVaultDelete, ExternalVaultInsert,
|
ExternalVault, ExternalVaultCreate, ExternalVaultDelete, ExternalVaultInsert,
|
||||||
@ -7069,6 +7069,14 @@ macro_rules! default_imp_for_subscriptions {
|
|||||||
SubscriptionCreateRequest,
|
SubscriptionCreateRequest,
|
||||||
SubscriptionCreateResponse,
|
SubscriptionCreateResponse,
|
||||||
> for $path::$connector {}
|
> for $path::$connector {}
|
||||||
|
impl GetSubscriptionEstimateFlow for $path::$connector {}
|
||||||
|
impl
|
||||||
|
ConnectorIntegration<
|
||||||
|
GetSubscriptionEstimate,
|
||||||
|
GetSubscriptionEstimateRequest,
|
||||||
|
GetSubscriptionEstimateResponse
|
||||||
|
> for $path::$connector
|
||||||
|
{}
|
||||||
)*
|
)*
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
@ -9400,3 +9408,15 @@ impl<const T: u8>
|
|||||||
> for connectors::DummyConnector<T>
|
> for connectors::DummyConnector<T>
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[cfg(feature = "dummy_connector")]
|
||||||
|
impl<const T: u8> GetSubscriptionEstimateFlow for connectors::DummyConnector<T> {}
|
||||||
|
#[cfg(feature = "dummy_connector")]
|
||||||
|
impl<const T: u8>
|
||||||
|
ConnectorIntegration<
|
||||||
|
GetSubscriptionEstimate,
|
||||||
|
GetSubscriptionEstimateRequest,
|
||||||
|
GetSubscriptionEstimateResponse,
|
||||||
|
> for connectors::DummyConnector<T>
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|||||||
@ -159,6 +159,9 @@ pub struct GetSubscriptionPlansData;
|
|||||||
#[derive(Debug, Clone)]
|
#[derive(Debug, Clone)]
|
||||||
pub struct GetSubscriptionPlanPricesData;
|
pub struct GetSubscriptionPlanPricesData;
|
||||||
|
|
||||||
|
#[derive(Debug, Clone)]
|
||||||
|
pub struct GetSubscriptionEstimateData;
|
||||||
|
|
||||||
#[derive(Debug, Clone)]
|
#[derive(Debug, Clone)]
|
||||||
pub struct UasFlowData {
|
pub struct UasFlowData {
|
||||||
pub authenticate_by: String,
|
pub authenticate_by: String,
|
||||||
|
|||||||
@ -5,3 +5,6 @@ pub struct GetSubscriptionPlans;
|
|||||||
|
|
||||||
#[derive(Debug, Clone)]
|
#[derive(Debug, Clone)]
|
||||||
pub struct GetSubscriptionPlanPrices;
|
pub struct GetSubscriptionPlanPrices;
|
||||||
|
|
||||||
|
#[derive(Debug, Clone)]
|
||||||
|
pub struct GetSubscriptionEstimate;
|
||||||
|
|||||||
@ -33,3 +33,8 @@ pub struct GetSubscriptionPlansRequest {
|
|||||||
pub struct GetSubscriptionPlanPricesRequest {
|
pub struct GetSubscriptionPlanPricesRequest {
|
||||||
pub plan_price_id: String,
|
pub plan_price_id: String,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Debug, Clone)]
|
||||||
|
pub struct GetSubscriptionEstimateRequest {
|
||||||
|
pub price_id: String,
|
||||||
|
}
|
||||||
|
|||||||
@ -61,3 +61,27 @@ pub enum PeriodUnit {
|
|||||||
Month,
|
Month,
|
||||||
Year,
|
Year,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Debug, Clone)]
|
||||||
|
pub struct GetSubscriptionEstimateResponse {
|
||||||
|
pub sub_total: MinorUnit,
|
||||||
|
pub total: MinorUnit,
|
||||||
|
pub credits_applied: Option<MinorUnit>,
|
||||||
|
pub amount_paid: Option<MinorUnit>,
|
||||||
|
pub amount_due: Option<MinorUnit>,
|
||||||
|
pub currency: Currency,
|
||||||
|
pub next_billing_at: Option<PrimitiveDateTime>,
|
||||||
|
pub line_items: Vec<SubscriptionLineItem>,
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Debug, Clone)]
|
||||||
|
pub struct SubscriptionLineItem {
|
||||||
|
pub item_id: String,
|
||||||
|
pub item_type: String,
|
||||||
|
pub description: String,
|
||||||
|
pub amount: MinorUnit,
|
||||||
|
pub currency: Currency,
|
||||||
|
pub unit_amount: Option<MinorUnit>,
|
||||||
|
pub quantity: i64,
|
||||||
|
pub pricing_model: Option<String>,
|
||||||
|
}
|
||||||
|
|||||||
@ -6,7 +6,10 @@ use crate::{
|
|||||||
router_flow_types::{
|
router_flow_types::{
|
||||||
mandate_revoke::MandateRevoke,
|
mandate_revoke::MandateRevoke,
|
||||||
revenue_recovery::InvoiceRecordBack,
|
revenue_recovery::InvoiceRecordBack,
|
||||||
subscriptions::{GetSubscriptionPlanPrices, GetSubscriptionPlans, SubscriptionCreate},
|
subscriptions::{
|
||||||
|
GetSubscriptionEstimate, GetSubscriptionPlanPrices, GetSubscriptionPlans,
|
||||||
|
SubscriptionCreate,
|
||||||
|
},
|
||||||
AccessTokenAuth, AccessTokenAuthentication, Authenticate, AuthenticationConfirmation,
|
AccessTokenAuth, AccessTokenAuthentication, Authenticate, AuthenticationConfirmation,
|
||||||
Authorize, AuthorizeSessionToken, BillingConnectorInvoiceSync,
|
Authorize, AuthorizeSessionToken, BillingConnectorInvoiceSync,
|
||||||
BillingConnectorPaymentsSync, CalculateTax, Capture, CompleteAuthorize,
|
BillingConnectorPaymentsSync, CalculateTax, Capture, CompleteAuthorize,
|
||||||
@ -21,8 +24,8 @@ use crate::{
|
|||||||
InvoiceRecordBackRequest,
|
InvoiceRecordBackRequest,
|
||||||
},
|
},
|
||||||
subscriptions::{
|
subscriptions::{
|
||||||
GetSubscriptionPlanPricesRequest, GetSubscriptionPlansRequest,
|
GetSubscriptionEstimateRequest, GetSubscriptionPlanPricesRequest,
|
||||||
SubscriptionCreateRequest,
|
GetSubscriptionPlansRequest, SubscriptionCreateRequest,
|
||||||
},
|
},
|
||||||
unified_authentication_service::{
|
unified_authentication_service::{
|
||||||
UasAuthenticationRequestData, UasAuthenticationResponseData,
|
UasAuthenticationRequestData, UasAuthenticationResponseData,
|
||||||
@ -46,8 +49,8 @@ use crate::{
|
|||||||
InvoiceRecordBackResponse,
|
InvoiceRecordBackResponse,
|
||||||
},
|
},
|
||||||
subscriptions::{
|
subscriptions::{
|
||||||
GetSubscriptionPlanPricesResponse, GetSubscriptionPlansResponse,
|
GetSubscriptionEstimateResponse, GetSubscriptionPlanPricesResponse,
|
||||||
SubscriptionCreateResponse,
|
GetSubscriptionPlansResponse, SubscriptionCreateResponse,
|
||||||
},
|
},
|
||||||
GiftCardBalanceCheckResponseData, MandateRevokeResponseData, PaymentsResponseData,
|
GiftCardBalanceCheckResponseData, MandateRevokeResponseData, PaymentsResponseData,
|
||||||
RefundsResponseData, TaxCalculationResponseData, VaultResponseData,
|
RefundsResponseData, TaxCalculationResponseData, VaultResponseData,
|
||||||
@ -144,6 +147,12 @@ pub type InvoiceRecordBackRouterData =
|
|||||||
pub type GetSubscriptionPlansRouterData =
|
pub type GetSubscriptionPlansRouterData =
|
||||||
RouterData<GetSubscriptionPlans, GetSubscriptionPlansRequest, GetSubscriptionPlansResponse>;
|
RouterData<GetSubscriptionPlans, GetSubscriptionPlansRequest, GetSubscriptionPlansResponse>;
|
||||||
|
|
||||||
|
pub type GetSubscriptionEstimateRouterData = RouterData<
|
||||||
|
GetSubscriptionEstimate,
|
||||||
|
GetSubscriptionEstimateRequest,
|
||||||
|
GetSubscriptionEstimateResponse,
|
||||||
|
>;
|
||||||
|
|
||||||
pub type UasAuthenticationRouterData =
|
pub type UasAuthenticationRouterData =
|
||||||
RouterData<Authenticate, UasAuthenticationRequestData, UasAuthenticationResponseData>;
|
RouterData<Authenticate, UasAuthenticationRequestData, UasAuthenticationResponseData>;
|
||||||
|
|
||||||
|
|||||||
@ -2,12 +2,16 @@
|
|||||||
#[cfg(feature = "v1")]
|
#[cfg(feature = "v1")]
|
||||||
use hyperswitch_domain_models::{
|
use hyperswitch_domain_models::{
|
||||||
router_flow_types::subscriptions::SubscriptionCreate as SubscriptionCreateFlow,
|
router_flow_types::subscriptions::SubscriptionCreate as SubscriptionCreateFlow,
|
||||||
router_flow_types::subscriptions::{GetSubscriptionPlanPrices, GetSubscriptionPlans},
|
router_flow_types::subscriptions::{
|
||||||
|
GetSubscriptionEstimate, GetSubscriptionPlanPrices, GetSubscriptionPlans,
|
||||||
|
},
|
||||||
router_request_types::subscriptions::{
|
router_request_types::subscriptions::{
|
||||||
GetSubscriptionPlanPricesRequest, GetSubscriptionPlansRequest, SubscriptionCreateRequest,
|
GetSubscriptionEstimateRequest, GetSubscriptionPlanPricesRequest,
|
||||||
|
GetSubscriptionPlansRequest, SubscriptionCreateRequest,
|
||||||
},
|
},
|
||||||
router_response_types::subscriptions::{
|
router_response_types::subscriptions::{
|
||||||
GetSubscriptionPlanPricesResponse, GetSubscriptionPlansResponse, SubscriptionCreateResponse,
|
GetSubscriptionEstimateResponse, GetSubscriptionPlanPricesResponse,
|
||||||
|
GetSubscriptionPlansResponse, SubscriptionCreateResponse,
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -45,6 +49,16 @@ pub trait SubscriptionCreate:
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[cfg(feature = "v1")]
|
||||||
|
/// trait GetSubscriptionEstimate for V1
|
||||||
|
pub trait GetSubscriptionEstimateFlow:
|
||||||
|
ConnectorIntegration<
|
||||||
|
GetSubscriptionEstimate,
|
||||||
|
GetSubscriptionEstimateRequest,
|
||||||
|
GetSubscriptionEstimateResponse,
|
||||||
|
>
|
||||||
|
{
|
||||||
|
}
|
||||||
/// trait Subscriptions
|
/// trait Subscriptions
|
||||||
#[cfg(feature = "v1")]
|
#[cfg(feature = "v1")]
|
||||||
pub trait Subscriptions:
|
pub trait Subscriptions:
|
||||||
@ -53,6 +67,7 @@ pub trait Subscriptions:
|
|||||||
+ GetSubscriptionPlanPricesFlow
|
+ GetSubscriptionPlanPricesFlow
|
||||||
+ SubscriptionCreate
|
+ SubscriptionCreate
|
||||||
+ PaymentsConnectorCustomer
|
+ PaymentsConnectorCustomer
|
||||||
|
+ GetSubscriptionEstimateFlow
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -75,3 +90,7 @@ pub trait ConnectorCustomer {}
|
|||||||
/// trait SubscriptionCreate
|
/// trait SubscriptionCreate
|
||||||
#[cfg(not(feature = "v1"))]
|
#[cfg(not(feature = "v1"))]
|
||||||
pub trait SubscriptionCreate {}
|
pub trait SubscriptionCreate {}
|
||||||
|
|
||||||
|
/// trait GetSubscriptionEstimateFlow (disabled when not V1)
|
||||||
|
#[cfg(not(feature = "v1"))]
|
||||||
|
pub trait GetSubscriptionEstimateFlow {}
|
||||||
|
|||||||
@ -1,16 +1,20 @@
|
|||||||
//! SubscriptionsV2
|
//! SubscriptionsV2
|
||||||
use hyperswitch_domain_models::{
|
use hyperswitch_domain_models::{
|
||||||
router_data_v2::flow_common_types::{
|
router_data_v2::flow_common_types::{
|
||||||
GetSubscriptionPlanPricesData, GetSubscriptionPlansData, SubscriptionCreateData,
|
GetSubscriptionEstimateData, GetSubscriptionPlanPricesData, GetSubscriptionPlansData,
|
||||||
|
SubscriptionCreateData,
|
||||||
},
|
},
|
||||||
router_flow_types::subscriptions::{
|
router_flow_types::subscriptions::{
|
||||||
GetSubscriptionPlanPrices, GetSubscriptionPlans, SubscriptionCreate,
|
GetSubscriptionEstimate, GetSubscriptionPlanPrices, GetSubscriptionPlans,
|
||||||
|
SubscriptionCreate,
|
||||||
},
|
},
|
||||||
router_request_types::subscriptions::{
|
router_request_types::subscriptions::{
|
||||||
GetSubscriptionPlanPricesRequest, GetSubscriptionPlansRequest, SubscriptionCreateRequest,
|
GetSubscriptionEstimateRequest, GetSubscriptionPlanPricesRequest,
|
||||||
|
GetSubscriptionPlansRequest, SubscriptionCreateRequest,
|
||||||
},
|
},
|
||||||
router_response_types::subscriptions::{
|
router_response_types::subscriptions::{
|
||||||
GetSubscriptionPlanPricesResponse, GetSubscriptionPlansResponse, SubscriptionCreateResponse,
|
GetSubscriptionEstimateResponse, GetSubscriptionPlanPricesResponse,
|
||||||
|
GetSubscriptionPlansResponse, SubscriptionCreateResponse,
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -19,7 +23,11 @@ use crate::connector_integration_v2::ConnectorIntegrationV2;
|
|||||||
|
|
||||||
/// trait SubscriptionsV2
|
/// trait SubscriptionsV2
|
||||||
pub trait SubscriptionsV2:
|
pub trait SubscriptionsV2:
|
||||||
GetSubscriptionPlansV2 + SubscriptionsCreateV2 + ConnectorCustomerV2 + GetSubscriptionPlanPricesV2
|
GetSubscriptionPlansV2
|
||||||
|
+ SubscriptionsCreateV2
|
||||||
|
+ ConnectorCustomerV2
|
||||||
|
+ GetSubscriptionPlanPricesV2
|
||||||
|
+ GetSubscriptionEstimateV2
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -55,3 +63,14 @@ pub trait SubscriptionsCreateV2:
|
|||||||
>
|
>
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// trait GetSubscriptionEstimate for V2
|
||||||
|
pub trait GetSubscriptionEstimateV2:
|
||||||
|
ConnectorIntegrationV2<
|
||||||
|
GetSubscriptionEstimate,
|
||||||
|
GetSubscriptionEstimateData,
|
||||||
|
GetSubscriptionEstimateRequest,
|
||||||
|
GetSubscriptionEstimateResponse,
|
||||||
|
>
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|||||||
@ -16,7 +16,10 @@ use hyperswitch_domain_models::{
|
|||||||
},
|
},
|
||||||
refunds::{Execute, RSync},
|
refunds::{Execute, RSync},
|
||||||
revenue_recovery::{BillingConnectorPaymentsSync, InvoiceRecordBack},
|
revenue_recovery::{BillingConnectorPaymentsSync, InvoiceRecordBack},
|
||||||
subscriptions::{GetSubscriptionPlanPrices, GetSubscriptionPlans, SubscriptionCreate},
|
subscriptions::{
|
||||||
|
GetSubscriptionEstimate, GetSubscriptionPlanPrices, GetSubscriptionPlans,
|
||||||
|
SubscriptionCreate,
|
||||||
|
},
|
||||||
unified_authentication_service::{
|
unified_authentication_service::{
|
||||||
Authenticate, AuthenticationConfirmation, PostAuthenticate, PreAuthenticate,
|
Authenticate, AuthenticationConfirmation, PostAuthenticate, PreAuthenticate,
|
||||||
},
|
},
|
||||||
@ -33,8 +36,8 @@ use hyperswitch_domain_models::{
|
|||||||
InvoiceRecordBackRequest,
|
InvoiceRecordBackRequest,
|
||||||
},
|
},
|
||||||
subscriptions::{
|
subscriptions::{
|
||||||
GetSubscriptionPlanPricesRequest, GetSubscriptionPlansRequest,
|
GetSubscriptionEstimateRequest, GetSubscriptionPlanPricesRequest,
|
||||||
SubscriptionCreateRequest,
|
GetSubscriptionPlansRequest, SubscriptionCreateRequest,
|
||||||
},
|
},
|
||||||
unified_authentication_service::{
|
unified_authentication_service::{
|
||||||
UasAuthenticationRequestData, UasAuthenticationResponseData,
|
UasAuthenticationRequestData, UasAuthenticationResponseData,
|
||||||
@ -61,8 +64,8 @@ use hyperswitch_domain_models::{
|
|||||||
InvoiceRecordBackResponse,
|
InvoiceRecordBackResponse,
|
||||||
},
|
},
|
||||||
subscriptions::{
|
subscriptions::{
|
||||||
GetSubscriptionPlanPricesResponse, GetSubscriptionPlansResponse,
|
GetSubscriptionEstimateResponse, GetSubscriptionPlanPricesResponse,
|
||||||
SubscriptionCreateResponse,
|
GetSubscriptionPlansResponse, SubscriptionCreateResponse,
|
||||||
},
|
},
|
||||||
AcceptDisputeResponse, DefendDisputeResponse, DisputeSyncResponse, FetchDisputesResponse,
|
AcceptDisputeResponse, DefendDisputeResponse, DisputeSyncResponse, FetchDisputesResponse,
|
||||||
GiftCardBalanceCheckResponseData, MandateRevokeResponseData, PaymentsResponseData,
|
GiftCardBalanceCheckResponseData, MandateRevokeResponseData, PaymentsResponseData,
|
||||||
@ -361,6 +364,13 @@ pub type GetSubscriptionPlansType = dyn ConnectorIntegration<
|
|||||||
GetSubscriptionPlansResponse,
|
GetSubscriptionPlansResponse,
|
||||||
>;
|
>;
|
||||||
|
|
||||||
|
/// Type alias for `ConnectorIntegration<GetSubscriptionEstimate, GetSubscriptionEstimateRequest, GetSubscriptionEstimateResponse>`
|
||||||
|
pub type GetSubscriptionEstimateType = dyn ConnectorIntegration<
|
||||||
|
GetSubscriptionEstimate,
|
||||||
|
GetSubscriptionEstimateRequest,
|
||||||
|
GetSubscriptionEstimateResponse,
|
||||||
|
>;
|
||||||
|
|
||||||
/// Type alias for `ConnectorIntegration<ExternalVaultInsertFlow, VaultRequestData, VaultResponseData>`
|
/// Type alias for `ConnectorIntegration<ExternalVaultInsertFlow, VaultRequestData, VaultResponseData>`
|
||||||
pub type ExternalVaultInsertType =
|
pub type ExternalVaultInsertType =
|
||||||
dyn ConnectorIntegration<ExternalVaultInsertFlow, VaultRequestData, VaultResponseData>;
|
dyn ConnectorIntegration<ExternalVaultInsertFlow, VaultRequestData, VaultResponseData>;
|
||||||
|
|||||||
@ -110,6 +110,8 @@ pub type BoxedGetSubscriptionPlansInterface<T, Req, Res> =
|
|||||||
BoxedConnectorIntegrationInterface<T, common_types::GetSubscriptionPlansData, Req, Res>;
|
BoxedConnectorIntegrationInterface<T, common_types::GetSubscriptionPlansData, Req, Res>;
|
||||||
pub type BoxedGetSubscriptionPlanPricesInterface<T, Req, Res> =
|
pub type BoxedGetSubscriptionPlanPricesInterface<T, Req, Res> =
|
||||||
BoxedConnectorIntegrationInterface<T, common_types::GetSubscriptionPlanPricesData, Req, Res>;
|
BoxedConnectorIntegrationInterface<T, common_types::GetSubscriptionPlanPricesData, Req, Res>;
|
||||||
|
pub type BoxedGetSubscriptionEstimateInterface<T, Req, Res> =
|
||||||
|
BoxedConnectorIntegrationInterface<T, common_types::GetSubscriptionEstimateData, Req, Res>;
|
||||||
pub type BoxedBillingConnectorInvoiceSyncIntegrationInterface<T, Req, Res> =
|
pub type BoxedBillingConnectorInvoiceSyncIntegrationInterface<T, Req, Res> =
|
||||||
BoxedConnectorIntegrationInterface<
|
BoxedConnectorIntegrationInterface<
|
||||||
T,
|
T,
|
||||||
|
|||||||
Reference in New Issue
Block a user