Esempio n. 1
0
    def create_shipment_of_all_products(self, supplier=None):
        """
        Create a shipment of all the products in this Order, no matter whether or not any have been previously
        marked as shipped or not.

        See the documentation for `create_shipment`.

        :param supplier: The Supplier to use. If `None`, the first supplier in
                         the order is used. (If several are in the order, this fails.)
        :return: Saved, complete Shipment object
        :rtype: shoop.shop.models.Shipment
        """
        suppliers_to_product_quantities = defaultdict(lambda: defaultdict(lambda: 0))
        lines = (
            self.lines
            .filter(type=OrderLineType.PRODUCT)
            .values_list("supplier_id", "product_id", "quantity"))
        for supplier_id, product_id, quantity in lines:
            if product_id:
                suppliers_to_product_quantities[supplier_id][product_id] += quantity

        if not suppliers_to_product_quantities:
            raise NoProductsToShipException("Could not find any products to ship.")

        if supplier is None:
            if len(suppliers_to_product_quantities) > 1:  # pragma: no cover
                raise ValueError("Can only use create_shipment_of_all_products when there is only one supplier")
            supplier_id, quantities = suppliers_to_product_quantities.popitem()
            supplier = Supplier.objects.get(pk=supplier_id)
        else:
            quantities = suppliers_to_product_quantities[supplier.id]

        products = dict((product.pk, product) for product in Product.objects.filter(pk__in=quantities.keys()))
        quantities = dict((products[product_id], quantity) for (product_id, quantity) in quantities.items())
        return self.create_shipment(supplier, quantities)
Esempio n. 2
0
    def create_shipment(self,
                        product_quantities,
                        supplier=None,
                        shipment=None):
        """
        Create a shipment for this order from `product_quantities`.
        `product_quantities` is expected to be a dict mapping Product instances to quantities.

        Only quantities over 0 are taken into account, and if the mapping is empty or has no quantity value
        over 0, `NoProductsToShipException` will be raised.

        :param product_quantities: a dict mapping Product instances to quantities to ship
        :type product_quantities: dict[shoop.shop.models.Product, decimal.Decimal]
        :param supplier: Optional Supplier for this product. No validation is made
                         as to whether the given supplier supplies the products.
        :param shipment: Optional unsaved Shipment for ShipmentProduct's. If not given
                         Shipment is created based on supplier parameter.
        :raises: NoProductsToShipException
        :return: Saved, complete Shipment object
        :rtype: shoop.core.models.Shipment
        """
        if not product_quantities or not any(
                quantity > 0 for quantity in product_quantities.values()):
            raise NoProductsToShipException(
                "No products to ship (`quantities` is empty or has no quantity over 0)."
            )

        assert (supplier or shipment)
        if shipment:
            assert shipment.order == self

        from ._shipments import ShipmentProduct
        if not shipment:
            from ._shipments import Shipment
            shipment = Shipment(order=self, supplier=supplier)
        shipment.save()

        for product, quantity in product_quantities.items():
            if quantity > 0:
                sp = ShipmentProduct(shipment=shipment,
                                     product=product,
                                     quantity=quantity)
                sp.cache_values()
                sp.save()

        shipment.cache_values()
        shipment.save()

        self.add_log_entry(_(u"Shipment #%d created.") % shipment.id)
        self.update_shipping_status()
        shipment_created.send(sender=type(self), order=self, shipment=shipment)
        return shipment
Esempio n. 3
0
    def create_shipment(self, supplier, product_quantities):
        """
        Create a shipment for this order from `product_quantities`.
        `product_quantities` is expected to be a dict mapping Product instances to quantities.

        Only quantities over 0 are taken into account, and if the mapping is empty or has no quantity value
        over 0, `NoProductsToShipException` will be raised.

        :param supplier: The Supplier for this product. No validation is made
                         as to whether the given supplier supplies the products.
        :param product_quantities: a dict mapping Product instances to quantities to ship
        :type product_quantities: dict[shoop.shop.models.products.Product, decimal.Decimal]
        :raises: NoProductsToShipException
        :return: Saved, complete Shipment object
        :rtype: shoop.core.models.shipments.Shipment
        """
        if not product_quantities or not any(
                quantity > 0 for quantity in product_quantities.values()):
            raise NoProductsToShipException(
                "No products to ship (`quantities` is empty or has no quantity over 0)."
            )

        from .shipments import Shipment, ShipmentProduct

        shipment = Shipment(order=self, supplier=supplier)
        shipment.save()

        for product, quantity in product_quantities.items():
            if quantity > 0:
                sp = ShipmentProduct(shipment=shipment,
                                     product=product,
                                     quantity=quantity)
                sp.cache_values()
                sp.save()

        shipment.cache_values()
        shipment.save()

        self.add_log_entry(_(u"Shipment #%d created.") % shipment.id)
        self.check_and_set_fully_shipped()
        return shipment