Skip to content

[release] 3.45.1 #423

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 2 commits into from
Jun 6, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
27 changes: 26 additions & 1 deletion mangopay/fields.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,8 @@
ScopeBlocked, BrowserInfo, Shipping, CurrentState, FallbackReason, InstantPayout, CountryAuthorizationData, \
PayinsLinked, ConversionRate, CardInfo, LocalAccountDetails, InternationalAccountDetails, \
VirtualAccountCapabilities, PaymentRef, PendingUserAction, LegalRepresentative, IndividualRecipient, \
BusinessRecipient, RecipientPropertySchema, IndividualRecipientPropertySchema, BusinessRecipientPropertySchema
BusinessRecipient, RecipientPropertySchema, IndividualRecipientPropertySchema, BusinessRecipientPropertySchema, \
CompanyNumberValidation


class FieldDescriptor(object):
Expand Down Expand Up @@ -1180,3 +1181,27 @@ def api_value(self, value):
}

return value


class CompanyNumberValidationField(Field):
def python_value(self, value):
if value is not None:
return CompanyNumberValidation(company_number=value.get('CompanyNumber', None),
country_code=value.get('CountryCode', None),
is_valid=value.get('IsValid', None),
validation_rules=value.get('ValidationRules', None))

return value

def api_value(self, value):
value = super(CompanyNumberValidationField, self).api_value(value)

if isinstance(value, CompanyNumberValidation):
value = {
'CompanyNumber': value.company_number,
'CountryCode': value.country_code,
'IsValid': value.is_valid,
'ValidationRules': value.validation_rules
}

return value
14 changes: 13 additions & 1 deletion mangopay/resources.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@
LocalAccountDetailsField, VirtualAccountCapabilitiesField, PaymentRefField, PendingUserActionField,
LegalRepresentativeField, IndividualRecipientField, BusinessRecipientField,
RecipientPropertySchemaField, IndividualRecipientPropertySchemaField,
BusinessRecipientPropertySchemaField)
BusinessRecipientPropertySchemaField, CompanyNumberValidationField)
from .query import InsertQuery, UpdateQuery, SelectQuery, ActionQuery, DeleteQuery


Expand Down Expand Up @@ -2800,3 +2800,15 @@ def get(cls, country, currency, *args, **kwargs):
kwargs['currency'] = currency
select = SelectQuery(PayoutMethod, *args, **kwargs)
return select.get("", *args, **kwargs)


class UserDataFormatValidation(BaseModel):
company_number = CompanyNumberValidationField(api_name='CompanyNumber')

class Meta:
verbose_name = 'user_data_format_validation'
verbose_name_plural = 'user_data_format_validations'

url = {
InsertQuery.identifier: '/users/data-formats/validation'
}
30 changes: 30 additions & 0 deletions mangopay/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -1295,3 +1295,33 @@ def to_api_json(self):
"BusinessName": self.business_name,
"Address": self.address
}


@add_camelcase_aliases
class CompanyNumberValidation(object):
def __init__(self, company_number=None, country_code=None, is_valid=None, validation_rules=None):
self.company_number = company_number
self.country_code = country_code
self.is_valid = is_valid
self.validation_rules = validation_rules

def __str__(self):
return 'CompanyNumberValidation: %s , %s, %s, %s' % \
(self.company_number, self.country_code, self.is_valid, self.validation_rules)

def __eq__(self, other):
if isinstance(other, CompanyNumberValidation):
stat = ((self.company_number == other.company_number) and
(self.country_code == other.country_code) and
(self.is_valid == other.is_valid) and
(self.validation_rules == other.validation_rules))
return stat
return False

def to_api_json(self):
return {
"CompanyNumber": self.company_number,
"CountryCode": self.country_code,
"IsValid": self.is_valid,
"ValidationRules": self.validation_rules
}
18 changes: 18 additions & 0 deletions tests/test_recipients.py
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,24 @@ def test_get_user_recipients(self):
self.assertIsInstance(fetched.data, list)
self.assertTrue(len(fetched.data) > 0)

def test_get_user_recipients_filtered_payout(self):
self.create_new_recipient()
john = BaseTestLive.get_john_sca_owner()
fetched = Recipient.get_user_recipients(john.id, RecipientScope='PAYOUT')

self.assertIsNotNone(fetched)
self.assertIsInstance(fetched.data, list)
self.assertTrue(len(fetched.data) > 0)

def test_get_user_recipients_filtered_payin(self):
self.create_new_recipient()
john = BaseTestLive.get_john_sca_owner()
fetched = Recipient.get_user_recipients(john.id, RecipientScope='PAYIN')

self.assertIsNotNone(fetched)
self.assertIsInstance(fetched.data, list)
self.assertTrue(len(fetched.data) == 0)

def test_get_recipient_schema_local_bank_transfer_individual(self):
schema = RecipientSchema.get('LocalBankTransfer', 'Individual', 'GBP', 'GB')

Expand Down
17 changes: 15 additions & 2 deletions tests/test_users.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,9 @@

from mangopay.exceptions import APIError
from mangopay.resources import (User, NaturalUser, Wallet,
LegalUser, Transfer, Transaction, NaturalUserSca, LegalUserSca)
from mangopay.utils import Money, Address
LegalUser, Transfer, Transaction, NaturalUserSca, LegalUserSca,
UserDataFormatValidation)
from mangopay.utils import Money, Address, CompanyNumberValidation
from tests import settings
from tests.mocks import today, today_timestamp
from tests.test_base import BaseTest, BaseTestLive
Expand Down Expand Up @@ -1000,3 +1001,15 @@ def test_users_GetTransactionsSca(self):
self.assertTrue('PendingUserAction RedirectUrl' in ex.headers.get('www-authenticate'))
except Exception as ex:
self.assertTrue('PendingUserAction RedirectUrl' in ex.headers.get('www-authenticate'))

def test_validate_user_data_format(self):
validation = UserDataFormatValidation()
validation.company_number = CompanyNumberValidation(company_number='AB123456', country_code='IT')
result = validation.save()
self.assertIsNotNone(result['company_number'])

try:
validation.company_number = CompanyNumberValidation(company_number='123')
validation.save()
except APIError as e:
self.assertTrue("One or several required parameters are missing or incorrect" in e.content['Message'])
Loading