Projet

Général

Profil

0001-lingo-move-transaction-identifier-to-URL-path-39074.patch

Emmanuel Cazenave, 20 janvier 2020 17:59

Télécharger (8,6 ko)

Voir les différences:

Subject: [PATCH] lingo: move transaction identifier to URL path (#39074)

 combo/apps/lingo/urls.py         |  2 +-
 combo/apps/lingo/views.py        | 17 +++++++++--------
 tests/test_lingo_payment.py      | 15 ++++-----------
 tests/test_lingo_remote_regie.py | 11 +++++------
 4 files changed, 19 insertions(+), 26 deletions(-)
combo/apps/lingo/urls.py
71 71
    url(r'^lingo/callback-payment-backend/(?P<payment_backend_pk>\w+)/$',
72 72
        CallbackView.as_view(), name='lingo-callback-payment-backend'),
73 73
    url(r'^lingo/return/(?P<regie_pk>\w+)/$', ReturnView.as_view(), name='lingo-return'),
74
    url(r'^lingo/return-payment-backend/(?P<payment_backend_pk>\w+)/$',
74
    url(r'^lingo/return-payment-backend/(?P<payment_backend_pk>\w+)/(?P<transaction_signature>.+)/$',
75 75
        ReturnView.as_view(), name='lingo-return-payment-backend'),
76 76
    url(r'^manage/lingo/', decorated_includes(manager_required,
77 77
        include(lingo_manager_urls))),
combo/apps/lingo/views.py
54 54
    if isinstance(regie_or_payment_backend, Regie):
55 55
        payment_backend = regie_or_payment_backend.payment_backend
56 56
    options = payment_backend.service_options
57
    normal_return_url = reverse(
58
        'lingo-return-payment-backend',
59
        kwargs={'payment_backend_pk': payment_backend.id}
60
    )
61
    if transaction_id:
62
        normal_return_url = "%s?lingo-transaction-id=%s" % (normal_return_url, signing.dumps(transaction_id))
63 57
    options.update({
64 58
        'automatic_return_url': request.build_absolute_uri(
65 59
                reverse('lingo-callback-payment-backend',
66 60
                        kwargs={'payment_backend_pk': payment_backend.id})),
67
        'normal_return_url': request.build_absolute_uri(normal_return_url)
68 61
    })
62

  
63
    if transaction_id:
64
        options['normal_return_url'] = request.build_absolute_uri(
65
            reverse('lingo-return-payment-backend', kwargs={
66
                'payment_backend_pk': payment_backend.id,
67
                'transaction_signature': signing.dumps(transaction_id)
68
            })
69
        )
69 70
    return eopayment.Payment(payment_backend.service, options)
70 71

  
71 72

  
......
642 643

  
643 644
    def handle_return(self, request, backend_response, **kwargs):
644 645
        transaction = None
645
        transaction_id = request.GET.get('lingo-transaction-id')
646
        transaction_id = kwargs.get('transaction_signature')
646 647
        if transaction_id:
647 648
            try:
648 649
                transaction_id = signing.loads(transaction_id)
tests/test_lingo_payment.py
226 226
            'ok': True, 'reason': 'Paid'}
227 227
    # make sure return url is the user return URL
228 228
    assert urlparse.urlparse(qs['return_url'][0]).path.startswith(
229
            reverse('lingo-return-payment-backend',
230
                    kwargs={'payment_backend_pk': regie.payment_backend.id}))
229
        '/lingo/return-payment-backend/%s/' % regie.payment_backend.id)
231 230
    # simulate successful call to callback URL
232 231
    with mock.patch('combo.utils.requests_wrapper.RequestsSession.request') as request:
233 232
        resp = app.get(get_url(with_payment_backend, 'lingo-callback', regie), params=args)
......
642 641
    parsed = urlparse.urlparse(location)
643 642
    qs = urlparse.parse_qs(parsed.query)
644 643
    transaction_id = qs['transaction_id'][0]
644
    return_url = qs['return_url'][0]
645 645
    data = {'transaction_id': transaction_id, 'signed': True,
646 646
            'amount': qs['amount'][0], 'ok': True}
647 647
    assert data['amount'] == '11.50'
......
653 653
    assert Transaction.objects.get(order_id=transaction_id).status == 3
654 654

  
655 655
    # call return view
656
    return_url = get_url(with_payment_backend, 'lingo-return', regie)
657 656
    get_resp = app.get(return_url, params=data)
658 657
    assert get_resp.status_code == 302
659 658
    resp = app.get(get_resp['Location'])
......
765 764
    data = {'transaction_id': transaction_id,
766 765
            'amount': qs['amount'][0], 'ok': True}
767 766
    assert data['amount'] == '10.50'
768
    return_qs = urlparse.parse_qs(urlparse.urlparse(qs['return_url'][0]).query)
769
    lingo_transaction_id = return_qs['lingo-transaction-id'][0]
767
    return_url = qs['return_url'][0]
770 768

  
771 769
    # call return with unsigned POST
772 770
    with check_log(caplog, 'received unsigned payment'):
773
        return_url = get_url(with_payment_backend, 'lingo-return', regie)
774 771
        with mock.patch('combo.utils.requests_wrapper.RequestsSession.request') as request:
775 772
            get_resp = app.post(return_url, params=data)
776 773
            assert request.call_count == 0
777 774
        assert get_resp.status_code == 302
778
        assert urlparse.urlparse(get_resp['location']).path == '/test_basket_cell/'
775
        assert urlparse.urlparse(get_resp['location']).path == '/lingo/payment-status'
779 776
        assert Transaction.objects.get(order_id=transaction_id).status == 0  # not paid
780 777

  
781 778
    # call return with missing data
......
792 789

  
793 790
    # call return with signed POST
794 791
    data['signed'] = True
795
    return_url = get_url(with_payment_backend, 'lingo-return', regie) + \
796
        '?lingo-transaction-id=%s' % lingo_transaction_id
797 792
    with mock.patch('combo.utils.requests_wrapper.RequestsSession.request') as request:
798 793
        get_resp = app.post(return_url, params=data)
799 794
        url = request.call_args[0][1]
......
1092 1087
    # simulate bad responseform payment backend, no transaction id
1093 1088
    data = {'amount': qs['amount'][0], 'signed': True}
1094 1089
    return_url = qs['return_url'][0]
1095
    assert 'lingo-transaction-id' in return_url
1096 1090
    resp = app.get(return_url, params=data)
1097 1091
    assert_payment_status(resp.location)
1098 1092
    resp = resp.follow()
......
1108 1102
        'amount': qs['amount'][0], 'signed': True
1109 1103
    }
1110 1104
    return_url = qs['return_url'][0]
1111
    assert 'lingo-transaction-id' in return_url
1112 1105
    resp = app.get(return_url, params=data)
1113 1106
    assert_payment_status(resp.location, transaction_id=item.transaction_set.last().pk)
1114 1107
    # check that item is paid
tests/test_lingo_remote_regie.py
206 206
    args = {'transaction_id': qs['transaction_id'][0], 'signed': True,
207 207
            'ok': True, 'reason': 'Paid'}
208 208
    # make sure return url is the user return URL
209
    assert urlparse.urlparse(qs['return_url'][0]).path.startswith(
210
        reverse('lingo-return-payment-backend',
211
                kwargs={'payment_backend_pk': remote_regie.payment_backend.id}))
209
    return_url = qs['return_url'][0]
210
    assert urlparse.urlparse(return_url).path.startswith('/lingo/return-payment-backend')
212 211
    # simulate successful return URL
213 212
    resp = app.get(qs['return_url'][0], params=args)
214 213
    # redirect to payment status
......
332 331
    args = {'transaction_id': qs['transaction_id'][0], 'signed': True,
333 332
            'ok': True, 'reason': 'Paid'}
334 333
    # make sure return url is the user return URL
335
    assert urlparse.urlparse(qs['return_url'][0]).path.startswith(
336
        reverse('lingo-return-payment-backend',
337
                kwargs={'payment_backend_pk': remote_regie.payment_backend.id}))
334
    return_url = qs['return_url'][0]
335
    assert urlparse.urlparse(return_url).path.startswith(
336
        '/lingo/return-payment-backend/%s/' % remote_regie.payment_backend.id)
338 337
    # simulate payment failure
339 338
    mock_get.side_effect = ConnectionError('where is my hostname?')
340 339
    resp = app.get(qs['return_url'][0], params=args)
341
-