Вы не можете выбрать более 25 тем Темы должны начинаться с буквы или цифры, могут содержать дефисы(-) и должны содержать не более 35 символов.

abstract_models.py 4.6KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127
  1. from django.conf import settings
  2. from django.db import models
  3. from django.utils.translation import ugettext_lazy as _
  4. from oscar.apps.partner.wrappers import get_partner_wrapper
  5. class AbstractPartner(models.Model):
  6. u"""Fulfillment partner"""
  7. name = models.CharField(max_length=128, unique=True)
  8. # A partner can have users assigned to it. These can be used
  9. # to provide authentication for webservices etc.
  10. users = models.ManyToManyField('auth.User', related_name="partners", null=True)
  11. class Meta:
  12. verbose_name_plural = 'Fulfillment partners'
  13. abstract = True
  14. permissions = (
  15. ("can_edit_stock_records", "Can edit stock records"),
  16. ("can_view_stock_records", "Can view stock records"),
  17. ("can_edit_product_range", "Can edit product range"),
  18. ("can_view_product_range", "Can view product range"),
  19. ("can_edit_order_lines", "Can edit order lines"),
  20. ("can_view_order_lines", "Can view order lines"),
  21. )
  22. def __unicode__(self):
  23. return self.name
  24. class AbstractStockRecord(models.Model):
  25. u"""
  26. A basic stock record.
  27. This links a product to a partner, together with price and availability
  28. information. Most projects will need to subclass this object to add custom
  29. fields such as lead_time, report_code, min_quantity.
  30. """
  31. product = models.OneToOneField('product.Item')
  32. partner = models.ForeignKey('partner.Partner')
  33. partner_sku = models.CharField(_("Partner SKU"), max_length=128, blank=True)
  34. # Price info:
  35. # We deliberately don't store tax information to allow each project
  36. # to subclass this model and put its own fields for convey tax.
  37. price_currency = models.CharField(max_length=12, default=settings.OSCAR_DEFAULT_CURRENCY)
  38. # This is the base price for calculations - tax should be applied
  39. # by the appropriate method. We don't store it here as its calculation is
  40. # highly domain-specific. It is NULLable because some items don't have a fixed
  41. # price.
  42. price_excl_tax = models.DecimalField(decimal_places=2, max_digits=12, blank=True, null=True)
  43. # Retail price for this item
  44. price_retail = models.DecimalField(decimal_places=2, max_digits=12, blank=True, null=True)
  45. # Cost price is optional as not all partner supply it
  46. cost_price = models.DecimalField(decimal_places=2, max_digits=12, blank=True, null=True)
  47. # Stock level information
  48. num_in_stock = models.IntegerField(default=0, blank=True, null=True)
  49. num_allocated = models.IntegerField(default=0, blank=True, null=True)
  50. # Date information
  51. date_created = models.DateTimeField(auto_now_add=True)
  52. date_updated = models.DateTimeField(auto_now=True, db_index=True)
  53. class Meta:
  54. abstract = True
  55. def decrement_num_in_stock(self, delta):
  56. """
  57. Decrement an item's stock level
  58. """
  59. if self.num_in_stock >= delta:
  60. self.num_in_stock -= delta
  61. self.num_allocated += delta
  62. self.save()
  63. def set_discount_price(self, price):
  64. """
  65. A setter method for setting a new price.
  66. This is called from within the "discount" app, which is responsible
  67. for applying fixed-discount offers to products. We use a setter method
  68. so that this behaviour can be customised in projects.
  69. """
  70. self.price_excl_tax = price
  71. self.save()
  72. # Price retrieval methods - these default to no tax being applicable
  73. # These are intended to be overridden.
  74. @property
  75. def availability(self):
  76. u"""Return an item's availability as a string"""
  77. return get_partner_wrapper(self.partner.name).availability(self)
  78. @property
  79. def dispatch_date(self):
  80. u"""
  81. Returns the estimated dispatch date for a line
  82. """
  83. return get_partner_wrapper(self.partner.name).dispatch_date(self)
  84. @property
  85. def price_incl_tax(self):
  86. """
  87. Return a product's price including tax.
  88. This defaults to the price_excl_tax as tax calculations are
  89. domain specific. This class needs to be subclassed and tax logic
  90. added to this method.
  91. """
  92. return self.price_excl_tax + self.price_tax
  93. @property
  94. def price_tax(self):
  95. u"""Return a product's tax value"""
  96. return 0
  97. def __unicode__(self):
  98. if self.partner_sku:
  99. return "%s (%s): %s" % (self.partner.name, self.partner_sku, self.product.title)
  100. else:
  101. return "%s: %s" % (self.partner.name, self.product.title)