mirror of
https://github.com/juspay/hyperswitch.git
synced 2025-11-01 19:42:27 +08:00
feat(pm_list): add required fields for sofort (#3192)
Co-authored-by: hyperswitch-bot[bot] <148525504+hyperswitch-bot[bot]@users.noreply.github.com> Co-authored-by: Prasunna Soppa <70575890+prasunna09@users.noreply.github.com>
This commit is contained in:
@ -374,13 +374,14 @@ slack_invite_url = "https://www.example.com/" # Slack invite url for hyperswit
|
||||
discord_invite_url = "https://www.example.com/" # Discord invite url for hyperswitch
|
||||
|
||||
[mandates.supported_payment_methods]
|
||||
card.credit = { connector_list = "stripe,adyen,cybersource" } # Mandate supported payment method type and connector for card
|
||||
wallet.paypal = { connector_list = "adyen" } # Mandate supported payment method type and connector for wallets
|
||||
pay_later.klarna = { connector_list = "adyen" } # Mandate supported payment method type and connector for pay_later
|
||||
bank_debit.ach = { connector_list = "gocardless" } # Mandate supported payment method type and connector for bank_debit
|
||||
bank_debit.becs = { connector_list = "gocardless" } # Mandate supported payment method type and connector for bank_debit
|
||||
bank_debit.sepa = { connector_list = "gocardless" } # Mandate supported payment method type and connector for bank_debit
|
||||
bank_redirect.ideal = { connector_list = "stripe,adyen" } # Mandate supported payment method type and connector for bank_redirect
|
||||
card.credit = { connector_list = "stripe,adyen,cybersource" } # Mandate supported payment method type and connector for card
|
||||
wallet.paypal = { connector_list = "adyen" } # Mandate supported payment method type and connector for wallets
|
||||
pay_later.klarna = { connector_list = "adyen" } # Mandate supported payment method type and connector for pay_later
|
||||
bank_debit.ach = { connector_list = "gocardless" } # Mandate supported payment method type and connector for bank_debit
|
||||
bank_debit.becs = { connector_list = "gocardless" } # Mandate supported payment method type and connector for bank_debit
|
||||
bank_debit.sepa = { connector_list = "gocardless" } # Mandate supported payment method type and connector for bank_debit
|
||||
bank_redirect.ideal = {connector_list = "stripe,adyen,globalpay"} # Mandate supported payment method type and connector for bank_redirect
|
||||
bank_redirect.sofort = {connector_list = "stripe,adyen,globalpay"}
|
||||
|
||||
|
||||
# Required fields info used while listing the payment_method_data
|
||||
|
||||
@ -474,7 +474,8 @@ card.debit = { connector_list = "stripe,adyen,authorizedotnet,cybersource,global
|
||||
bank_debit.ach = { connector_list = "gocardless"}
|
||||
bank_debit.becs = { connector_list = "gocardless"}
|
||||
bank_debit.sepa = { connector_list = "gocardless"}
|
||||
bank_redirect.ideal = {connector_list = "stripe,adyen"}
|
||||
bank_redirect.ideal = {connector_list = "stripe,adyen,globalpay"}
|
||||
bank_redirect.sofort = {connector_list = "stripe,adyen,globalpay"}
|
||||
|
||||
[connector_request_reference_id_config]
|
||||
merchant_ids_send_payment_id_as_connector_request_id = []
|
||||
|
||||
@ -340,7 +340,8 @@ card.debit = {connector_list = "stripe,adyen,authorizedotnet,cybersource,globalp
|
||||
bank_debit.ach = { connector_list = "gocardless"}
|
||||
bank_debit.becs = { connector_list = "gocardless"}
|
||||
bank_debit.sepa = { connector_list = "gocardless"}
|
||||
bank_redirect.ideal = {connector_list = "stripe,adyen"}
|
||||
bank_redirect.ideal = {connector_list = "stripe,adyen,globalpay"}
|
||||
bank_redirect.sofort = {connector_list = "stripe,adyen,globalpay"}
|
||||
|
||||
[connector_customer]
|
||||
connector_list = "gocardless,stax,stripe"
|
||||
|
||||
@ -1336,15 +1336,15 @@ pub enum BankRedirectData {
|
||||
},
|
||||
Sofort {
|
||||
/// The billing details for bank redirection
|
||||
billing_details: BankRedirectBilling,
|
||||
billing_details: Option<BankRedirectBilling>,
|
||||
|
||||
/// The country for bank payment
|
||||
#[schema(value_type = CountryAlpha2, example = "US")]
|
||||
country: api_enums::CountryAlpha2,
|
||||
country: Option<api_enums::CountryAlpha2>,
|
||||
|
||||
/// The preferred language
|
||||
#[schema(example = "en")]
|
||||
preferred_language: String,
|
||||
preferred_language: Option<String>,
|
||||
},
|
||||
Trustly {
|
||||
/// The country for bank payment
|
||||
|
||||
@ -4750,14 +4750,303 @@ impl Default for super::settings::RequiredFields {
|
||||
ConnectorFields {
|
||||
fields: HashMap::from([
|
||||
(
|
||||
enums::Connector::Stripe,
|
||||
enums::Connector::Aci,
|
||||
RequiredFieldFinal {
|
||||
mandate: HashMap::new(),
|
||||
non_mandate: HashMap::from([
|
||||
("payment_method_data.bank_redirect.sofort.country".to_string(),
|
||||
RequiredFieldInfo {
|
||||
required_field: "payment_method_data.bank_redirect.sofort.country".to_string(),
|
||||
display_name: "country".to_string(),
|
||||
field_type: enums::FieldType::UserCountry {
|
||||
options: vec![
|
||||
"ES".to_string(),
|
||||
"GB".to_string(),
|
||||
"SE".to_string(),
|
||||
"AT".to_string(),
|
||||
"NL".to_string(),
|
||||
"DE".to_string(),
|
||||
"CH".to_string(),
|
||||
"BE".to_string(),
|
||||
"FR".to_string(),
|
||||
"FI".to_string(),
|
||||
"IT".to_string(),
|
||||
"PL".to_string(),
|
||||
]
|
||||
},
|
||||
value: None,
|
||||
}
|
||||
)
|
||||
]),
|
||||
common: HashMap::new(),
|
||||
}
|
||||
),
|
||||
(
|
||||
enums::Connector::Adyen,
|
||||
RequiredFieldFinal {
|
||||
mandate: HashMap::new(),
|
||||
non_mandate: HashMap::new(),
|
||||
common: HashMap::new(),
|
||||
}
|
||||
),
|
||||
]),
|
||||
(
|
||||
enums::Connector::Globalpay,
|
||||
RequiredFieldFinal {
|
||||
mandate: HashMap::new(),
|
||||
non_mandate: HashMap::new(),
|
||||
common: HashMap::from([
|
||||
("billing.address.country".to_string(),
|
||||
RequiredFieldInfo {
|
||||
required_field: "billing.address.country".to_string(),
|
||||
display_name: "country".to_string(),
|
||||
field_type: enums::FieldType::UserAddressCountry {
|
||||
options: vec![
|
||||
"AT".to_string(),
|
||||
"BE".to_string(),
|
||||
"DE".to_string(),
|
||||
"ES".to_string(),
|
||||
"IT".to_string(),
|
||||
"NL".to_string(),
|
||||
]
|
||||
},
|
||||
value: None,
|
||||
}
|
||||
)
|
||||
]),
|
||||
}
|
||||
),
|
||||
(
|
||||
enums::Connector::Mollie,
|
||||
RequiredFieldFinal {
|
||||
mandate: HashMap::new(),
|
||||
non_mandate: HashMap::new(),
|
||||
common: HashMap::new(),
|
||||
}
|
||||
),
|
||||
(
|
||||
enums::Connector::Nexinets,
|
||||
RequiredFieldFinal {
|
||||
mandate: HashMap::new(),
|
||||
non_mandate: HashMap::new(),
|
||||
common: HashMap::new(),
|
||||
}
|
||||
),
|
||||
(
|
||||
enums::Connector::Nuvei,
|
||||
RequiredFieldFinal {
|
||||
mandate: HashMap::new(),
|
||||
non_mandate:HashMap::from([
|
||||
(
|
||||
"email".to_string(),
|
||||
RequiredFieldInfo {
|
||||
required_field: "email".to_string(),
|
||||
display_name: "email".to_string(),
|
||||
field_type: enums::FieldType::UserEmailAddress,
|
||||
value: None,
|
||||
}
|
||||
),
|
||||
(
|
||||
"billing.address.first_name".to_string(),
|
||||
RequiredFieldInfo {
|
||||
required_field: "billing.address.first_name".to_string(),
|
||||
display_name: "billing_first_name".to_string(),
|
||||
field_type: enums::FieldType::UserBillingName,
|
||||
value: None,
|
||||
}
|
||||
),
|
||||
(
|
||||
"billing.address.last_name".to_string(),
|
||||
RequiredFieldInfo {
|
||||
required_field: "billing.address.last_name".to_string(),
|
||||
display_name: "billing_last_name".to_string(),
|
||||
field_type: enums::FieldType::UserBillingName,
|
||||
value: None,
|
||||
}
|
||||
),
|
||||
(
|
||||
"billing.address.country".to_string(),
|
||||
RequiredFieldInfo {
|
||||
required_field: "billing.address.country".to_string(),
|
||||
display_name: "country".to_string(),
|
||||
field_type: enums::FieldType::UserAddressCountry{
|
||||
options: vec![
|
||||
"ES".to_string(),
|
||||
"GB".to_string(),
|
||||
"IT".to_string(),
|
||||
"DE".to_string(),
|
||||
"FR".to_string(),
|
||||
"AT".to_string(),
|
||||
"BE".to_string(),
|
||||
"NL".to_string(),
|
||||
"BE".to_string(),
|
||||
"SK".to_string(),
|
||||
]
|
||||
},
|
||||
value: None,
|
||||
}
|
||||
)]
|
||||
),
|
||||
common: HashMap::new(),
|
||||
}
|
||||
),
|
||||
(
|
||||
enums::Connector::Paypal,
|
||||
RequiredFieldFinal {
|
||||
mandate: HashMap::new(),
|
||||
non_mandate: HashMap::from([
|
||||
("payment_method_data.bank_redirect.sofort.country".to_string(),
|
||||
RequiredFieldInfo {
|
||||
required_field: "payment_method_data.bank_redirect.sofort.country".to_string(),
|
||||
display_name: "country".to_string(),
|
||||
field_type: enums::FieldType::UserCountry {
|
||||
options: vec![
|
||||
"ES".to_string(),
|
||||
"GB".to_string(),
|
||||
"AT".to_string(),
|
||||
"NL".to_string(),
|
||||
"DE".to_string(),
|
||||
"BE".to_string(),
|
||||
]
|
||||
},
|
||||
value: None,
|
||||
}
|
||||
),
|
||||
(
|
||||
"payment_method_data.bank_redirect.sofort.billing_details.billing_name".to_string(),
|
||||
RequiredFieldInfo {
|
||||
required_field: "payment_method_data.bank_redirect.sofort.billing_details.billing_name".to_string(),
|
||||
display_name: "billing_name".to_string(),
|
||||
field_type: enums::FieldType::UserBillingName,
|
||||
value: None,
|
||||
}
|
||||
)
|
||||
]),
|
||||
common: HashMap::new(),
|
||||
}
|
||||
),
|
||||
(
|
||||
enums::Connector::Shift4,
|
||||
RequiredFieldFinal {
|
||||
mandate: HashMap::new(),
|
||||
non_mandate: HashMap::new(),
|
||||
common: HashMap::new(),
|
||||
}
|
||||
),
|
||||
(
|
||||
enums::Connector::Stripe,
|
||||
RequiredFieldFinal {
|
||||
mandate: HashMap::from([
|
||||
(
|
||||
"payment_method_data.bank_redirect.sofort.billing_details.email".to_string(),
|
||||
RequiredFieldInfo {
|
||||
required_field: "payment_method_data.bank_redirect.sofort.billing_details.email".to_string(),
|
||||
display_name: "email".to_string(),
|
||||
field_type: enums::FieldType::UserEmailAddress,
|
||||
value: None,
|
||||
}
|
||||
),
|
||||
(
|
||||
"payment_method_data.bank_redirect.sofort.billing_details.billing_name".to_string(),
|
||||
RequiredFieldInfo {
|
||||
required_field: "payment_method_data.bank_redirect.sofort.billing_details.billing_name".to_string(),
|
||||
display_name: "billing_name".to_string(),
|
||||
field_type: enums::FieldType::UserBillingName,
|
||||
value: None,
|
||||
}
|
||||
)
|
||||
]),
|
||||
non_mandate : HashMap::from([
|
||||
("payment_method_data.bank_redirect.sofort.country".to_string(),
|
||||
RequiredFieldInfo {
|
||||
required_field: "payment_method_data.bank_redirect.sofort.country".to_string(),
|
||||
display_name: "country".to_string(),
|
||||
field_type: enums::FieldType::UserCountry {
|
||||
options: vec![
|
||||
"ES".to_string(),
|
||||
"AT".to_string(),
|
||||
"NL".to_string(),
|
||||
"DE".to_string(),
|
||||
"BE".to_string(),
|
||||
]
|
||||
},
|
||||
value: None,
|
||||
}
|
||||
)]),
|
||||
common: HashMap::new(
|
||||
|
||||
),
|
||||
}
|
||||
),
|
||||
(
|
||||
enums::Connector::Trustpay,
|
||||
RequiredFieldFinal {
|
||||
mandate: HashMap::new(),
|
||||
non_mandate: HashMap::from([
|
||||
(
|
||||
"billing.address.first_name".to_string(),
|
||||
RequiredFieldInfo {
|
||||
required_field: "billing.address.first_name".to_string(),
|
||||
display_name: "billing_first_name".to_string(),
|
||||
field_type: enums::FieldType::UserBillingName,
|
||||
value: None,
|
||||
}
|
||||
),
|
||||
(
|
||||
"billing.address.line1".to_string(),
|
||||
RequiredFieldInfo {
|
||||
required_field: "billing.address.line1".to_string(),
|
||||
display_name: "line1".to_string(),
|
||||
field_type: enums::FieldType::UserAddressLine1,
|
||||
value: None,
|
||||
}
|
||||
),
|
||||
(
|
||||
"billing.address.city".to_string(),
|
||||
RequiredFieldInfo {
|
||||
required_field: "billing.address.city".to_string(),
|
||||
display_name: "city".to_string(),
|
||||
field_type: enums::FieldType::UserAddressCity,
|
||||
value: None,
|
||||
}
|
||||
),
|
||||
(
|
||||
"billing.address.zip".to_string(),
|
||||
RequiredFieldInfo {
|
||||
required_field: "billing.address.zip".to_string(),
|
||||
display_name: "zip".to_string(),
|
||||
field_type: enums::FieldType::UserAddressPincode,
|
||||
value: None,
|
||||
}
|
||||
),
|
||||
(
|
||||
"billing.address.country".to_string(),
|
||||
RequiredFieldInfo {
|
||||
required_field: "billing.address.country".to_string(),
|
||||
display_name: "country".to_string(),
|
||||
field_type: enums::FieldType::UserAddressCountry {
|
||||
options: vec![
|
||||
"ES".to_string(),
|
||||
"GB".to_string(),
|
||||
"SE".to_string(),
|
||||
"AT".to_string(),
|
||||
"NL".to_string(),
|
||||
"DE".to_string(),
|
||||
"CH".to_string(),
|
||||
"BE".to_string(),
|
||||
"FR".to_string(),
|
||||
"FI".to_string(),
|
||||
"IT".to_string(),
|
||||
"PL".to_string(),
|
||||
]
|
||||
},
|
||||
value: None,
|
||||
}
|
||||
),
|
||||
]),
|
||||
common: HashMap::new(),
|
||||
}
|
||||
),
|
||||
]),
|
||||
},
|
||||
),
|
||||
(
|
||||
|
||||
@ -202,7 +202,11 @@ impl
|
||||
api_models::payments::BankRedirectData::Sofort { country, .. } => {
|
||||
Self::BankRedirect(Box::new(BankRedirectionPMData {
|
||||
payment_brand: PaymentBrand::Sofortueberweisung,
|
||||
bank_account_country: Some(country.to_owned()),
|
||||
bank_account_country: Some(country.to_owned().ok_or(
|
||||
errors::ConnectorError::MissingRequiredField {
|
||||
field_name: "sofort.country",
|
||||
},
|
||||
)?),
|
||||
bank_account_bank_name: None,
|
||||
bank_account_bic: None,
|
||||
bank_account_iban: None,
|
||||
|
||||
@ -2715,10 +2715,7 @@ fn get_redirect_extra_details(
|
||||
country,
|
||||
preferred_language,
|
||||
..
|
||||
} => Ok((
|
||||
Some(preferred_language.to_string()),
|
||||
Some(country.to_owned()),
|
||||
)),
|
||||
} => Ok((preferred_language.clone(), *country)),
|
||||
api_models::payments::BankRedirectData::OpenBankingUk { country, .. } => {
|
||||
let country = country.ok_or(errors::ConnectorError::MissingRequiredField {
|
||||
field_name: "country",
|
||||
|
||||
@ -360,8 +360,15 @@ fn get_payment_source(
|
||||
preferred_language: _,
|
||||
billing_details,
|
||||
} => Ok(PaymentSourceItem::Sofort(RedirectRequest {
|
||||
name: billing_details.get_billing_name()?,
|
||||
country_code: *country,
|
||||
name: billing_details
|
||||
.clone()
|
||||
.ok_or(errors::ConnectorError::MissingRequiredField {
|
||||
field_name: "sofort.billing_details",
|
||||
})?
|
||||
.get_billing_name()?,
|
||||
country_code: country.ok_or(errors::ConnectorError::MissingRequiredField {
|
||||
field_name: "sofort.country",
|
||||
})?,
|
||||
experience_context: ContextStruct {
|
||||
return_url: item.request.complete_authorize_url.clone(),
|
||||
cancel_url: item.request.complete_authorize_url.clone(),
|
||||
|
||||
@ -290,7 +290,7 @@ pub struct StripeSofort {
|
||||
#[serde(rename = "payment_method_data[type]")]
|
||||
pub payment_method_data_type: StripePaymentMethodType,
|
||||
#[serde(rename = "payment_method_options[sofort][preferred_language]")]
|
||||
preferred_language: String,
|
||||
preferred_language: Option<String>,
|
||||
#[serde(rename = "payment_method_data[sofort][country]")]
|
||||
country: api_enums::CountryAlpha2,
|
||||
}
|
||||
@ -1115,36 +1115,10 @@ impl TryFrom<(&payments::BankRedirectData, Option<bool>)> for StripeBillingAddre
|
||||
}),
|
||||
payments::BankRedirectData::Ideal {
|
||||
billing_details, ..
|
||||
} => {
|
||||
let billing_name = billing_details
|
||||
.clone()
|
||||
.and_then(|billing_data| billing_data.billing_name.clone());
|
||||
|
||||
let billing_email = billing_details
|
||||
.clone()
|
||||
.and_then(|billing_data| billing_data.email.clone());
|
||||
match is_customer_initiated_mandate_payment {
|
||||
Some(true) => Ok(Self {
|
||||
name: Some(billing_name.ok_or(
|
||||
errors::ConnectorError::MissingRequiredField {
|
||||
field_name: "billing_name",
|
||||
},
|
||||
)?),
|
||||
|
||||
email: Some(billing_email.ok_or(
|
||||
errors::ConnectorError::MissingRequiredField {
|
||||
field_name: "billing_email",
|
||||
},
|
||||
)?),
|
||||
..Self::default()
|
||||
}),
|
||||
Some(false) | None => Ok(Self {
|
||||
name: billing_name,
|
||||
email: billing_email,
|
||||
..Self::default()
|
||||
}),
|
||||
}
|
||||
}
|
||||
} => Ok(get_stripe_sepa_dd_mandate_billing_details(
|
||||
billing_details,
|
||||
is_customer_initiated_mandate_payment,
|
||||
)?),
|
||||
payments::BankRedirectData::Przelewy24 {
|
||||
billing_details, ..
|
||||
} => Ok(Self {
|
||||
@ -1183,11 +1157,11 @@ impl TryFrom<(&payments::BankRedirectData, Option<bool>)> for StripeBillingAddre
|
||||
}
|
||||
payments::BankRedirectData::Sofort {
|
||||
billing_details, ..
|
||||
} => Ok(Self {
|
||||
name: billing_details.billing_name.clone(),
|
||||
email: billing_details.email.clone(),
|
||||
..Self::default()
|
||||
}),
|
||||
} => Ok(get_stripe_sepa_dd_mandate_billing_details(
|
||||
billing_details,
|
||||
is_customer_initiated_mandate_payment,
|
||||
)?),
|
||||
|
||||
payments::BankRedirectData::Bizum {}
|
||||
| payments::BankRedirectData::Blik { .. }
|
||||
| payments::BankRedirectData::Interac { .. }
|
||||
@ -1674,8 +1648,10 @@ impl TryFrom<&payments::BankRedirectData> for StripePaymentMethodData {
|
||||
} => Ok(Self::BankRedirect(StripeBankRedirectData::StripeSofort(
|
||||
Box::new(StripeSofort {
|
||||
payment_method_data_type,
|
||||
country: country.to_owned(),
|
||||
preferred_language: preferred_language.to_owned(),
|
||||
country: country.ok_or(errors::ConnectorError::MissingRequiredField {
|
||||
field_name: "sofort.country",
|
||||
})?,
|
||||
preferred_language: preferred_language.clone(),
|
||||
}),
|
||||
))),
|
||||
payments::BankRedirectData::OnlineBankingFpx { .. } => {
|
||||
@ -3593,6 +3569,41 @@ pub struct Evidence {
|
||||
pub submit: bool,
|
||||
}
|
||||
|
||||
// Mandates for bank redirects - ideal and sofort happens through sepa direct debit in stripe
|
||||
fn get_stripe_sepa_dd_mandate_billing_details(
|
||||
billing_details: &Option<payments::BankRedirectBilling>,
|
||||
is_customer_initiated_mandate_payment: Option<bool>,
|
||||
) -> Result<StripeBillingAddress, errors::ConnectorError> {
|
||||
let billing_name = billing_details
|
||||
.clone()
|
||||
.and_then(|billing_data| billing_data.billing_name.clone());
|
||||
|
||||
let billing_email = billing_details
|
||||
.clone()
|
||||
.and_then(|billing_data| billing_data.email.clone());
|
||||
match is_customer_initiated_mandate_payment {
|
||||
Some(true) => Ok(StripeBillingAddress {
|
||||
name: Some(
|
||||
billing_name.ok_or(errors::ConnectorError::MissingRequiredField {
|
||||
field_name: "billing_name",
|
||||
})?,
|
||||
),
|
||||
|
||||
email: Some(
|
||||
billing_email.ok_or(errors::ConnectorError::MissingRequiredField {
|
||||
field_name: "billing_email",
|
||||
})?,
|
||||
),
|
||||
..StripeBillingAddress::default()
|
||||
}),
|
||||
Some(false) | None => Ok(StripeBillingAddress {
|
||||
name: billing_name,
|
||||
email: billing_email,
|
||||
..StripeBillingAddress::default()
|
||||
}),
|
||||
}
|
||||
}
|
||||
|
||||
impl TryFrom<&types::SubmitEvidenceRouterData> for Evidence {
|
||||
type Error = error_stack::Report<errors::ConnectorError>;
|
||||
fn try_from(item: &types::SubmitEvidenceRouterData) -> Result<Self, Self::Error> {
|
||||
|
||||
@ -246,7 +246,8 @@ card.debit = {connector_list = "stripe,adyen,authorizedotnet,cybersource,globalp
|
||||
bank_debit.ach = { connector_list = "gocardless"}
|
||||
bank_debit.becs = { connector_list = "gocardless"}
|
||||
bank_debit.sepa = { connector_list = "gocardless"}
|
||||
bank_redirect.ideal = {connector_list = "stripe,adyen"}
|
||||
bank_redirect.ideal = {connector_list = "stripe,adyen,globalpay"}
|
||||
bank_redirect.sofort = {connector_list = "stripe,adyen,globalpay"}
|
||||
|
||||
[analytics]
|
||||
source = "sqlx"
|
||||
|
||||
@ -5367,13 +5367,16 @@
|
||||
"sofort": {
|
||||
"type": "object",
|
||||
"required": [
|
||||
"billing_details",
|
||||
"country",
|
||||
"preferred_language"
|
||||
"country"
|
||||
],
|
||||
"properties": {
|
||||
"billing_details": {
|
||||
"$ref": "#/components/schemas/BankRedirectBilling"
|
||||
"allOf": [
|
||||
{
|
||||
"$ref": "#/components/schemas/BankRedirectBilling"
|
||||
}
|
||||
],
|
||||
"nullable": true
|
||||
},
|
||||
"country": {
|
||||
"$ref": "#/components/schemas/CountryAlpha2"
|
||||
@ -5381,7 +5384,8 @@
|
||||
"preferred_language": {
|
||||
"type": "string",
|
||||
"description": "The preferred language",
|
||||
"example": "en"
|
||||
"example": "en",
|
||||
"nullable": true
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user