Skip to content

Commit 82e070a

Browse files
Implemented idempotent requests and corrected disputes unit tests.
1 parent 774a5dc commit 82e070a

20 files changed

+442
-51
lines changed

mangopay2-python-sdk.pyproj

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@
3131
<Compile Include="mangopaysdk\entities\bankaccount.py">
3232
<SubType>Code</SubType>
3333
</Compile>
34+
<Compile Include="mangopaysdk\entities\idempotencyresponse.py" />
3435
<Compile Include="mangopaysdk\entities\repudiation.py" />
3536
<Compile Include="mangopaysdk\entities\disputedocument.py" />
3637
<Compile Include="mangopaysdk\entities\dispute.py" />
@@ -50,11 +51,14 @@
5051
<Compile Include="mangopaysdk\entities\entitybase.py">
5152
<SubType>Code</SubType>
5253
</Compile>
54+
<Compile Include="mangopaysdk\entities\settlement.py" />
5355
<Compile Include="mangopaysdk\tools\apicardpreauthorizations.py" />
5456
<Compile Include="mangopaysdk\tools\apicards.py" />
5557
<Compile Include="mangopaysdk\tools\apicardregistrations.py" />
5658
<Compile Include="mangopaysdk\tools\apidisputes.py" />
59+
<Compile Include="mangopaysdk\tools\apiidempotency.py" />
5760
<Compile Include="mangopaysdk\tools\apievents.py" />
61+
<Compile Include="mangopaysdk\tools\filterdisputedocuments.py" />
5862
<Compile Include="mangopaysdk\tools\sorting.py" />
5963
<Compile Include="mangopaysdk\tools\apikycdocuments.py" />
6064
<Compile Include="mangopaysdk\tools\apihooks.py" />
@@ -200,6 +204,7 @@
200204
<Compile Include="tests\testdisputes.py" />
201205
<Compile Include="tests\testcardpreauthorizations.py" />
202206
<Compile Include="tests\testevents.py" />
207+
<Compile Include="tests\testidempotency.py" />
203208
<Compile Include="tests\testkycdocuments.py" />
204209
<Compile Include="tests\testhooks.py" />
205210
<Compile Include="tests\testrefunds.py">
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
from mangopaysdk.entities.entitybase import EntityBase
2+
3+
class IdempotencyResponse(EntityBase):
4+
"""IdempotencyResponse entity."""
5+
6+
def __init__(self, id = None):
7+
self.StatusCode = None
8+
self.ContentLength = None
9+
self.ContentType = None
10+
self.Date = None
11+
self.Resource = None
12+
return super(IdempotencyResponse, self).__init__(id)

mangopaysdk/entities/settlement.py

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
from mangopaysdk.entities.transfer import Transfer
2+
3+
4+
class Settlement (Transfer):
5+
6+
def __init__(self, id = None):
7+
self.RepudiationId = None
8+
return super(Settlement, self).__init__(id)

mangopaysdk/mangopayapi.py

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
1-
from mangopaysdk.tools import apioauth, apiclients, apiusers, apiwallets, apitransfers, apipayins, apipayouts, apievents, apicardpreauthorizations
2-
from mangopaysdk.tools import apirefunds, apicardregistrations, apicards, apihooks, apikycdocuments, apidisputes
1+
from mangopaysdk.tools import apioauth, apiclients, apiusers, apiwallets, apitransfers, apipayins, apipayouts, apievents, apicardpreauthorizations
2+
from mangopaysdk.tools import apirefunds, apicardregistrations, apicards, apihooks, apikycdocuments, apidisputes, apiidempotency
33
from mangopaysdk.configuration import Configuration
44
from mangopaysdk.tools.storages.authorizationtokenmanager import AuthorizationTokenManager
55

@@ -39,4 +39,5 @@ def __init__(self):
3939
self.events = apievents.ApiEvents(self)
4040
self.hooks = apihooks.ApiHooks(self)
4141
self.kycdocuments = apikycdocuments.ApiKycDocuments(self)
42-
self.disputes = apidisputes.ApiDisputes(self)
42+
self.disputes = apidisputes.ApiDisputes(self)
43+
self.idempotency = apiidempotency.ApiIdempotency(self)

mangopaysdk/tools/apibase.py

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
from mangopaysdk.types.pagination import Pagination
1+
from mangopaysdk.types.pagination import Pagination
22
from mangopaysdk.entities.entitybase import EntityBase
33
from mangopaysdk.types.dto import Dto
44
from mangopaysdk.types.money import Money
@@ -16,6 +16,7 @@
1616
from mangopaysdk.entities.transfer import Transfer
1717
from mangopaysdk.entities.transaction import Transaction
1818
from mangopaysdk.entities.transfer import Transfer
19+
from mangopaysdk.entities.settlement import Settlement
1920
from mangopaysdk.entities.client import Client
2021
from mangopaysdk.entities.card import Card
2122
from mangopaysdk.entities.refund import Refund
@@ -151,7 +152,10 @@ class ApiBase(object):
151152
'disputes_document_get_for_client' : ('/dispute-documents', 'GET'),
152153
'disputes_repudiation_get' : ('/repudiations/%s', 'GET'),
153154
'disputes_repudiation_create_settlement' : ('/repudiations/%s/settlementtransfer', 'POST'),
155+
156+
'settlement_get' : ('/settlements/%s', 'GET'),
154157

158+
'idempotency_response_get' : ('/responses/%s', 'GET'),
155159

156160
# These are temporary functions and WILL be removed in the future.
157161
# Contact support before using these features or if have any queries.
@@ -208,13 +212,25 @@ def _createObject (self, methodKey, entity, responseClassName = None, entityId =
208212
param int secondEntityId Releated entity identifier
209213
return dictionary Response data
210214
"""
215+
return self._createObjectIdempotent(None, methodKey, entity, responseClassName, entityId, secondEntityId)
216+
217+
def _createObjectIdempotent (self, idempotencyKey, methodKey, entity, responseClassName = None, entityId = None, secondEntityId = None):
218+
"""Create object in API.
219+
param string idempotencyKey Idempotency key for this request
220+
param string methodKey Key with request data
221+
param object entity Entity object
222+
param object responseClassName Name of entity class from response
223+
param int entityId Entity identifier
224+
param int secondEntityId Releated entity identifier
225+
return dictionary Response data
226+
"""
211227
urlMethod = self._buildUrl(methodKey, entityId, secondEntityId)
212228

213229
if entity != None:
214230
requestData = self._buildRequestData(entity)
215231

216232
rest = RestTool(self._root, True)
217-
response = rest.Request(urlMethod, self._getRequestType(methodKey), requestData)
233+
response = rest.RequestIdempotent(idempotencyKey, urlMethod, self._getRequestType(methodKey), requestData)
218234

219235
if responseClassName != None:
220236
return self._castResponseToEntity(response, responseClassName)

mangopaysdk/tools/apicardpreauthorizations.py

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
from mangopaysdk.tools.apibase import ApiBase
1+
from mangopaysdk.tools.apibase import ApiBase
22
from mangopaysdk.entities.cardpreauthorization import CardPreAuthorization
33

44

@@ -12,7 +12,15 @@ def Create(self, cardPreAuthorization):
1212
param CardPreAuthorization object to create
1313
return CardPreAuthorization Object returned from API
1414
"""
15-
return self._createObject('preauthorizations_create', cardPreAuthorization, 'CardPreAuthorization')
15+
return self.CreateIdempotent(None, cardPreAuthorization)
16+
17+
def CreateIdempotent(self, idempotencyKey, cardPreAuthorization):
18+
"""Create new card preauthorization
19+
param string idempotencyKey Idempotency key for this request
20+
param CardPreAuthorization object to create
21+
return CardPreAuthorization Object returned from API
22+
"""
23+
return self._createObjectIdempotent(idempotencyKey, 'preauthorizations_create', cardPreAuthorization, 'CardPreAuthorization')
1624

1725
def Get(self, cardPreAuthorizationId):
1826
"""Get card preauthorization

mangopaysdk/tools/apicardregistrations.py

Lines changed: 23 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
from mangopaysdk.tools.apibase import ApiBase
1+
from mangopaysdk.tools.apibase import ApiBase
22
from mangopaysdk.entities.cardregistration import CardRegistration
33
from mangopaysdk.entities.temporarypaymentcard import TemporaryPaymentCard
44

@@ -11,7 +11,15 @@ def Create(self, cardRegistration):
1111
param CardRegistration object to create
1212
return CardRegistration Object returned from API
1313
"""
14-
return self._createObject('cardregistration_create', cardRegistration, 'CardRegistration')
14+
return self.CreateIdempotent(None, cardRegistration)
15+
16+
def CreateIdempotent(self, idempotencyKey, cardRegistration):
17+
"""Create new card registration
18+
param string idempotencyKey Idempotency key for this request
19+
param CardRegistration object to create
20+
return CardRegistration Object returned from API
21+
"""
22+
return self._createObjectIdempotent(idempotencyKey, 'cardregistration_create', cardRegistration, 'CardRegistration')
1523

1624
def Get(self, cardRegistrationId):
1725
"""Get card registration
@@ -37,7 +45,19 @@ def CreateTemporaryPaymentCard(self, paymentCard):
3745
param TemporaryPaymentCard Temporary payment card to be created
3846
return TemporaryPaymentCard Object returned from API
3947
"""
40-
return self._createObject('temp_paymentcards_create', paymentCard, 'TemporaryPaymentCard')
48+
return self.CreateTemporaryPaymentCardIdempotent(None, paymentCard)
49+
50+
def CreateTemporaryPaymentCardIdempotent(self, idempotencyKey, paymentCard):
51+
"""WARNING!
52+
This is temporary function and will be removed in future.
53+
Contact support before using these features or if have any queries.
54+
55+
Creates new temporary payment card.
56+
param string idempotencyKey Idempotency key for this request
57+
param TemporaryPaymentCard Temporary payment card to be created
58+
return TemporaryPaymentCard Object returned from API
59+
"""
60+
return self._createObjectIdempotent(idempotencyKey, 'temp_paymentcards_create', paymentCard, 'TemporaryPaymentCard')
4161

4262
def GetTemporaryPaymentCard(self, paymentCardId):
4363
"""WARNING!

mangopaysdk/tools/apidisputes.py

Lines changed: 40 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,10 @@
1-
from mangopaysdk.tools.apibase import ApiBase
1+
from mangopaysdk.tools.apibase import ApiBase
22
from mangopaysdk.tools.resttool import RestTool
33
from mangopaysdk.entities.dispute import Dispute
44
from mangopaysdk.entities.transaction import Transaction
55
from mangopaysdk.entities.repudiation import Repudiation
66
from mangopaysdk.entities.transfer import Transfer
7+
from mangopaysdk.entities.settlement import Settlement
78

89

910
class ApiDisputes(ApiBase):
@@ -68,15 +69,33 @@ def CreateDocument(self, disputeDocument, disputeId):
6869
param Dispute identifier
6970
return DisputeDocument object returned from API
7071
"""
71-
return self._createObject('disputes_document_create', disputeDocument, 'DisputeDocument', disputeId)
72+
return self.CreateDocumentIdempotent(None, disputeDocument, disputeId)
73+
74+
def CreateDocumentIdempotent(self, idempotencyKey, disputeDocument, disputeId):
75+
"""Create dispute document.
76+
param string idempotencyKey Idempotency key for this request
77+
param DisputeDocument entity
78+
param Dispute identifier
79+
return DisputeDocument object returned from API
80+
"""
81+
return self._createObjectIdempotent(idempotencyKey, 'disputes_document_create', disputeDocument, 'DisputeDocument', disputeId)
7282

7383
def CreatePage(self, disputePage, disputeId, disputeDocumentId):
7484
"""Create DisputePage for existing DisputeDocument.
7585
param DisputePage entity (File should be base64 string)
7686
param Dispute identifier
7787
param DisputeDocument identifier
7888
"""
79-
return self._createObject('disputes_document_page_create', disputePage, None, disputeId, disputeDocumentId)
89+
return self.CreatePageIdempotent(None, disputePage, disputeId, disputeDocumentId)
90+
91+
def CreatePageIdempotent(self, idempotencyKey, disputePage, disputeId, disputeDocumentId):
92+
"""Create DisputePage for existing DisputeDocument.
93+
param string idempotencyKey Idempotency key for this request
94+
param DisputePage entity (File should be base64 string)
95+
param Dispute identifier
96+
param DisputeDocument identifier
97+
"""
98+
return self._createObjectIdempotent(idempotencyKey, 'disputes_document_page_create', disputePage, None, disputeId, disputeDocumentId)
8099

81100
def ContestDispute(self, contestedFunds, disputeId):
82101
"""Contest dispute.
@@ -148,7 +167,23 @@ def CreateSettlementTransfer(self, settlementTransfer, repudiationId):
148167
param Repudiation identifier
149168
return Transfer object returned from API
150169
"""
151-
return self._createObject('disputes_repudiation_create_settlement', settlementTransfer, 'Transfer', repudiationId)
170+
return self.CreateSettlementTransferIdempotent(None, settlementTransfer, repudiationId)
171+
172+
def CreateSettlementTransferIdempotent(self, idempotencyKey, settlementTransfer, repudiationId):
173+
"""Create settlement transfer.
174+
param string idempotencyKey Idempotency key for this request
175+
param Settlement transfer object
176+
param Repudiation identifier
177+
return Transfer object returned from API
178+
"""
179+
return self._createObjectIdempotent(idempotencyKey, 'disputes_repudiation_create_settlement', settlementTransfer, 'Transfer', repudiationId)
152180

153181
def ResubmitDispute(self, disputeId):
154-
return self._saveObject('disputes_save_contest_funds', None, 'Dispute', disputeId)
182+
return self._saveObject('disputes_save_contest_funds', None, 'Dispute', disputeId)
183+
184+
def GetSettlementTransfer(self, settlementId):
185+
"""Get settlement transfer.
186+
param string settlementId SettlementTransfer identifier
187+
return Settlement instance returned from API
188+
"""
189+
return self._getObject('settlement_get', settlementId, 'Settlement')

mangopaysdk/tools/apihooks.py

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
from mangopaysdk.tools.apibase import ApiBase
1+
from mangopaysdk.tools.apibase import ApiBase
22

33
class ApiHooks(ApiBase):
44
"""MangoPay API for hooks and notifications."""
@@ -8,7 +8,15 @@ def Create(self, hook):
88
param Hook hook
99
return Newly created hook object returned from API
1010
"""
11-
return self._createObject('hooks_create', hook, 'Hook')
11+
return self.CreateIdempotent(None, hook)
12+
13+
def CreateIdempotent(self, idempotencyKey, hook):
14+
"""Creates a new hook.
15+
param string idempotencyKey Idempotency key for this request
16+
param Hook hook
17+
return Newly created hook object returned from API
18+
"""
19+
return self._createObjectIdempotent(idempotencyKey, 'hooks_create', hook, 'Hook')
1220

1321
def Get(self, hookId):
1422
"""Gets hook.

mangopaysdk/tools/apiidempotency.py

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
from mangopaysdk.tools.apibase import ApiBase
2+
from mangopaysdk.tools.resttool import RestTool
3+
4+
5+
class ApiIdempotency(ApiBase):
6+
"""MangoPay API methods for idempotency."""
7+
8+
def Get(self, idempotencyKey = None):
9+
"""Get idempotency response object
10+
param string Idempotency key
11+
return IdempotencyResponse from API
12+
"""
13+
return self._getObject('idempotency_response_get', idempotencyKey)

mangopaysdk/tools/apipayins.py

Lines changed: 33 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
from mangopaysdk.tools.apibase import ApiBase
1+
from mangopaysdk.tools.apibase import ApiBase
22
from mangopaysdk.entities.payin import PayIn
33
from mangopaysdk.entities.temporaryimmediatepayin import TemporaryImmediatePayIn
44

@@ -11,9 +11,17 @@ def Create(self, payIn):
1111
param PayIn payIn object
1212
return PayIn Object returned from API
1313
"""
14+
return self.CreateIdempotent(None, payIn)
15+
16+
def CreateIdempotent(self, idempotencyKey, payIn):
17+
"""Create new pay-in object.
18+
param string idempotencyKey Idempotency key for this request
19+
param PayIn payIn object
20+
return PayIn Object returned from API
21+
"""
1422
paymentKey = self._getPaymentKey(payIn);
1523
executionKey = self._getExecutionKey(payIn);
16-
return self._createObject('payins_' + paymentKey + '-' + executionKey + '_create', payIn, 'PayIn')
24+
return self._createObjectIdempotent(idempotencyKey, 'payins_' + paymentKey + '-' + executionKey + '_create', payIn, 'PayIn')
1725

1826
def Get(self, payInId):
1927
"""Get pay-in object.
@@ -28,7 +36,16 @@ def CreateRefund(self, payInId, refund):
2836
param Refund refund object to create
2937
return Refund Object returned by REST API
3038
"""
31-
return self._createObject('payins_createrefunds', refund, 'Refund', payInId)
39+
return self.CreateRefundIdempotent(None, payInId, refund)
40+
41+
def CreateRefundIdempotent(self, idempotencyKey, payInId, refund):
42+
"""Create refund for pay-in object.
43+
param string idempotencyKey Idempotency key for this request
44+
param type payInId Pay-in identifier
45+
param Refund refund object to create
46+
return Refund Object returned by REST API
47+
"""
48+
return self._createObjectIdempotent(idempotencyKey, 'payins_createrefunds', refund, 'Refund', payInId)
3249

3350
def GetRefund(self, payInId):
3451
"""Get refund for pay-in object.
@@ -46,7 +63,19 @@ def CreateTemporaryImmediatePayIn(self, immediatePayIn):
4663
param TemporaryImmediatePayIn Immediate pay-in object to create
4764
return TemporaryImmediatePayIn Object returned from API
4865
"""
49-
return self._createObject('temp_immediatepayins_create', immediatePayIn, 'TemporaryImmediatePayIn')
66+
return self.CreateTemporaryImmediatePayInIdempotent(None, immediatePayIn)
67+
68+
def CreateTemporaryImmediatePayInIdempotent(self, idempotencyKey, immediatePayIn):
69+
"""WARNING!
70+
This is temporary function and will be removed in future.
71+
Contact support before using these features or if have any queries.
72+
73+
Creates new temporary immediate pay-in.
74+
param string idempotencyKey Idempotency key for this request
75+
param TemporaryImmediatePayIn Immediate pay-in object to create
76+
return TemporaryImmediatePayIn Object returned from API
77+
"""
78+
return self._createObjectIdempotent(idempotencyKey, 'temp_immediatepayins_create', immediatePayIn, 'TemporaryImmediatePayIn')
5079

5180
def _getPaymentKey(self, payIn):
5281

0 commit comments

Comments
 (0)