from django.views.decorators.csrf import csrf_exempt from django.conf import settings from django.http import HttpResponse from rest_framework import generics from rest_framework.response import Response from rest_framework.views import APIView from drf_spectacular.utils import extend_schema import os import logging from .models import StripeTransaction from commerce.models import Order, Payment logger = logging.getLogger(__name__) import stripe stripe.api_key = os.getenv("STRIPE_SECRET_KEY") class StripeWebhook(APIView): @extend_schema( tags=["stripe"], ) def post(self, request): payload = request.body sig_header = request.META['HTTP_STRIPE_SIGNATURE'] try: #build stripe event event = stripe.Webhook.construct_event( payload, sig_header, os.getenv("STRIPE_WEBHOOK_SECRET") ) except ValueError as e: logger.error(f"Invalid payload: {e}") return HttpResponse(status=400) except stripe.error as e: # stripe error logger.error(f"Stripe error: {e}") return HttpResponse(status=400) session = event['data']['object'] # ZAPLACENO if event['type'] == 'checkout.session.completed': stripe_transaction = StripeTransaction.objects.get(stripe_session_id=session.id) if stripe_transaction: stripe_transaction.paid() logger.info(f"Transaction {stripe_transaction.id} marked as paid.") else: logger.warning(f"No transaction found for session ID: {session.id}") # EXPIRACE (zrušení objednávky) uživatel nezaplatil do 24 hodin! elif event['type'] == 'checkout.session.expired': order = Order.objects.get(payment=Payment.objects.get(stripe=StripeTransaction.objects.get(stripe_session_id=session.id))) order.status = Order.STATUS_CHOICES.CANCELLED order.save() elif event['type'] == 'payment_intent.payment_failed': #nothing to do for now pass # REFUND POTVRZEN elif event['type'] == 'payment_intent.refunded': session = event['data']['object'] stripe_transaction = StripeTransaction.objects.get(stripe_payment_intent=session.id) if stripe_transaction: stripe_transaction.refund_confirmed() logger.info(f"Transaction {stripe_transaction.id} marked as refunded.")