Skip to content

Commit

Permalink
Merge branch 'main' into noon_issue_2277
Browse files Browse the repository at this point in the history
  • Loading branch information
SagarDevAchar authored Oct 25, 2023
2 parents 6752cf6 + e6272c6 commit d007b0b
Show file tree
Hide file tree
Showing 14 changed files with 164 additions and 38 deletions.
9 changes: 9 additions & 0 deletions .cargo/config.toml
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,15 @@ rustflags = [
# "-Wmissing_docs",
"-Wrust_2018_idioms",
"-Wunused_qualifications",
"--cfg",
"uuid_unstable"
]


[build]
rustdocflags = [
"--cfg",
"uuid_unstable"
]

[alias]
Expand Down
11 changes: 9 additions & 2 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions crates/api_models/src/refunds.rs
Original file line number Diff line number Diff line change
Expand Up @@ -124,6 +124,7 @@ pub struct RefundResponse {
/// The connector used for the refund and the corresponding payment
#[schema(example = "stripe")]
pub connector: String,
pub profile_id: Option<String>,
}

#[derive(Debug, Clone, Eq, PartialEq, Deserialize, Serialize, ToSchema)]
Expand Down
22 changes: 11 additions & 11 deletions crates/router/src/configs/settings.rs
Original file line number Diff line number Diff line change
Expand Up @@ -491,17 +491,17 @@ impl From<QueueStrategy> for bb8::QueueStrategy {
}

#[cfg(not(feature = "kms"))]
impl Into<storage_impl::config::Database> for Database {
fn into(self) -> storage_impl::config::Database {
storage_impl::config::Database {
username: self.username,
password: self.password,
host: self.host,
port: self.port,
dbname: self.dbname,
pool_size: self.pool_size,
connection_timeout: self.connection_timeout,
queue_strategy: self.queue_strategy.into(),
impl From<Database> for storage_impl::config::Database {
fn from(val: Database) -> Self {
Self {
username: val.username,
password: val.password,
host: val.host,
port: val.port,
dbname: val.dbname,
pool_size: val.pool_size,
connection_timeout: val.connection_timeout,
queue_strategy: val.queue_strategy.into(),
}
}
}
Expand Down
12 changes: 10 additions & 2 deletions crates/router/src/connector/cryptopay.rs
Original file line number Diff line number Diff line change
Expand Up @@ -171,8 +171,6 @@ impl ConnectorCommon for Cryptopay {
}
}

impl ConnectorValidation for Cryptopay {}

impl ConnectorIntegration<api::Session, types::PaymentsSessionData, types::PaymentsResponseData>
for Cryptopay
{
Expand Down Expand Up @@ -279,6 +277,16 @@ impl ConnectorIntegration<api::Authorize, types::PaymentsAuthorizeData, types::P
}
}

impl ConnectorValidation for Cryptopay {
fn validate_psync_reference_id(
&self,
_data: &types::PaymentsSyncRouterData,
) -> CustomResult<(), errors::ConnectorError> {
// since we can make psync call with our reference_id, having connector_transaction_id is not an mandatory criteria
Ok(())
}
}

impl ConnectorIntegration<api::PSync, types::PaymentsSyncData, types::PaymentsResponseData>
for Cryptopay
{
Expand Down
20 changes: 17 additions & 3 deletions crates/router/src/connector/cryptopay/transformers.rs
Original file line number Diff line number Diff line change
Expand Up @@ -69,9 +69,23 @@ impl TryFrom<&CryptopayRouterData<&types::PaymentsAuthorizeRouterData>>
custom_id: item.router_data.connector_request_reference_id.clone(),
})
}
_ => Err(errors::ConnectorError::NotImplemented(
"payment method".to_string(),
)),
api_models::payments::PaymentMethodData::Card(_)
| api_models::payments::PaymentMethodData::CardRedirect(_)
| api_models::payments::PaymentMethodData::Wallet(_)
| api_models::payments::PaymentMethodData::PayLater(_)
| api_models::payments::PaymentMethodData::BankRedirect(_)
| api_models::payments::PaymentMethodData::BankDebit(_)
| api_models::payments::PaymentMethodData::BankTransfer(_)
| api_models::payments::PaymentMethodData::MandatePayment {}
| api_models::payments::PaymentMethodData::Reward {}
| api_models::payments::PaymentMethodData::Upi(_)
| api_models::payments::PaymentMethodData::Voucher(_)
| api_models::payments::PaymentMethodData::GiftCard(_) => {
Err(errors::ConnectorError::NotSupported {
message: utils::SELECTED_PAYMENT_METHOD.to_string(),
connector: "CryptoPay",
})
}
}?;
Ok(cryptopay_request)
}
Expand Down
13 changes: 12 additions & 1 deletion crates/router/src/connector/cybersource.rs
Original file line number Diff line number Diff line change
Expand Up @@ -93,6 +93,10 @@ impl ConnectorCommon for Cybersource {
connectors.cybersource.base_url.as_ref()
}

fn get_currency_unit(&self) -> api::CurrencyUnit {
api::CurrencyUnit::Minor
}

fn build_error_response(
&self,
res: types::Response,
Expand Down Expand Up @@ -468,7 +472,14 @@ impl ConnectorIntegration<api::Authorize, types::PaymentsAuthorizeData, types::P
&self,
req: &types::PaymentsAuthorizeRouterData,
) -> CustomResult<Option<types::RequestBody>, errors::ConnectorError> {
let connector_request = cybersource::CybersourcePaymentsRequest::try_from(req)?;
let connector_router_data = cybersource::CybersourceRouterData::try_from((
&self.get_currency_unit(),
req.request.currency,
req.request.amount,
req,
))?;
let connector_request =
cybersource::CybersourcePaymentsRequest::try_from(&connector_router_data)?;
let cybersource_payments_request = types::RequestBody::log_and_get_request_body(
&connector_request,
utils::Encode::<cybersource::CybersourcePaymentsRequest>::encode_to_string_of_json,
Expand Down
55 changes: 46 additions & 9 deletions crates/router/src/connector/cybersource/transformers.rs
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,37 @@ use crate::{
},
};

#[derive(Debug, Serialize)]
pub struct CybersourceRouterData<T> {
pub amount: String,
pub router_data: T,
}

impl<T>
TryFrom<(
&types::api::CurrencyUnit,
types::storage::enums::Currency,
i64,
T,
)> for CybersourceRouterData<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> {
let amount = utils::get_amount_as_string(currency_unit, amount, currency)?;
Ok(Self {
amount,
router_data: item,
})
}
}

#[derive(Default, Debug, Serialize, Eq, PartialEq)]
#[serde(rename_all = "camelCase")]
pub struct CybersourcePaymentsRequest {
Expand Down Expand Up @@ -109,27 +140,33 @@ fn build_bill_to(
})
}

impl TryFrom<&types::PaymentsAuthorizeRouterData> for CybersourcePaymentsRequest {
impl TryFrom<&CybersourceRouterData<&types::PaymentsAuthorizeRouterData>>
for CybersourcePaymentsRequest
{
type Error = error_stack::Report<errors::ConnectorError>;
fn try_from(item: &types::PaymentsAuthorizeRouterData) -> Result<Self, Self::Error> {
match item.request.payment_method_data.clone() {
fn try_from(
item: &CybersourceRouterData<&types::PaymentsAuthorizeRouterData>,
) -> Result<Self, Self::Error> {
match item.router_data.request.payment_method_data.clone() {
api::PaymentMethodData::Card(ccard) => {
let phone = item.get_billing_phone()?;
let phone = item.router_data.get_billing_phone()?;
let phone_number = phone.get_number()?;
let country_code = phone.get_country_code()?;
let number_with_code =
Secret::new(format!("{}{}", country_code, phone_number.peek()));
let email = item
.router_data
.request
.email
.clone()
.ok_or_else(utils::missing_field_err("email"))?;
let bill_to = build_bill_to(item.get_billing()?, email, number_with_code)?;
let bill_to =
build_bill_to(item.router_data.get_billing()?, email, number_with_code)?;

let order_information = OrderInformationWithBill {
amount_details: Amount {
total_amount: item.request.amount.to_string(),
currency: item.request.currency.to_string().to_uppercase(),
total_amount: item.amount.to_owned(),
currency: item.router_data.request.currency.to_string().to_uppercase(),
},
bill_to,
};
Expand All @@ -145,14 +182,14 @@ impl TryFrom<&types::PaymentsAuthorizeRouterData> for CybersourcePaymentsRequest

let processing_information = ProcessingInformation {
capture: matches!(
item.request.capture_method,
item.router_data.request.capture_method,
Some(enums::CaptureMethod::Automatic) | None
),
capture_options: None,
};

let client_reference_information = ClientReferenceInformation {
code: Some(item.connector_request_reference_id.clone()),
code: Some(item.router_data.connector_request_reference_id.clone()),
};

Ok(Self {
Expand Down
2 changes: 1 addition & 1 deletion crates/router/src/connector/utils.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1077,7 +1077,7 @@ pub fn get_amount_as_string(
currency: diesel_models::enums::Currency,
) -> Result<String, error_stack::Report<errors::ConnectorError>> {
let amount = match currency_unit {
types::api::CurrencyUnit::Minor => amount.to_string(),
types::api::CurrencyUnit::Minor => to_currency_lower_unit(amount.to_string(), currency)?,
types::api::CurrencyUnit::Base => to_currency_base_unit(amount, currency)?,
};
Ok(amount)
Expand Down
39 changes: 31 additions & 8 deletions crates/router/src/connector/worldline/transformers.rs
Original file line number Diff line number Diff line change
Expand Up @@ -247,11 +247,19 @@ impl
make_bank_redirect_request(&item.router_data.request, bank_redirect)?,
))
}
_ => {
return Err(
errors::ConnectorError::NotImplemented("Payment methods".to_string()).into(),
)
}
api::PaymentMethodData::CardRedirect(_)
| api::PaymentMethodData::Wallet(_)
| api::PaymentMethodData::PayLater(_)
| api::PaymentMethodData::BankDebit(_)
| api::PaymentMethodData::BankTransfer(_)
| api::PaymentMethodData::Crypto(_)
| api::PaymentMethodData::MandatePayment
| api::PaymentMethodData::Reward
| api::PaymentMethodData::Upi(_)
| api::PaymentMethodData::Voucher(_)
| api::PaymentMethodData::GiftCard(_) => Err(errors::ConnectorError::NotImplemented(
utils::get_unimplemented_payment_method_error_message("worldline"),
))?,
};

let customer =
Expand Down Expand Up @@ -393,10 +401,25 @@ fn make_bank_redirect_request(
},
809,
),
_ => {
return Err(
errors::ConnectorError::NotImplemented("Payment methods".to_string()).into(),
payments::BankRedirectData::BancontactCard { .. }
| payments::BankRedirectData::Bizum {}
| payments::BankRedirectData::Blik { .. }
| payments::BankRedirectData::Eps { .. }
| payments::BankRedirectData::Interac { .. }
| payments::BankRedirectData::OnlineBankingCzechRepublic { .. }
| payments::BankRedirectData::OnlineBankingFinland { .. }
| payments::BankRedirectData::OnlineBankingPoland { .. }
| payments::BankRedirectData::OnlineBankingSlovakia { .. }
| payments::BankRedirectData::OpenBankingUk { .. }
| payments::BankRedirectData::Przelewy24 { .. }
| payments::BankRedirectData::Sofort { .. }
| payments::BankRedirectData::Trustly { .. }
| payments::BankRedirectData::OnlineBankingFpx { .. }
| payments::BankRedirectData::OnlineBankingThailand { .. } => {
return Err(errors::ConnectorError::NotImplemented(
utils::get_unimplemented_payment_method_error_message("worldline"),
)
.into())
}
};
Ok(RedirectPaymentMethod {
Expand Down
2 changes: 2 additions & 0 deletions crates/router/src/core/refunds.rs
Original file line number Diff line number Diff line change
Expand Up @@ -602,6 +602,7 @@ pub async fn validate_and_create_refund(
.set_description(req.reason.clone())
.set_attempt_id(payment_attempt.attempt_id.clone())
.set_refund_reason(req.reason)
.set_profile_id(payment_intent.profile_id.clone())
.to_owned();

refund = db
Expand Down Expand Up @@ -704,6 +705,7 @@ impl ForeignFrom<storage::Refund> for api::RefundResponse {
currency: refund.currency.to_string(),
reason: refund.refund_reason,
status: refund.refund_status.foreign_into(),
profile_id: refund.profile_id,
metadata: refund.metadata,
error_message: refund.refund_error_message,
error_code: refund.refund_error_code,
Expand Down
2 changes: 1 addition & 1 deletion crates/router_env/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ strum = { version = "0.24.1", features = ["derive"] }
time = { version = "0.3.21", default-features = false, features = ["formatting"] }
tokio = { version = "1.28.2" }
tracing = { version = "=0.1.36" }
tracing-actix-web = { version = "0.7.5", features = ["opentelemetry_0_19"], optional = true }
tracing-actix-web = { version = "0.7.8", features = ["opentelemetry_0_19", "uuid_v7"], optional = true }
tracing-appender = { version = "0.2.2" }
tracing-attributes = "=0.1.22"
tracing-opentelemetry = { version = "0.19.0" }
Expand Down
4 changes: 4 additions & 0 deletions openapi/openapi_spec.json
Original file line number Diff line number Diff line change
Expand Up @@ -10680,6 +10680,10 @@
"type": "string",
"description": "The connector used for the refund and the corresponding payment",
"example": "stripe"
},
"profile_id": {
"type": "string",
"nullable": true
}
}
},
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,3 +28,13 @@ if (jsonData?.refund_id) {
"INFO - Unable to assign variable {{refund_id}}, as jsonData.refund_id is undefined.",
);
}


// Response body should have "profile_id" and not "null"
pm.test(
"[POST]::/payments - Content check if 'profile_id' exists and is not 'null'",
function () {
pm.expect(typeof jsonData.profile_id !== "undefined").to.be.true;
pm.expect(jsonData.profile_id).is.not.null;
},
);

0 comments on commit d007b0b

Please sign in to comment.