feat(connector): [Adyen] Implement Clearpay in BNPL (#1546)

Co-authored-by: chikke srujan <121822803+srujanchikke@users.noreply.github.com>
Co-authored-by: Sanchith Hegde <22217505+SanchithHegde@users.noreply.github.com>
This commit is contained in:
Sakil Mostak
2023-07-17 14:47:54 +05:30
committed by GitHub
parent c6f745540f
commit abed197366
4 changed files with 105 additions and 9 deletions

View File

@ -267,6 +267,7 @@ pub enum AdyenPaymentMethod<'a> {
BancontactCard(Box<BancontactCardData>),
Bizum(Box<BankRedirectionPMData>),
Blik(Box<BlikRedirectionData>),
ClearPay(Box<AdyenPayLaterData>),
Eps(Box<BankRedirectionWithIssuer<'a>>),
Giropay(Box<BankRedirectionPMData>),
Gpay(Box<AdyenGPay>),
@ -680,6 +681,7 @@ pub enum PaymentType {
Applepay,
Bizum,
Blik,
ClearPay,
Eps,
Giropay,
Googlepay,
@ -919,7 +921,8 @@ fn get_address_info(address: Option<&api_models::payments::Address>) -> Option<A
}
fn get_line_items(item: &types::PaymentsAuthorizeRouterData) -> Vec<LineItem> {
let order_details = item.request.order_details.clone();
let order_details: Option<Vec<payments::OrderDetailsWithAmount>> =
item.request.order_details.clone();
match order_details {
Some(od) => od
.iter()
@ -937,7 +940,7 @@ fn get_line_items(item: &types::PaymentsAuthorizeRouterData) -> Vec<LineItem> {
let line_item = LineItem {
amount_including_tax: Some(item.request.amount),
amount_excluding_tax: Some(item.request.amount),
description: None,
description: item.description.clone(),
id: Some(String::from("Items #1")),
tax_amount: None,
quantity: Some(1),
@ -1178,9 +1181,14 @@ impl<'a> TryFrom<&api::WalletData> for AdyenPaymentMethod<'a> {
}
}
impl<'a> TryFrom<&api::PayLaterData> for AdyenPaymentMethod<'a> {
impl<'a> TryFrom<(&api::PayLaterData, Option<api_enums::CountryAlpha2>)>
for AdyenPaymentMethod<'a>
{
type Error = Error;
fn try_from(pay_later_data: &api::PayLaterData) -> Result<Self, Self::Error> {
fn try_from(
value: (&api::PayLaterData, Option<api_enums::CountryAlpha2>),
) -> Result<Self, Self::Error> {
let (pay_later_data, country_code) = value;
match pay_later_data {
api_models::payments::PayLaterData::KlarnaRedirect { .. } => {
let klarna = AdyenPayLaterData {
@ -1194,9 +1202,25 @@ impl<'a> TryFrom<&api::PayLaterData> for AdyenPaymentMethod<'a> {
})),
),
api_models::payments::PayLaterData::AfterpayClearpayRedirect { .. } => {
Ok(AdyenPaymentMethod::AfterPay(Box::new(AdyenPayLaterData {
payment_type: PaymentType::Afterpaytouch,
})))
if let Some(country) = country_code {
match country {
api_enums::CountryAlpha2::IT
| api_enums::CountryAlpha2::FR
| api_enums::CountryAlpha2::ES
| api_enums::CountryAlpha2::GB => {
Ok(AdyenPaymentMethod::ClearPay(Box::new(AdyenPayLaterData {
payment_type: PaymentType::ClearPay,
})))
}
_ => Ok(AdyenPaymentMethod::AfterPay(Box::new(AdyenPayLaterData {
payment_type: PaymentType::Afterpaytouch,
}))),
}
} else {
Err(errors::ConnectorError::MissingRequiredField {
field_name: "country",
})?
}
}
api_models::payments::PayLaterData::PayBrightRedirect { .. } => {
Ok(AdyenPaymentMethod::PayBright(Box::new(PayBrightData {
@ -1647,7 +1671,8 @@ impl<'a> TryFrom<(&types::PaymentsAuthorizeRouterData, &api::PayLaterData)>
let auth_type = AdyenAuthType::try_from(&item.connector_auth_type)?;
let browser_info = get_browser_info(item)?;
let additional_data = get_additional_data(item);
let payment_method = AdyenPaymentMethod::try_from(paylater_data)?;
let country_code = get_country_code(item);
let payment_method = AdyenPaymentMethod::try_from((paylater_data, country_code))?;
let shopper_interaction = AdyenShopperInteraction::from(item);
let (recurring_processing_model, store_payment_method, shopper_reference) =
get_recurring_processing_model(item)?;
@ -1656,7 +1681,6 @@ impl<'a> TryFrom<(&types::PaymentsAuthorizeRouterData, &api::PayLaterData)>
let shopper_email = item.request.email.clone();
let billing_address = get_address_info(item.address.billing.as_ref());
let delivery_address = get_address_info(item.address.shipping.as_ref());
let country_code = get_country_code(item);
let line_items = Some(get_line_items(item));
let telephone_number = get_telephone_number(item);
Ok(AdyenPaymentRequest {

View File

@ -192,6 +192,23 @@ async fn should_make_adyen_bizum_payment(driver: WebDriver) -> Result<(), WebDri
Ok(())
}
async fn should_make_adyen_clearpay_payment(driver: WebDriver) -> Result<(), WebDriverError> {
let conn = AdyenSeleniumTest {};
conn.make_clearpay_payment(
driver,
&format!("{CHEKOUT_BASE_URL}/saved/163"),
vec![
Event::Assert(Assert::IsPresent("Google")),
Event::Assert(Assert::ContainsAny(
Selector::QueryParamStr,
vec!["status=succeeded"],
)),
],
)
.await?;
Ok(())
}
#[test]
#[serial]
#[ignore]
@ -243,4 +260,10 @@ fn should_make_adyen_bizum_payment_test() {
tester!(should_make_adyen_bizum_payment);
}
#[test]
#[serial]
fn should_make_adyen_clearpay_payment_test() {
tester!(should_make_adyen_clearpay_payment);
}
// https://hs-payments-test.netlify.app/paypal-redirect?amount=70.00&country=US&currency=USD&mandate_data[customer_acceptance][acceptance_type]=offline&mandate_data[customer_acceptance][accepted_at]=1963-05-03T04:07:52.723Z&mandate_data[customer_acceptance][online][ip_address]=127.0.0.1&mandate_data[customer_acceptance][online][user_agent]=amet%20irure%20esse&mandate_data[mandate_type][multi_use][amount]=700&mandate_data[mandate_type][multi_use][currency]=USD&apikey=dev_uFpxA0r6jjbVaxHSY3X0BZLL3erDUzvg3i51abwB1Bknu3fdiPxw475DQgnByn1z

View File

@ -542,6 +542,53 @@ pub trait SeleniumTest {
pypl_actions.extend(actions);
self.complete_actions(&web_driver, pypl_actions).await
}
async fn make_clearpay_payment(
&self,
driver: WebDriver,
url: &str,
actions: Vec<Event<'_>>,
) -> Result<(), WebDriverError> {
self.complete_actions(
&driver,
vec![
Event::Trigger(Trigger::Goto(url)),
Event::Trigger(Trigger::Click(By::Id("card-submit-btn"))),
],
)
.await?;
let (email, pass) = (
&self
.get_configs()
.automation_configs
.unwrap()
.clearpay_email
.unwrap(),
&self
.get_configs()
.automation_configs
.unwrap()
.clearpay_pass
.unwrap(),
);
let mut clearpay_actions = vec![
Event::Trigger(Trigger::Sleep(3)),
Event::EitherOr(
Assert::IsPresent("Review your order | Clearpay"),
vec![Event::Trigger(Trigger::Click(By::ClassName("ai_az")))],
vec![
Event::Trigger(Trigger::SendKeys(By::ClassName("n8_fl"), email)),
Event::Trigger(Trigger::Click(By::ClassName("ai_az"))),
Event::Trigger(Trigger::Sleep(3)),
Event::Trigger(Trigger::SendKeys(By::ClassName("n8_fl"), pass)),
Event::Trigger(Trigger::Click(By::ClassName("ai_az"))),
Event::Trigger(Trigger::Sleep(10)), //Time needed for login
Event::Trigger(Trigger::Click(By::ClassName("ai_az"))),
],
),
];
clearpay_actions.extend(actions);
self.complete_actions(&driver, clearpay_actions).await
}
}
async fn is_text_present_now(driver: &WebDriver, key: &str) -> WebDriverResult<bool> {
let mut xpath = "//*[contains(text(),'".to_owned();

View File

@ -249,6 +249,8 @@ pub struct AutomationConfigs {
pub pypl_pass: Option<String>,
pub gmail_email: Option<String>,
pub gmail_pass: Option<String>,
pub clearpay_email: Option<String>,
pub clearpay_pass: Option<String>,
pub configs_url: Option<String>,
pub stripe_pub_key: Option<String>,
pub testcases_path: Option<String>,