fake gateway

This commit is contained in:
Sayyid Hamid Mahdavi 2025-05-31 13:36:25 +03:30
parent a1e4fbcc52
commit f0edf10f53
5 changed files with 108 additions and 60 deletions

View file

@ -24,7 +24,7 @@ class BasePGModel(models.Model):
def make_request(self):
pass
def confirm_request(self):
def confirm_request(self, request=None):
pass
def reverse_request(self):

View file

@ -0,0 +1,26 @@
# Generated by Django 5.1.4 on 2025-05-31 10:03
import django.db.models.deletion
from django.db import migrations, models
class Migration(migrations.Migration):
dependencies = [
('pg', '0004_paymentrequest_phone_number_and_more'),
]
operations = [
migrations.CreateModel(
name='Fake',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('created_at', models.DateTimeField(auto_now_add=True, db_index=True)),
('updated_at', models.DateTimeField(auto_now=True, db_index=True)),
('payment_request', models.OneToOneField(on_delete=django.db.models.deletion.PROTECT, related_name='+', to='pg.paymentrequest')),
],
options={
'abstract': False,
},
),
]

View file

@ -2,6 +2,7 @@ import urllib.parse
from mimetypes import guess_all_extensions
from django.conf import settings
from django.contrib import messages
from django.db import models
from django.db.models import TextChoices
from django.urls import reverse
@ -20,9 +21,10 @@ from django.utils.translation import gettext_lazy as _
class GatewayChoise(TextChoices):
FAKE = "fake", _("fake")
PNA = 'pna' , _('pna')
PNA = 'pna', _('pna')
# TODO: use generic relation
class PaymentRequest(models.Model):
id = None
uuid = models.UUIDField(primary_key=True, editable=False, default=uuid.uuid4, unique=True, db_index=True)
@ -42,23 +44,30 @@ class PaymentRequest(models.Model):
updated_at = models.DateTimeField(auto_now=True, db_index=True)
def get_gateway_tools(self):
if self.gateway == 'pna':
return self.pna
if self.gateway == GatewayChoise.PNA:
return PNA.objects.get(payment_request=self)
if self.gateway == GatewayChoise.FAKE:
return Fake.objects.get(payment_request=self)
def set_gateway(self, data):
if 'fake' in data:
self.gateway = GatewayChoise.FAKE
fake = Fake.objects.create(payment_request=self)
fake.payment_request = self
def set_gateway(self, gateway):
self.gateway = gateway
if gateway == 'pna':
elif 'pna' in data:
self.gateway = GatewayChoise.PNA
pna = PNA.objects.create(payment_request=self)
pna.payment_request = self
if gateway == 'fake':
pass
else:
raise Exception('Unknown gateway')
self.save()
# TODO: complete and use this
def change_state(self, from_state, to_state, error_message=None, **data):
if self.state == from_state:
@ -132,7 +141,6 @@ class PaymentRequest(models.Model):
return bool(to_pay_success)
class PNA(BasePGModel):
payment_request = models.OneToOneField(PaymentRequest, on_delete=models.PROTECT, related_name='pna')
@ -145,7 +153,6 @@ class PNA(BasePGModel):
pna_status_code = models.IntegerField(null=True, blank=True)
pna_status_message = models.CharField(null=True, blank=True, max_length=255)
client = PNAClient()
def make_request(self):
@ -166,20 +173,56 @@ class PNA(BasePGModel):
self.save()
def get_redirect_url(self):
def get_pg_page_url(self):
if self.pna_token:
return self.client.pg_base_url.format(token=self.pna_token)
def confirm_request(self):
pna_token = self.pna_token
response = self.client.request_normal_sale_confirm(pna_token)
# response = {'status': 0, 'cardNumberMasked': '504172******9210', 'rrn': 511629210215, 'appToken': 4101434578524, 'token': 'NDEwMTQzNDU3ODUyNA=='}
self.details = response
if response['status'] == 0:
self.pna_status = StateChoices.SUCCESS.value
self.save()
def confirm_request(self, request=None):
print(dict(request.POST))
post_dict = dict(request.POST)
if post_dict.get('status') in [0, '0', [0], ['0']]:
try:
pna_token = self.pna_token
response = self.client.request_normal_sale_confirm(pna_token)
# response = {'status': 0, 'cardNumberMasked': '504172******9210', 'rrn': 511629210215, 'appToken': 4101434578524, 'token': 'NDEwMTQzNDU3ODUyNA=='}
# post = <QueryDict: {'Token': ['NDEwMTI0Nzc0MDMzMA=='], 'OrderId': ['7'], 'TerminalNo': ['31127029'], 'RRN': ['511629156251'], 'status': ['0'], 'TspToken': ['00000000-0000-0000-0000-000000000000'], 'HashCardNumber': ['6008617E6BAB76997499446356F5C8B60288445650DD551FDF32007BCF2B14AF'], 'Amount': ['21,000'], 'SwAmount': [''], 'STraceNo': ['123232']}>
# post = <QueryDict: {'Token': ['NDI2MDY3ODI0MTg1OA=='], 'OrderId': ['47'], 'status': ['-138']}>
self.details = response
if response['status'] == 0:
self.pna_status = StateChoices.SUCCESS.value
self.save()
self.payment_request.charge_wallet_balance()
messages.success(request, 'شارژ انجام شد')
except Exception as e:
print(e)
messages.error(request, str(e))
else:
print(request.POST)
messages.error(request, "نتیجه تراکنش از سمت درگاه دریافت نشد.")
def reverse_request(self):
raise NotImplementedError()
class Fake(BasePGModel):
payment_request = models.OneToOneField(PaymentRequest, on_delete=models.PROTECT, related_name='+')
def make_request(self):
pass
def get_pg_page_url(self):
return reverse('pg:payment-confirm-view', kwargs={'uuid': self.payment_request.uuid})
def confirm_request(self, request=None):
self.payment_request.charge_wallet_balance()
messages.success(request, 'شارژ انجام شد')
self.save()
def reverse_request(self):
raise NotImplementedError()

View file

@ -48,22 +48,19 @@ class PaymentRequestView(UpdateView):
self.object = form.save()
charge_request: PaymentRequest = self.get_object()
if 'fake' in form.data:
print('fake')
if 'pna' in form.data:
charge_request.set_gateway('pna')
charge_request.set_gateway(form.data)
tool = charge_request.get_gateway_tools()
# try:
tool.make_request()
redirect_url = tool.get_redirect_url()
redirect_url = tool.get_pg_page_url()
if redirect_url:
return HttpResponseRedirect(redirect_url)
else:
messages.error(self.request, 'can not redirect to payment gateway')
messages.info(self.request, 'در پردازش صفحه خطایی وجود دارد.')
# TODO: redirect to error page
return HttpResponseRedirect(reverse('pg:payment-confirm-view', kwargs={'uuid': charge_request.uuid}))
@ -81,13 +78,15 @@ class PaymentConfirmView(UpdateView):
# return Charge.objects.filter(state__in=[StateChoices.CREATED.value, StateChoices.SUCCESS.value])
def get(self, request, *args, **kwargs):
print('get')
print(args)
print(kwargs)
self.object = self.get_object()
context = self.get_context_data()
messages.info(self.request, 'در پردازش صفحه خطایی وجود دارد.')
tool = self.object.get_gateway_tools()
tool.confirm_request(request)
context = self.get_context_data()
return self.render_to_response(context)
def post(self, request, *args, **kwargs):
@ -95,37 +94,17 @@ class PaymentConfirmView(UpdateView):
print(request.POST)
print(args)
print(kwargs)
self.object = self.get_object()
# post = <QueryDict: {'Token': ['NDEwMTI0Nzc0MDMzMA=='], 'OrderId': ['7'], 'TerminalNo': ['31127029'], 'RRN': ['511629156251'], 'status': ['0'], 'TspToken': ['00000000-0000-0000-0000-000000000000'], 'HashCardNumber': ['6008617E6BAB76997499446356F5C8B60288445650DD551FDF32007BCF2B14AF'], 'Amount': ['21,000'], 'SwAmount': [''], 'STraceNo': ['123232']}>
if 'redirect-to-app' in request.POST:
response = HttpResponse(status=302)
response['Location'] = self.object.callback_url
return response
else:
# post = <QueryDict: {'Token': ['NDEwMTI0Nzc0MDMzMA=='], 'OrderId': ['7'], 'TerminalNo': ['31127029'], 'RRN': ['511629156251'], 'status': ['0'], 'TspToken': ['00000000-0000-0000-0000-000000000000'], 'HashCardNumber': ['6008617E6BAB76997499446356F5C8B60288445650DD551FDF32007BCF2B14AF'], 'Amount': ['21,000'], 'SwAmount': [''], 'STraceNo': ['123232']}>
# post = <QueryDict: {'Token': ['NDI2MDY3ODI0MTg1OA=='], 'OrderId': ['47'], 'status': ['-138']}>
print(dict(request.POST))
post_dict = dict(request.POST)
if post_dict.get('status') in [0, '0', [0], ['0']]:
try:
payment_request: PaymentRequest = self.get_object()
tool = payment_request.get_gateway_tools()
tool.confirm_request()
payment_request.charge_wallet_balance()
messages.success(self.request, 'شارژ انجام شد')
except Exception as e:
print(e)
messages.error(self.request, str(e))
else:
print(request.POST)
messages.error(self.request, "نتیجه تراکنش از سمت درگاه دریافت نشد.")
context = self.get_context_data(object=self.object)
return self.render_to_response(context)
self.object = self.get_object()
tool = self.object.get_gateway_tools()
tool.confirm_request(request)
context = self.get_context_data(object=self.object)
return self.render_to_response(context)
# def form_valid(self, form):

View file

@ -26,9 +26,9 @@
<button type="submit" class="btn mx-auto center-block" name="pna">
<img class="img-thumbnail" width="128" height="128" src="{% static "image/pna.png" %}"/>
</button>
{# <button type="submit" class="btn mx-auto center-block" name="fake">#}
{# <img class="img-thumbnail" width="128" height="128" src="{% static "image/fake.png" %}"/>#}
{# </button>#}
<button type="submit" class="btn mx-auto center-block" name="fake">
<img class="img-thumbnail" width="128" height="128" src="{% static "image/fake.png" %}"/>
</button>
</div>
</div>
</div>