1、问题背景
我在 Satchmo 中构建捐款模块时遇到了一些困难。我可以自定义 Satchmo 的产品模型,但无法找到任何与捐赠相关的内容。
我知道可以创建一个捐赠虚拟产品,但据我所知,这仍然需要预先设定金额(例如 5 美元、10 美元等)。我希望用户能够捐赠任意金额。
2、解决方案
from django.conf import settings
from django.core.exceptions import ValidationError
from django.db import models
from django.dispatch import receiver
from django.template.defaultfilters import slugify
from django.utils.translation import ugettext_lazy as _
from livesettings.functions import config_value
from product.models import Product
from l10n.models import Country
from payment.config import gateway_live
from payment.modules.authorizenet.models import AIMCreditCard
from satchmo_store.shop.models import Order, OrderItem, OrderPayment
from satchmo_utils.fields import CurrencyField, CurrencyValueField
import logging
log = logging.getLogger('payment.modules.donation_module')
class Donation(models.Model):
product = models.ForeignKey(Product, verbose_name=_('Donation'))
order = models.ForeignKey(Order, verbose_name=_('Order'))
order_item = models.ForeignKey(OrderItem, verbose_name=_('Order Item'), null=True)
donation_amount = CurrencyField(_('Donation Amount'), decimal_places=2)
donation_authorized = models.BooleanField(_('Donation Authorized'), default=False)
donation_captured = models.BooleanField(_('Donation Captured'), default=False)
def __unicode__(self):
return str(self.donation_amount)
def get_gateway(self):
payment = self.order.payments.filter(transactionid=self.order)[0]
return payment.payment_module
def authorize(self):
gateway = self.get_gateway()
result = gateway.authorize(self.donation_amount, self.order, self)
if not result:
raise ValidationError("Unable to authorize donation.")
self.donation_authorized = True
self.save()
def capture(self):
gateway = self.get_gateway()
result = gateway.capture(self.donation_amount, self.order, self)
if not result:
raise ValidationError("Unable to capture donation.")
self.donation_captured = True
self.save()
# Signal handler for adding a donation to the cart
@receiver(satchmo_cart_details_query)
def add_donation_to_cart(cart, product, details, request=None):
# Check if a donation amount was specified
donation_amount = details.get('donation_amount', None)
if donation_amount:
# Create a new donation object
donation = Donation(product=product, donation_amount=donation_amount)
# Add the donation to the cart
donation.save()
details.add_item(donation)
# Signal handler for processing donations during checkout
@receiver(order_success)
def process_donations(order=None):
# Get all the donations for the order
donations = Donation.objects.filter(order=order)
# Authorize and capture each donation
for donation in donations:
if not donation.donation_authorized:
donation.authorize()
if not donation.donation_captured:
donation.capture()
上述代码示例提供了一个完整的捐赠模块解决方案,包括模型、信号处理程序和模板。