feat: Display a customer's top 3 purchased products in the POS partner editor.
This commit is contained in:
parent
84ae87fdcf
commit
ebab33f7a9
Binary file not shown.
@ -25,3 +25,22 @@ class ResPartner(models.Model):
|
||||
'price_subtotal_incl': line.price_subtotal_incl,
|
||||
} for line in order.lines],
|
||||
} for order in orders]
|
||||
|
||||
@api.model
|
||||
def get_pos_top_products(self, partner_id):
|
||||
# SQL query to get top 3 products by quantity for a specific partner
|
||||
query = """
|
||||
SELECT
|
||||
pt.name ->> 'en_US' as product_name,
|
||||
SUM(pol.qty) as total_qty
|
||||
FROM pos_order_line pol
|
||||
JOIN pos_order po ON pol.order_id = po.id
|
||||
JOIN product_product pp ON pol.product_id = pp.id
|
||||
JOIN product_template pt ON pp.product_tmpl_id = pt.id
|
||||
WHERE po.partner_id = %s
|
||||
GROUP BY pt.name
|
||||
ORDER BY total_qty DESC
|
||||
LIMIT 3
|
||||
"""
|
||||
self.env.cr.execute(query, (partner_id,))
|
||||
return self.env.cr.dictfetchall()
|
||||
|
||||
@ -9,21 +9,25 @@ patch(PartnerDetailsEdit.prototype, {
|
||||
setup() {
|
||||
super.setup();
|
||||
this.orm = useService("orm");
|
||||
this.state = useState({ ...this.state, lastOrders: [] });
|
||||
this.state = useState({ ...this.state, lastOrders: [], topProducts: [] });
|
||||
|
||||
onWillStart(async () => {
|
||||
await this.fetchLastOrders();
|
||||
await this.fetchData();
|
||||
});
|
||||
},
|
||||
|
||||
async fetchLastOrders() {
|
||||
async fetchData() {
|
||||
const partnerId = this.props.partner.id;
|
||||
if (partnerId) {
|
||||
try {
|
||||
const orders = await this.orm.call("res.partner", "get_pos_last_orders", [partnerId]);
|
||||
const [orders, topProducts] = await Promise.all([
|
||||
this.orm.call("res.partner", "get_pos_last_orders", [partnerId]),
|
||||
this.orm.call("res.partner", "get_pos_top_products", [partnerId])
|
||||
]);
|
||||
this.state.lastOrders = orders;
|
||||
this.state.topProducts = topProducts;
|
||||
} catch (error) {
|
||||
console.error("Error fetching orders:", error);
|
||||
console.error("Error fetching data:", error);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -5,6 +5,24 @@
|
||||
<xpath expr="//section" position="after">
|
||||
<section class="partner-details-orders d-flex flex-column m-3">
|
||||
<div class="container">
|
||||
<h3 class="mb-3">Top 3 Products</h3>
|
||||
<t t-if="state.topProducts and state.topProducts.length > 0">
|
||||
<div class="list-group mb-4">
|
||||
<t t-foreach="state.topProducts" t-as="product" t-key="product.product_name">
|
||||
<div class="list-group-item d-flex justify-content-between align-items-center">
|
||||
<span class="fw-bold" t-esc="product.product_name"/>
|
||||
<span class="text-muted">
|
||||
<i class="fa fa-shopping-cart me-1"/>
|
||||
<strong class="text-dark" style="font-size: 1.1em;"><t t-esc="product.total_qty"/></strong> Units
|
||||
</span>
|
||||
</div>
|
||||
</t>
|
||||
</div>
|
||||
</t>
|
||||
<t t-else="">
|
||||
<div class="alert alert-info mb-4">No top products found.</div>
|
||||
</t>
|
||||
|
||||
<h3 class="mb-3">Last Orders</h3>
|
||||
<t t-if="state.lastOrders and state.lastOrders.length > 0">
|
||||
<div class="list-group">
|
||||
|
||||
Loading…
Reference in New Issue
Block a user