Использование Django 1.11
У меня есть следующие модели:
class Vendor(Model):
class Product(Model):
class Pricebook(Model):
class Quote(Model):
vendor = models.ForeignKey(Vendor)
class SKU(Model):
product = models.ForeignKey(Product)
pricebook = models.ForeignKey(Pricebook)
vendor = models.ForeignKey(Vendor)
class SKUPrice(Model):
sku = models.ForeignKey(SKU, related_name="prices")
class LineItem(Model):
quote = models.ForeignKey(Quote, related_name="quote_line_items")
sku = models.ForeignKey(SKU)
Это необработанный запрос, который работает для меня.
SELECT
qli.quantity,
sku_source.product_id,
sku_dest.id as sku_dest_id,
sku_dest_price.id as sku_dest_price_id
FROM lineitem qli
INNER JOIN sku sku_source ON
qli.sku_id = sku_source.id
LEFT JOIN sku sku_dest ON
sku_dest.pricebook_id = sku_source.pricebook_id AND
sku_dest.product_id = sku_source.product_id
LEFT JOIN skuprice sku_dest_price ON
sku_dest_price.status = 'default' AND
sku_dest_price.sku_id = sku_dest.id
WHERE qli.quotation_id = 40 AND
qli.quantity > 0 AND
sku_dest.vendor_id = 38;
Что я пробовалis:
(the_quote_with_id_as_40
.quotation_line_items
.filter(quantity__gt=0)
.select_related('sku__product')
.values('sku__product__id', 'quantity')
)
Это производит этот запрос
SELECT "sku"."product_id", "lineitem"."quantity"
FROM "lineitem"
INNER JOIN "sku" ON ("lineitem"."sku_id" = "sku"."id")
WHERE ("lineitem"."quotation_id" = 40 AND
"lineitem"."quantity" > 0)
, что не совсем то, что я хочу.
Я, конечно, могу использовать необработанный запрос.Но я хотел бы знать, если возможно использовать ORM.По крайней мере, это для расширения моих знаний.
Спасибо.
ОБНОВЛЕНИЕ
Поскольку есть просьба уточнить мои модели, япишу следующее.
У меня есть объект Quote.Это позволяет много объектов LineItem.Каждый LineItem один-ко-многим с SKU и Quote.
Артикул принадлежит Ценовой книжке, Продукту и Продавцу.Это описание отношения также можно почерпнуть из приведенного выше кода.
Но для ясности я повторю здесь.
Эта схема такова, что один и тот же Продукт может быть продан разными Продавцами, но они будут выглядеть как разные SKU.
Это специально.
Наш вариант использования следующий: пользователь пытается скопировать элементы LineItem отдельной цитаты в другую цитату.
По мнению пользователей, у них нет опыта, чтобы оценить различия между SKU, LineItem или Продуктом.
Все это - продукт в их сознании.Они просто хотят, чтобы один и тот же продукт появлялся в другой цитате с одинаковым количеством.
Проблема заключается в следующем.Теперь у нас есть две цитаты (исходная цитата для копирования и целевая цитата для копирования).Обе цитаты могут иметь одного и того же продавца.Или они не могут.Пользователь хочет, чтобы мое приложение Django автоматически обслуживало обе ситуации.
Так что это означает, что мне нужно выяснить следующее, прежде чем дублировать.
- количество, указанное в LineItem
- Продукт, как указано в LineItem по отношению к SKU
- , находит соответствующий SKU, проданный Продавцом для цены назначения
- и соответствующую цену за единицу
Необработанный запрос позволяет мне извлечь все 4 фрагмента информации в одном запросе.Это эффективно.
Следовательно, вы видите, что у меня есть псевдоним sku_source
и sku_dest
Вот почему мои критерии WHERE содержат 3 условия:
- будут скопированы только исходные элементы LineItems с количеством> 0
- будут скопированы только строки LineItems из определенного исходного предложения
- только SKU, предназначенные для конкретного поставщика (в данном случае поставщик для конечного предложения) будет рассмотрено
Возможно, что:
несколько LineItems для одного и того же продукта (по отношению к SKU) появятся в одном источникеЦитата.
Поставщик пункта назначения (имеется в виду Продавец пункта назначения) не продает конкретный Продукт, который продает Поставщик источника.Поэтому я использую LEFT JOIN.Это означает, что данный конкретный продукт не будет продублирован.
Надеюсь, это прояснит ситуацию.