mirror of
https://github.com/juspay/hyperswitch.git
synced 2025-10-28 04:04:55 +08:00
feat(connector): [ZSL] add connector template code (#4285)
Co-authored-by: hyperswitch-bot[bot] <148525504+hyperswitch-bot[bot]@users.noreply.github.com> Co-authored-by: SamraatBansal <55536657+SamraatBansal@users.noreply.github.com>
This commit is contained in:
@ -228,6 +228,7 @@ volt.base_url = "https://api.sandbox.volt.io/"
|
||||
wise.base_url = "https://api.sandbox.transferwise.tech/"
|
||||
worldline.base_url = "https://eu.sandbox.api-ingenico.com/"
|
||||
worldpay.base_url = "https://try.access.worldpay.com/"
|
||||
zsl.base_url = "https://api.sitoffalb.net/"
|
||||
zen.base_url = "https://api.zen-test.com/"
|
||||
zen.secondary_base_url = "https://secure.zen-test.com/"
|
||||
|
||||
@ -280,6 +281,7 @@ cards = [
|
||||
"threedsecureio",
|
||||
"worldpay",
|
||||
"zen",
|
||||
"zsl",
|
||||
]
|
||||
|
||||
# Scheduler settings provides a point to modify the behaviour of scheduler flow.
|
||||
|
||||
@ -143,6 +143,7 @@ cards = [
|
||||
"worldline",
|
||||
"worldpay",
|
||||
"zen",
|
||||
"zsl",
|
||||
]
|
||||
|
||||
[refund]
|
||||
@ -227,6 +228,7 @@ volt.base_url = "https://api.sandbox.volt.io/"
|
||||
trustpay.base_url_bank_redirects = "https://aapi.trustpay.eu/"
|
||||
zen.base_url = "https://api.zen-test.com/"
|
||||
zen.secondary_base_url = "https://secure.zen-test.com/"
|
||||
zsl.base_url = "https://api.sitoffalb.net/"
|
||||
|
||||
[scheduler]
|
||||
stream = "SCHEDULER_STREAM"
|
||||
|
||||
@ -164,6 +164,7 @@ worldline.base_url = "https://eu.sandbox.api-ingenico.com/"
|
||||
worldpay.base_url = "https://try.access.worldpay.com/"
|
||||
zen.base_url = "https://api.zen-test.com/"
|
||||
zen.secondary_base_url = "https://secure.zen-test.com/"
|
||||
zsl.base_url = "https://api.sitoffalb.net/"
|
||||
|
||||
|
||||
[pm_filters.default]
|
||||
@ -225,6 +226,7 @@ cards = [
|
||||
"worldline",
|
||||
"worldpay",
|
||||
"zen",
|
||||
"zsl"
|
||||
]
|
||||
|
||||
[delayed_session_response]
|
||||
|
||||
@ -126,10 +126,11 @@ pub enum Connector {
|
||||
Wise,
|
||||
Worldline,
|
||||
Worldpay,
|
||||
Zen,
|
||||
Signifyd,
|
||||
Plaid,
|
||||
Riskified,
|
||||
Zen,
|
||||
// Zsl, Added as template code for future usage
|
||||
}
|
||||
|
||||
impl Connector {
|
||||
@ -207,6 +208,7 @@ impl Connector {
|
||||
| Self::Worldline
|
||||
| Self::Worldpay
|
||||
| Self::Zen
|
||||
// | Self::Zsl Added as template code for future usage
|
||||
| Self::Signifyd
|
||||
| Self::Plaid
|
||||
| Self::Riskified
|
||||
@ -264,6 +266,7 @@ impl Connector {
|
||||
| Self::Worldline
|
||||
| Self::Worldpay
|
||||
| Self::Zen
|
||||
// | Self::Zsl, Added as template code for future usage
|
||||
| Self::Signifyd
|
||||
| Self::Plaid
|
||||
| Self::Riskified
|
||||
|
||||
@ -167,6 +167,7 @@ pub enum RoutableConnectors {
|
||||
Worldline,
|
||||
Worldpay,
|
||||
Zen,
|
||||
// Zsl, Added as template code for future usage
|
||||
}
|
||||
|
||||
impl AttemptStatus {
|
||||
|
||||
@ -163,12 +163,13 @@ pub struct ConnectorConfig {
|
||||
pub wise_payout: Option<ConnectorTomlConfig>,
|
||||
pub worldline: Option<ConnectorTomlConfig>,
|
||||
pub worldpay: Option<ConnectorTomlConfig>,
|
||||
pub zen: Option<ConnectorTomlConfig>,
|
||||
pub square: Option<ConnectorTomlConfig>,
|
||||
pub stax: Option<ConnectorTomlConfig>,
|
||||
pub dummy_connector: Option<ConnectorTomlConfig>,
|
||||
pub stripe_test: Option<ConnectorTomlConfig>,
|
||||
pub paypal_test: Option<ConnectorTomlConfig>,
|
||||
pub zen: Option<ConnectorTomlConfig>,
|
||||
pub zsl: Option<ConnectorTomlConfig>,
|
||||
}
|
||||
|
||||
impl ConnectorConfig {
|
||||
@ -277,6 +278,7 @@ impl ConnectorConfig {
|
||||
Connector::Worldline => Ok(connector_data.worldline),
|
||||
Connector::Worldpay => Ok(connector_data.worldpay),
|
||||
Connector::Zen => Ok(connector_data.zen),
|
||||
// Connector::Zsl => Ok(connector_data.zsl), Added as template code for future usage
|
||||
#[cfg(feature = "dummy_connector")]
|
||||
Connector::DummyConnector1 => Ok(connector_data.dummy_connector),
|
||||
#[cfg(feature = "dummy_connector")]
|
||||
|
||||
@ -539,6 +539,7 @@ pub struct Connectors {
|
||||
pub worldline: ConnectorParams,
|
||||
pub worldpay: ConnectorParams,
|
||||
pub zen: ConnectorParams,
|
||||
pub zsl: ConnectorParams,
|
||||
}
|
||||
|
||||
#[derive(Debug, Deserialize, Clone, Default, router_derive::ConfigValidate)]
|
||||
|
||||
@ -57,6 +57,7 @@ pub mod wise;
|
||||
pub mod worldline;
|
||||
pub mod worldpay;
|
||||
pub mod zen;
|
||||
pub mod zsl;
|
||||
|
||||
#[cfg(feature = "dummy_connector")]
|
||||
pub use self::dummyconnector::DummyConnector;
|
||||
@ -72,5 +73,5 @@ pub use self::{
|
||||
payu::Payu, placetopay::Placetopay, powertranz::Powertranz, prophetpay::Prophetpay,
|
||||
rapyd::Rapyd, riskified::Riskified, shift4::Shift4, signifyd::Signifyd, square::Square,
|
||||
stax::Stax, stripe::Stripe, threedsecureio::Threedsecureio, trustpay::Trustpay, tsys::Tsys,
|
||||
volt::Volt, wise::Wise, worldline::Worldline, worldpay::Worldpay, zen::Zen,
|
||||
volt::Volt, wise::Wise, worldline::Worldline, worldpay::Worldpay, zen::Zen, zsl::Zsl,
|
||||
};
|
||||
|
||||
279
crates/router/src/connector/zsl.rs
Normal file
279
crates/router/src/connector/zsl.rs
Normal file
@ -0,0 +1,279 @@
|
||||
pub mod transformers;
|
||||
|
||||
use std::fmt::Debug;
|
||||
|
||||
use error_stack::{report, ResultExt};
|
||||
use masking::ExposeInterface;
|
||||
use transformers as zsl;
|
||||
|
||||
use crate::{
|
||||
configs::settings,
|
||||
core::errors::{self, CustomResult},
|
||||
events::connector_api_logs::ConnectorEvent,
|
||||
headers,
|
||||
services::{
|
||||
self,
|
||||
request::{self, Mask},
|
||||
ConnectorIntegration, ConnectorValidation,
|
||||
},
|
||||
types::{
|
||||
self,
|
||||
api::{self, ConnectorCommon, ConnectorCommonExt},
|
||||
ErrorResponse, RequestContent, Response,
|
||||
},
|
||||
utils::BytesExt,
|
||||
};
|
||||
|
||||
#[derive(Debug, Clone)]
|
||||
pub struct Zsl;
|
||||
|
||||
impl api::Payment for Zsl {}
|
||||
impl api::PaymentSession for Zsl {}
|
||||
impl api::ConnectorAccessToken for Zsl {}
|
||||
impl api::MandateSetup for Zsl {}
|
||||
impl api::PaymentAuthorize for Zsl {}
|
||||
impl api::PaymentSync for Zsl {}
|
||||
impl api::PaymentCapture for Zsl {}
|
||||
impl api::PaymentVoid for Zsl {}
|
||||
impl api::Refund for Zsl {}
|
||||
impl api::RefundExecute for Zsl {}
|
||||
impl api::RefundSync for Zsl {}
|
||||
impl api::PaymentToken for Zsl {}
|
||||
|
||||
impl
|
||||
ConnectorIntegration<
|
||||
api::PaymentMethodToken,
|
||||
types::PaymentMethodTokenizationData,
|
||||
types::PaymentsResponseData,
|
||||
> for Zsl
|
||||
{
|
||||
// Not Implemented (R)
|
||||
}
|
||||
|
||||
impl<Flow, Request, Response> ConnectorCommonExt<Flow, Request, Response> for Zsl
|
||||
where
|
||||
Self: ConnectorIntegration<Flow, Request, Response>,
|
||||
{
|
||||
fn build_headers(
|
||||
&self,
|
||||
req: &types::RouterData<Flow, Request, Response>,
|
||||
_connectors: &settings::Connectors,
|
||||
) -> CustomResult<Vec<(String, request::Maskable<String>)>, errors::ConnectorError> {
|
||||
let mut header = vec![(
|
||||
headers::CONTENT_TYPE.to_string(),
|
||||
self.get_content_type().to_string().into(),
|
||||
)];
|
||||
let mut api_key = self.get_auth_header(&req.connector_auth_type)?;
|
||||
header.append(&mut api_key);
|
||||
Ok(header)
|
||||
}
|
||||
}
|
||||
|
||||
impl ConnectorCommon for Zsl {
|
||||
fn id(&self) -> &'static str {
|
||||
"zsl"
|
||||
}
|
||||
|
||||
fn get_currency_unit(&self) -> api::CurrencyUnit {
|
||||
api::CurrencyUnit::Minor
|
||||
}
|
||||
|
||||
fn common_get_content_type(&self) -> &'static str {
|
||||
"application/json"
|
||||
}
|
||||
|
||||
fn base_url<'a>(&self, connectors: &'a settings::Connectors) -> &'a str {
|
||||
connectors.zsl.base_url.as_ref()
|
||||
}
|
||||
|
||||
fn get_auth_header(
|
||||
&self,
|
||||
auth_type: &types::ConnectorAuthType,
|
||||
) -> CustomResult<Vec<(String, request::Maskable<String>)>, errors::ConnectorError> {
|
||||
let auth = zsl::ZslAuthType::try_from(auth_type)
|
||||
.change_context(errors::ConnectorError::FailedToObtainAuthType)?;
|
||||
|
||||
Ok(vec![(
|
||||
headers::AUTHORIZATION.to_string(),
|
||||
format!("{}:{}", auth.api_key.expose(), auth.merchant_id.expose()).into_masked(),
|
||||
)])
|
||||
}
|
||||
|
||||
fn build_error_response(
|
||||
&self,
|
||||
res: Response,
|
||||
event_builder: Option<&mut ConnectorEvent>,
|
||||
) -> CustomResult<ErrorResponse, errors::ConnectorError> {
|
||||
let response: zsl::ZslErrorResponse = res
|
||||
.response
|
||||
.parse_struct("ZslErrorResponse")
|
||||
.change_context(errors::ConnectorError::ResponseDeserializationFailed)?;
|
||||
|
||||
event_builder.map(|i| i.set_response_body(&response));
|
||||
router_env::logger::info!(connector_response=?response);
|
||||
|
||||
Ok(ErrorResponse {
|
||||
status_code: res.status_code,
|
||||
code: response.code,
|
||||
message: response.message,
|
||||
reason: response.reason,
|
||||
attempt_status: None,
|
||||
connector_transaction_id: None,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
impl ConnectorValidation for Zsl {
|
||||
//TODO: implement functions when support enabled
|
||||
}
|
||||
|
||||
impl ConnectorIntegration<api::Session, types::PaymentsSessionData, types::PaymentsResponseData>
|
||||
for Zsl
|
||||
{
|
||||
//TODO: implement sessions flow
|
||||
}
|
||||
|
||||
impl ConnectorIntegration<api::AccessTokenAuth, types::AccessTokenRequestData, types::AccessToken>
|
||||
for Zsl
|
||||
{
|
||||
}
|
||||
|
||||
impl
|
||||
ConnectorIntegration<
|
||||
api::SetupMandate,
|
||||
types::SetupMandateRequestData,
|
||||
types::PaymentsResponseData,
|
||||
> for Zsl
|
||||
{
|
||||
}
|
||||
|
||||
impl ConnectorIntegration<api::Authorize, types::PaymentsAuthorizeData, types::PaymentsResponseData>
|
||||
for Zsl
|
||||
{
|
||||
fn get_headers(
|
||||
&self,
|
||||
req: &types::PaymentsAuthorizeRouterData,
|
||||
connectors: &settings::Connectors,
|
||||
) -> CustomResult<Vec<(String, request::Maskable<String>)>, errors::ConnectorError> {
|
||||
self.build_headers(req, connectors)
|
||||
}
|
||||
|
||||
fn get_content_type(&self) -> &'static str {
|
||||
self.common_get_content_type()
|
||||
}
|
||||
|
||||
fn get_url(
|
||||
&self,
|
||||
_req: &types::PaymentsAuthorizeRouterData,
|
||||
_connectors: &settings::Connectors,
|
||||
) -> CustomResult<String, errors::ConnectorError> {
|
||||
Err(errors::ConnectorError::NotImplemented("get_url method".to_string()).into())
|
||||
}
|
||||
|
||||
fn get_request_body(
|
||||
&self,
|
||||
req: &types::PaymentsAuthorizeRouterData,
|
||||
_connectors: &settings::Connectors,
|
||||
) -> CustomResult<RequestContent, errors::ConnectorError> {
|
||||
let connector_router_data = zsl::ZslRouterData::try_from((
|
||||
&self.get_currency_unit(),
|
||||
req.request.currency,
|
||||
req.request.amount,
|
||||
req,
|
||||
))?;
|
||||
let connector_req = zsl::ZslPaymentsRequest::try_from(&connector_router_data)?;
|
||||
Ok(RequestContent::Json(Box::new(connector_req)))
|
||||
}
|
||||
|
||||
fn build_request(
|
||||
&self,
|
||||
req: &types::PaymentsAuthorizeRouterData,
|
||||
connectors: &settings::Connectors,
|
||||
) -> CustomResult<Option<services::Request>, errors::ConnectorError> {
|
||||
Ok(Some(
|
||||
services::RequestBuilder::new()
|
||||
.method(services::Method::Post)
|
||||
.url(&types::PaymentsAuthorizeType::get_url(
|
||||
self, req, connectors,
|
||||
)?)
|
||||
.attach_default_headers()
|
||||
.headers(types::PaymentsAuthorizeType::get_headers(
|
||||
self, req, connectors,
|
||||
)?)
|
||||
.set_body(types::PaymentsAuthorizeType::get_request_body(
|
||||
self, req, connectors,
|
||||
)?)
|
||||
.build(),
|
||||
))
|
||||
}
|
||||
|
||||
fn handle_response(
|
||||
&self,
|
||||
data: &types::PaymentsAuthorizeRouterData,
|
||||
event_builder: Option<&mut ConnectorEvent>,
|
||||
res: Response,
|
||||
) -> CustomResult<types::PaymentsAuthorizeRouterData, errors::ConnectorError> {
|
||||
let response: zsl::ZslPaymentsResponse = res
|
||||
.response
|
||||
.parse_struct("Zsl PaymentsAuthorizeResponse")
|
||||
.change_context(errors::ConnectorError::ResponseDeserializationFailed)?;
|
||||
event_builder.map(|i| i.set_response_body(&response));
|
||||
router_env::logger::info!(connector_response=?response);
|
||||
types::RouterData::try_from(types::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)
|
||||
}
|
||||
}
|
||||
|
||||
impl ConnectorIntegration<api::PSync, types::PaymentsSyncData, types::PaymentsResponseData>
|
||||
for Zsl
|
||||
{
|
||||
}
|
||||
|
||||
impl ConnectorIntegration<api::Capture, types::PaymentsCaptureData, types::PaymentsResponseData>
|
||||
for Zsl
|
||||
{
|
||||
}
|
||||
|
||||
impl ConnectorIntegration<api::Void, types::PaymentsCancelData, types::PaymentsResponseData>
|
||||
for Zsl
|
||||
{
|
||||
}
|
||||
|
||||
impl ConnectorIntegration<api::Execute, types::RefundsData, types::RefundsResponseData> for Zsl {}
|
||||
|
||||
impl ConnectorIntegration<api::RSync, types::RefundsData, types::RefundsResponseData> for Zsl {}
|
||||
|
||||
#[async_trait::async_trait]
|
||||
impl api::IncomingWebhook for Zsl {
|
||||
fn get_webhook_object_reference_id(
|
||||
&self,
|
||||
_request: &api::IncomingWebhookRequestDetails<'_>,
|
||||
) -> CustomResult<api::webhooks::ObjectReferenceId, errors::ConnectorError> {
|
||||
Err(report!(errors::ConnectorError::WebhooksNotImplemented))
|
||||
}
|
||||
|
||||
fn get_webhook_event_type(
|
||||
&self,
|
||||
_request: &api::IncomingWebhookRequestDetails<'_>,
|
||||
) -> CustomResult<api::IncomingWebhookEvent, errors::ConnectorError> {
|
||||
Err(report!(errors::ConnectorError::WebhooksNotImplemented))
|
||||
}
|
||||
|
||||
fn get_webhook_resource_object(
|
||||
&self,
|
||||
_request: &api::IncomingWebhookRequestDetails<'_>,
|
||||
) -> CustomResult<Box<dyn masking::ErasedMaskSerialize>, errors::ConnectorError> {
|
||||
Err(report!(errors::ConnectorError::WebhooksNotImplemented))
|
||||
}
|
||||
}
|
||||
159
crates/router/src/connector/zsl/transformers.rs
Normal file
159
crates/router/src/connector/zsl/transformers.rs
Normal file
@ -0,0 +1,159 @@
|
||||
use masking::Secret;
|
||||
use serde::{Deserialize, Serialize};
|
||||
|
||||
use crate::{
|
||||
connector::utils::PaymentsAuthorizeRequestData,
|
||||
core::errors,
|
||||
types::{self, domain, storage::enums},
|
||||
};
|
||||
|
||||
//TODO: Fill the struct with respective fields
|
||||
pub struct ZslRouterData<T> {
|
||||
pub amount: i64, // The type of amount that a connector accepts, for example, String, i64, f64, etc.
|
||||
pub router_data: T,
|
||||
}
|
||||
|
||||
impl<T>
|
||||
TryFrom<(
|
||||
&types::api::CurrencyUnit,
|
||||
types::storage::enums::Currency,
|
||||
i64,
|
||||
T,
|
||||
)> for ZslRouterData<T>
|
||||
{
|
||||
type Error = error_stack::Report<errors::ConnectorError>;
|
||||
fn try_from(
|
||||
(_currency_unit, _currency, amount, item): (
|
||||
&types::api::CurrencyUnit,
|
||||
types::storage::enums::Currency,
|
||||
i64,
|
||||
T,
|
||||
),
|
||||
) -> Result<Self, Self::Error> {
|
||||
//Todo : use utils to convert the amount to the type of amount that a connector accepts
|
||||
Ok(Self {
|
||||
amount,
|
||||
router_data: item,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
//TODO: Fill the struct with respective fields
|
||||
#[derive(Default, Debug, Serialize, Eq, PartialEq)]
|
||||
pub struct ZslPaymentsRequest {
|
||||
amount: i64,
|
||||
card: ZslCard,
|
||||
}
|
||||
|
||||
#[derive(Default, Debug, Serialize, Eq, PartialEq)]
|
||||
pub struct ZslCard {
|
||||
number: cards::CardNumber,
|
||||
expiry_month: Secret<String>,
|
||||
expiry_year: Secret<String>,
|
||||
cvc: Secret<String>,
|
||||
complete: bool,
|
||||
}
|
||||
|
||||
impl TryFrom<&ZslRouterData<&types::PaymentsAuthorizeRouterData>> for ZslPaymentsRequest {
|
||||
type Error = error_stack::Report<errors::ConnectorError>;
|
||||
fn try_from(
|
||||
item: &ZslRouterData<&types::PaymentsAuthorizeRouterData>,
|
||||
) -> Result<Self, Self::Error> {
|
||||
match item.router_data.request.payment_method_data.clone() {
|
||||
domain::PaymentMethodData::Card(req_card) => {
|
||||
let card = ZslCard {
|
||||
number: req_card.card_number,
|
||||
expiry_month: req_card.card_exp_month,
|
||||
expiry_year: req_card.card_exp_year,
|
||||
cvc: req_card.card_cvc,
|
||||
complete: item.router_data.request.is_auto_capture()?,
|
||||
};
|
||||
Ok(Self {
|
||||
amount: item.amount.to_owned(),
|
||||
card,
|
||||
})
|
||||
}
|
||||
_ => Err(errors::ConnectorError::NotImplemented("Payment methods".to_string()).into()),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//TODO: Fill the struct with respective fields
|
||||
// Auth Struct
|
||||
pub struct ZslAuthType {
|
||||
pub(super) api_key: Secret<String>,
|
||||
pub(super) merchant_id: Secret<String>,
|
||||
}
|
||||
|
||||
impl TryFrom<&types::ConnectorAuthType> for ZslAuthType {
|
||||
type Error = error_stack::Report<errors::ConnectorError>;
|
||||
fn try_from(auth_type: &types::ConnectorAuthType) -> Result<Self, Self::Error> {
|
||||
match auth_type {
|
||||
types::ConnectorAuthType::BodyKey { api_key, key1 } => Ok(Self {
|
||||
api_key: api_key.to_owned(),
|
||||
merchant_id: key1.to_owned(),
|
||||
}),
|
||||
_ => Err(errors::ConnectorError::FailedToObtainAuthType.into()),
|
||||
}
|
||||
}
|
||||
}
|
||||
// PaymentsResponse
|
||||
//TODO: Append the remaining status flags
|
||||
#[derive(Debug, Clone, Default, Serialize, Deserialize, PartialEq)]
|
||||
#[serde(rename_all = "lowercase")]
|
||||
pub enum ZslPaymentStatus {
|
||||
Succeeded,
|
||||
Failed,
|
||||
#[default]
|
||||
Processing,
|
||||
}
|
||||
|
||||
impl From<ZslPaymentStatus> for enums::AttemptStatus {
|
||||
fn from(item: ZslPaymentStatus) -> Self {
|
||||
match item {
|
||||
ZslPaymentStatus::Succeeded => Self::Charged,
|
||||
ZslPaymentStatus::Failed => Self::Failure,
|
||||
ZslPaymentStatus::Processing => Self::Authorizing,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//TODO: Fill the struct with respective fields
|
||||
#[derive(Default, Debug, Clone, Serialize, Deserialize, PartialEq)]
|
||||
pub struct ZslPaymentsResponse {
|
||||
status: ZslPaymentStatus,
|
||||
id: String,
|
||||
}
|
||||
|
||||
impl<F, T>
|
||||
TryFrom<types::ResponseRouterData<F, ZslPaymentsResponse, T, types::PaymentsResponseData>>
|
||||
for types::RouterData<F, T, types::PaymentsResponseData>
|
||||
{
|
||||
type Error = error_stack::Report<errors::ConnectorError>;
|
||||
fn try_from(
|
||||
item: types::ResponseRouterData<F, ZslPaymentsResponse, T, types::PaymentsResponseData>,
|
||||
) -> Result<Self, Self::Error> {
|
||||
Ok(Self {
|
||||
status: enums::AttemptStatus::from(item.response.status),
|
||||
response: Ok(types::PaymentsResponseData::TransactionResponse {
|
||||
resource_id: types::ResponseId::ConnectorTransactionId(item.response.id),
|
||||
redirection_data: None,
|
||||
mandate_reference: None,
|
||||
connector_metadata: None,
|
||||
network_txn_id: None,
|
||||
connector_response_reference_id: None,
|
||||
incremental_authorization_allowed: None,
|
||||
}),
|
||||
..item.data
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
//TODO: Fill the struct with respective fields
|
||||
#[derive(Default, Debug, Serialize, Deserialize, PartialEq)]
|
||||
pub struct ZslErrorResponse {
|
||||
pub status_code: u16,
|
||||
pub code: String,
|
||||
pub message: String,
|
||||
pub reason: Option<String>,
|
||||
}
|
||||
@ -1916,6 +1916,10 @@ pub(crate) fn validate_auth_and_metadata_type(
|
||||
zen::transformers::ZenAuthType::try_from(val)?;
|
||||
Ok(())
|
||||
}
|
||||
// api_enums::Connector::Zsl => {
|
||||
// zsl::transformers::ZslAuthType::try_from(val)?;
|
||||
// Ok(())
|
||||
// } Added as template code for future usage
|
||||
api_enums::Connector::Signifyd => {
|
||||
signifyd::transformers::SignifydAuthType::try_from(val)?;
|
||||
Ok(())
|
||||
|
||||
@ -185,7 +185,8 @@ default_imp_for_complete_authorize!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
macro_rules! default_imp_for_webhook_source_verification {
|
||||
($($path:ident::$connector:ident),*) => {
|
||||
@ -268,7 +269,8 @@ default_imp_for_webhook_source_verification!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
macro_rules! default_imp_for_create_customer {
|
||||
@ -351,7 +353,8 @@ default_imp_for_create_customer!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
macro_rules! default_imp_for_connector_redirect_response {
|
||||
@ -423,7 +426,8 @@ default_imp_for_connector_redirect_response!(
|
||||
connector::Volt,
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay
|
||||
connector::Worldpay,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
macro_rules! default_imp_for_connector_request_id {
|
||||
@ -438,6 +442,7 @@ macro_rules! default_imp_for_connector_request_id {
|
||||
impl<const T: u8> api::ConnectorTransactionId for connector::DummyConnector<T> {}
|
||||
|
||||
default_imp_for_connector_request_id!(
|
||||
connector::Zsl,
|
||||
connector::Aci,
|
||||
connector::Adyen,
|
||||
connector::Airwallex,
|
||||
@ -579,7 +584,8 @@ default_imp_for_accept_dispute!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
macro_rules! default_imp_for_file_upload {
|
||||
@ -685,7 +691,8 @@ default_imp_for_file_upload!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
macro_rules! default_imp_for_submit_evidence {
|
||||
@ -769,7 +776,8 @@ default_imp_for_submit_evidence!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
macro_rules! default_imp_for_defend_dispute {
|
||||
@ -854,7 +862,8 @@ default_imp_for_defend_dispute!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
macro_rules! default_imp_for_pre_processing_steps{
|
||||
@ -931,7 +940,8 @@ default_imp_for_pre_processing_steps!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
macro_rules! default_imp_for_payouts {
|
||||
@ -999,7 +1009,8 @@ default_imp_for_payouts!(
|
||||
connector::Volt,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
#[cfg(feature = "payouts")]
|
||||
@ -1084,7 +1095,8 @@ default_imp_for_payouts_create!(
|
||||
connector::Volt,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
#[cfg(feature = "payouts")]
|
||||
@ -1172,7 +1184,8 @@ default_imp_for_payouts_eligibility!(
|
||||
connector::Volt,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
#[cfg(feature = "payouts")]
|
||||
@ -1257,7 +1270,8 @@ default_imp_for_payouts_fulfill!(
|
||||
connector::Volt,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
#[cfg(feature = "payouts")]
|
||||
@ -1342,7 +1356,8 @@ default_imp_for_payouts_cancel!(
|
||||
connector::Volt,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
#[cfg(feature = "payouts")]
|
||||
@ -1428,7 +1443,8 @@ default_imp_for_payouts_quote!(
|
||||
connector::Volt,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
#[cfg(feature = "payouts")]
|
||||
@ -1514,7 +1530,8 @@ default_imp_for_payouts_recipient!(
|
||||
connector::Volt,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
macro_rules! default_imp_for_approve {
|
||||
@ -1600,7 +1617,8 @@ default_imp_for_approve!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
macro_rules! default_imp_for_reject {
|
||||
@ -1686,7 +1704,8 @@ default_imp_for_reject!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
macro_rules! default_imp_for_fraud_check {
|
||||
@ -1754,7 +1773,8 @@ default_imp_for_fraud_check!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
#[cfg(feature = "frm")]
|
||||
@ -1840,7 +1860,8 @@ default_imp_for_frm_sale!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
#[cfg(feature = "frm")]
|
||||
@ -1926,7 +1947,8 @@ default_imp_for_frm_checkout!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
#[cfg(feature = "frm")]
|
||||
@ -2012,7 +2034,8 @@ default_imp_for_frm_transaction!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
#[cfg(feature = "frm")]
|
||||
@ -2098,7 +2121,8 @@ default_imp_for_frm_fulfillment!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
#[cfg(feature = "frm")]
|
||||
@ -2184,7 +2208,8 @@ default_imp_for_frm_record_return!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
macro_rules! default_imp_for_incremental_authorization {
|
||||
@ -2269,7 +2294,8 @@ default_imp_for_incremental_authorization!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
macro_rules! default_imp_for_revoking_mandates {
|
||||
@ -2351,7 +2377,8 @@ default_imp_for_revoking_mandates!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
macro_rules! default_imp_for_connector_authentication {
|
||||
@ -2476,5 +2503,6 @@ default_imp_for_connector_authentication!(
|
||||
connector::Wise,
|
||||
connector::Worldline,
|
||||
connector::Worldpay,
|
||||
connector::Zen
|
||||
connector::Zen,
|
||||
connector::Zsl
|
||||
);
|
||||
|
||||
@ -385,6 +385,7 @@ impl ConnectorData {
|
||||
enums::Connector::Tsys => Ok(Box::new(&connector::Tsys)),
|
||||
enums::Connector::Volt => Ok(Box::new(&connector::Volt)),
|
||||
enums::Connector::Zen => Ok(Box::new(&connector::Zen)),
|
||||
// enums::Connector::Zsl => Ok(Box::new(&connector::Zsl)), Added as template code for future usage
|
||||
enums::Connector::Signifyd
|
||||
| enums::Connector::Plaid
|
||||
| enums::Connector::Riskified
|
||||
|
||||
@ -247,6 +247,7 @@ impl ForeignTryFrom<api_enums::Connector> for common_enums::RoutableConnectors {
|
||||
api_enums::Connector::Worldline => Self::Worldline,
|
||||
api_enums::Connector::Worldpay => Self::Worldpay,
|
||||
api_enums::Connector::Zen => Self::Zen,
|
||||
// api_enums::Connector::Zsl => Self::Zsl, Added as template code for future usage
|
||||
#[cfg(feature = "dummy_connector")]
|
||||
api_enums::Connector::DummyConnector1 => Self::DummyConnector1,
|
||||
#[cfg(feature = "dummy_connector")]
|
||||
|
||||
@ -306,7 +306,7 @@ async fn should_sync_refund() {
|
||||
);
|
||||
}
|
||||
|
||||
// Cards Negative scenerios
|
||||
// Cards Negative scenarios
|
||||
// Creates a payment with incorrect CVC.
|
||||
#[actix_web::test]
|
||||
async fn should_fail_payment_for_incorrect_cvc() {
|
||||
|
||||
@ -65,3 +65,4 @@ mod wise;
|
||||
mod worldline;
|
||||
mod worldpay;
|
||||
mod zen;
|
||||
mod zsl;
|
||||
|
||||
@ -206,3 +206,9 @@ api_key="API Key"
|
||||
|
||||
[ebanx]
|
||||
api_key="API Key"
|
||||
|
||||
|
||||
[zsl]
|
||||
api_key="API Key"
|
||||
key1= "Merchant id"
|
||||
|
||||
|
||||
59
crates/router/tests/connectors/zsl.rs
Normal file
59
crates/router/tests/connectors/zsl.rs
Normal file
@ -0,0 +1,59 @@
|
||||
use router::types::{self, storage::enums};
|
||||
use test_utils::connector_auth;
|
||||
|
||||
use crate::utils::{self, ConnectorActions};
|
||||
|
||||
struct ZslTest;
|
||||
impl ConnectorActions for ZslTest {}
|
||||
impl utils::Connector for ZslTest {
|
||||
fn get_data(&self) -> types::api::ConnectorData {
|
||||
use router::connector::Zsl;
|
||||
types::api::ConnectorData {
|
||||
connector: Box::new(&Zsl),
|
||||
connector_name: types::Connector::Adyen,
|
||||
// Added as Dummy connector as template code is added for future usage
|
||||
get_token: types::api::GetToken::Connector,
|
||||
merchant_connector_id: None,
|
||||
}
|
||||
}
|
||||
|
||||
fn get_auth_token(&self) -> types::ConnectorAuthType {
|
||||
utils::to_connector_auth_type(
|
||||
connector_auth::ConnectorAuthentication::new()
|
||||
.zsl
|
||||
.expect("Missing connector authentication configuration")
|
||||
.into(),
|
||||
)
|
||||
}
|
||||
|
||||
fn get_name(&self) -> String {
|
||||
"zsl".to_string()
|
||||
}
|
||||
}
|
||||
|
||||
static CONNECTOR: ZslTest = ZslTest {};
|
||||
|
||||
fn get_default_payment_info() -> Option<utils::PaymentInfo> {
|
||||
None
|
||||
}
|
||||
|
||||
fn payment_method_details() -> Option<types::PaymentsAuthorizeData> {
|
||||
None
|
||||
}
|
||||
|
||||
// Partially captures a payment using the manual capture flow (Non 3DS).
|
||||
#[actix_web::test]
|
||||
async fn should_partially_capture_authorized_payment() {
|
||||
let response = CONNECTOR
|
||||
.authorize_and_capture_payment(
|
||||
payment_method_details(),
|
||||
Some(types::PaymentsCaptureData {
|
||||
amount_to_capture: 50,
|
||||
..utils::PaymentCaptureType::default().0
|
||||
}),
|
||||
get_default_payment_info(),
|
||||
)
|
||||
.await
|
||||
.expect("Capture payment response");
|
||||
assert_eq!(response.status, enums::AttemptStatus::AuthenticationPending);
|
||||
}
|
||||
@ -68,6 +68,7 @@ pub struct ConnectorAuthentication {
|
||||
pub worldpay: Option<BodyKey>,
|
||||
pub worldline: Option<SignatureKey>,
|
||||
pub zen: Option<HeaderKey>,
|
||||
pub zsl: Option<BodyKey>,
|
||||
pub automation_configs: Option<AutomationConfigs>,
|
||||
}
|
||||
|
||||
|
||||
@ -131,6 +131,7 @@ worldpay.base_url = "https://try.access.worldpay.com/"
|
||||
wise.base_url = "https://api.sandbox.transferwise.tech/"
|
||||
zen.base_url = "https://api.zen-test.com/"
|
||||
zen.secondary_base_url = "https://secure.zen-test.com/"
|
||||
zsl.base_url = "https://api.sitoffalb.net/"
|
||||
|
||||
[pm_filters.default]
|
||||
apple_pay = { country = "AU,CN,HK,JP,MO,MY,NZ,SG,TW,AM,AT,AZ,BY,BE,BG,HR,CY,CZ,DK,EE,FO,FI,FR,GE,DE,GR,GL,GG,HU,IS,IE,IM,IT,KZ,JE,LV,LI,LT,LU,MT,MD,MC,ME,NL,NO,PL,PT,RO,SM,RS,SK,SI,ES,SE,CH,UA,GB,AR,CO,CR,BR,MX,PE,BH,IL,JO,KW,PS,QA,SA,AE,CA,UM,US,KR,VN,MA,ZA,VA,CL,SV,GT,HN,PA", currency = "AED,AUD,CHF,CAD,EUR,GBP,HKD,SGD,USD" }
|
||||
@ -191,6 +192,7 @@ cards = [
|
||||
"worldline",
|
||||
"worldpay",
|
||||
"zen",
|
||||
"zsl",
|
||||
]
|
||||
|
||||
[pm_filters.volt]
|
||||
|
||||
@ -7179,10 +7179,10 @@
|
||||
"wise",
|
||||
"worldline",
|
||||
"worldpay",
|
||||
"zen",
|
||||
"signifyd",
|
||||
"plaid",
|
||||
"riskified"
|
||||
"riskified",
|
||||
"zen"
|
||||
]
|
||||
},
|
||||
"ConnectorMetadata": {
|
||||
|
||||
@ -6,7 +6,7 @@ function find_prev_connector() {
|
||||
git checkout $self
|
||||
cp $self $self.tmp
|
||||
# Add new connector to existing list and sort it
|
||||
connectors=(aci adyen airwallex applepay authorizedotnet bambora bankofamerica billwerk bitpay bluesnap boku braintree cashtocode checkout coinbase cryptopay cybersource dlocal dummyconnector ebanx fiserv forte globalpay globepay gocardless helcim iatapay klarna mollie multisafepay nexinets noon nuvei opayo opennode payeezy payme paypal payu placetopay powertranz prophetpay rapyd shift4 square stax stripe threedsecureio trustpay tsys volt wise worldline worldpay "$1")
|
||||
connectors=(aci adyen airwallex applepay authorizedotnet bambora bankofamerica billwerk bitpay bluesnap boku braintree cashtocode checkout coinbase cryptopay cybersource dlocal dummyconnector ebanx fiserv forte globalpay globepay gocardless helcim iatapay klarna mollie multisafepay nexinets noon nuvei opayo opennode payeezy payme paypal payu placetopay powertranz prophetpay rapyd shift4 square stax stripe threedsecureio trustpay tsys volt wise worldline worldpay zsl "$1")
|
||||
IFS=$'\n' sorted=($(sort <<<"${connectors[*]}")); unset IFS
|
||||
res=`echo ${sorted[@]}`
|
||||
sed -i'' -e "s/^ connectors=.*/ connectors=($res \"\$1\")/" $self.tmp
|
||||
|
||||
Reference in New Issue
Block a user