You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

81 lines
3.3 KiB

import logging
import os
import requests
from django.conf import settings
from django.db import transaction
from django.utils import timezone
from yandex_money.models import Payment
from finance.loggers import FinanceLogger
from finance.models import InvoiceRebilling, Invoice
from lms import celery_app
finance_logger = FinanceLogger()
@celery_app.task
def periodic_billing():
finance_logger.info("start periodic billing task")
# TODO заюзать Invoice.BILL_STATUSES
invoices = InvoiceRebilling.objects.filter(method='Y', status='W')
# TODO тут был exclude('F') то есть все неоплаченные... но это не верно!
for invoice in invoices.filter(expected_date__lt=timezone.now()):
# выбираем все необработанные из прошлого
with transaction.atomic():
try:
_yandex_repeat_card_payment(invoice)
except Exception as exc:
finance_logger.exception('Yandex Money repeatCardPayment Exception', invoice_id=invoice.id)
invoice.comment += 'Yandex Money: Ошибка при попытке повторного платежа, свяжитесь с клиентской службой'
invoice.save()
def _yandex_repeat_card_payment(invoice):
user = invoice.bill.user
yandex_pay = Payment.objects.create(
order_amount=invoice.price,
customer_number=user.id,
user=user,
cps_email=user.email,
shop_id=settings.YANDEX_MONEY_REBILLING_SHOP_ID,
scid=settings.YANDEX_MONEY_REBILLING_SCID
)
invoice.yandex_pay = yandex_pay
finance_logger.info('YandexMoney repeatCardPayment start', invoice_id=invoice.id)
resp = requests.post(
url=settings.YANDEX_MONEY_MWS_URL + 'repeatCardPayment',
data={
'clientOrderId': invoice.id, # уникальное возрастающее целое число
'invoiceId': invoice.key,
'amount': invoice.price,
'orderNumber': invoice.yandex_pay.order_number
},
cert=(
os.path.join(settings.SSL_ROOT, 'skillbox.cer'),
os.path.join(settings.SSL_ROOT, 'skillbox.key')
),
verify=os.path.join(settings.SSL_ROOT, 'yamoney_chain.cer')
)
resp_text = resp.text
finance_logger.info('YandexMoney repeatCardPayment response',
invoice_id=invoice.id, response=resp_text, code=resp.status_code, )
try:
_check_yandex_response_status(invoice, resp_text)
except Exception as exc:
finance_logger.exception("Can't parse yandex response", invoice_id=invoice.id, response=resp_text)
def _check_yandex_response_status(invoice, resp_text):
from xml.dom import minidom
dom = minidom.parseString(resp_text)
dom.normalize()
resp_node = dom.getElementsByTagName("repeatCardPaymentResponse")[0]
status = resp_node.getAttribute('status')
if status != '0':
error = resp_node.getAttribute('error')
processed_dt = resp_node.getAttribute('processedDT')
tech_message = resp_node.getAttribute('techMessage')
invoice.status += Invoice.BILL_STATUSES[-1][0]
invoice.comment += 'Yandex Money: ошибка № {}, сообщение {} от {}'.format(error, tech_message, processed_dt)