Skip to content

Commit 23a750c

Browse files
feat(payment): Add gateway link renewal method
1 parent 014c780 commit 23a750c

6 files changed

Lines changed: 54 additions & 7 deletions

File tree

mono/acm/settings.py

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -284,4 +284,5 @@
284284
SKYROOM_ROOMID = env("SKYROOM_ROOMID", default="")
285285

286286
# Competition
287-
COMPETITION_APPROVAL_REDIRECT_URL = env("COMPETITION_APPROVAL_REDIRECT_URL", default="https://aut-icpc.ir/DAMN")
287+
COMPETITION_APPROVAL_REDIRECT_URL = env("COMPETITION_APPROVAL_REDIRECT_URL", default="https://aut-icpc.ir/DAMN")
288+
PAYMENT_EMAIL_LINK_BASE_URL = env("PAYMENT_EMAIL_LINK_BASE_URL", default="")

mono/competitions/services.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -302,7 +302,7 @@ def backoffice_approve_request(tr: TeamRequest) -> TeamRequest:
302302
status_code=409,
303303
)
304304

305-
tr.payment_link = result.url
305+
tr.payment_link = f"{settings.PAYMENT_EMAIL_LINK_BASE_URL}?authority={result.authority}"
306306
tr.status = TeamRequest.Status.PENDING_PAYMENT
307307
tr.save(update_fields=["payment_link", "status"])
308308
send_email_with_custom_template(

mono/payment/serializers.py

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,4 +7,11 @@ class VerifySerializer(serializers.Serializer):
77
class PaymentSerializer(serializers.ModelSerializer):
88
class Meta:
99
model = Payment
10-
fields = ("id","status","authority","ref_id","amount","zarinpal_code","zarinpal_message","target_type","target_id")
10+
fields = ("id","status","authority","ref_id","amount","zarinpal_code","zarinpal_message","target_type","target_id")
11+
12+
13+
class StartPaymentSerializer(serializers.Serializer):
14+
authority = serializers.CharField()
15+
16+
class Meta:
17+
fields = ("authority",)

mono/payment/services.py

Lines changed: 26 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@
2626
class StartPayResult:
2727
url: str
2828
payment: Payment
29+
authority: str
2930

3031

3132
# ---- Helpers ----
@@ -198,7 +199,7 @@ def initiate_payment_for_target(
198199
metadata={"fee_type": d.get("fee_type"), "fee": d.get("fee"), **(extra_metadata or {})},
199200
)
200201
startpay_url = f"https://payment.zarinpal.com/pg/StartPay/{authority}"
201-
return StartPayResult(url=startpay_url, payment=pay)
202+
return StartPayResult(url=startpay_url, payment=pay, authority=authority)
202203

203204

204205
@transaction.atomic
@@ -275,3 +276,27 @@ def verify_by_authority(*, user: User, authority: str) -> Payment:
275276
pass
276277

277278
return p
279+
280+
def startpay(authority: str) -> str:
281+
current_payment = Payment.objects.filter(authority=authority).last()
282+
if not current_payment:
283+
raise CustomAPIException(
284+
code=EC.PAY_NOT_FOUND_FOR_USER,
285+
message="Payment not found for this user/authority",
286+
status_code=404)
287+
try:
288+
new_payment = initiate_payment_for_target(
289+
user=current_payment.user,
290+
target_type=current_payment.target_type,
291+
target_id=current_payment.target_id,
292+
amount=current_payment.amount,
293+
description=current_payment.description,
294+
)
295+
except Exception as e:
296+
raise CustomAPIException(
297+
message=f"Failed to initiate payment: {e}",
298+
code=EC.COMP_PAYMENT_INIT_FAILED,
299+
status_code=409
300+
)
301+
return new_payment.url
302+

mono/payment/urls.py

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,8 @@
11
from django.urls import path
2-
from .views import VerifyPaymentView, CallbackView
2+
from .views import VerifyPaymentView, CallbackView, StartpaymentView
33

44
urlpatterns = [
55
path("verify/", VerifyPaymentView.as_view()),
66
path("callback/", CallbackView.as_view()),
7+
path("startpay/", StartpaymentView.as_view())
78
]

mono/payment/views.py

Lines changed: 15 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,9 +9,10 @@
99

1010
from .serializers import (
1111
VerifySerializer,
12-
PaymentSerializer,
12+
PaymentSerializer, StartPaymentSerializer,
1313
)
14-
from .services import verify_by_authority
14+
from .services import verify_by_authority, startpay
15+
1516

1617
class VerifyPaymentView(APIView):
1718
permission_classes = [permissions.IsAuthenticated]
@@ -43,3 +44,15 @@ def get(self, request):
4344
authority = request.GET.get("Authority")
4445
url = f"{settings.PAYMENT_FRONTEND_RETURN}?authority={authority}" if authority else settings.PAYMENT_FRONTEND_RETURN
4546
return HttpResponseRedirect(url)
47+
48+
49+
class StartpaymentView(APIView):
50+
permission_classes = []
51+
@extend_schema(
52+
parameters=[StartPaymentSerializer],
53+
responses={302: OpenApiResponse(description="Redirects to new payment page")}
54+
)
55+
def get(self, request):
56+
authority = request.GET.get("authority")
57+
redirection_url = startpay(authority)
58+
return HttpResponseRedirect(redirection_url)

0 commit comments

Comments
 (0)