diff options
| author | Rafi Zadanly <zadanlyr@gmail.com> | 2023-08-15 16:03:58 +0700 |
|---|---|---|
| committer | Rafi Zadanly <zadanlyr@gmail.com> | 2023-08-15 16:03:58 +0700 |
| commit | dd233630dce7128b6e25660db3e655b0a2e069e3 (patch) | |
| tree | 8f3e81d53156c783177fad6fdfa0a322db39ba0a | |
| parent | b603e5eca682c7d42d259d3432316ed28b41737f (diff) | |
Refactor sale order model
| -rw-r--r-- | indoteknik_custom/models/performance_test.py | 20 | ||||
| -rwxr-xr-x | indoteknik_custom/models/sale_order.py | 237 |
2 files changed, 81 insertions, 176 deletions
diff --git a/indoteknik_custom/models/performance_test.py b/indoteknik_custom/models/performance_test.py new file mode 100644 index 00000000..1782eb9d --- /dev/null +++ b/indoteknik_custom/models/performance_test.py @@ -0,0 +1,20 @@ +import time, logging + +_logger = logging.getLogger(__name__) + +def performance_test(num_tests): + def decorator(func): + def wrapper(*args, **kwargs): + total_time = 0 + for _ in range(num_tests): + start_time = time.time() + result = func(*args, **kwargs) + end_time = time.time() + total_time += end_time - start_time + + average_time = total_time / num_tests + _logger.info(f"Average execution time over {num_tests} tests: {average_time:.6f} seconds") + return result + + return wrapper + return decorator diff --git a/indoteknik_custom/models/sale_order.py b/indoteknik_custom/models/sale_order.py index 25d28bbb..0f4c5c2e 100755 --- a/indoteknik_custom/models/sale_order.py +++ b/indoteknik_custom/models/sale_order.py @@ -1,14 +1,6 @@ from odoo import fields, models, api, _ -from odoo.exceptions import AccessError, UserError, ValidationError -from odoo.tools.misc import formatLang, get_lang -import logging -import warnings -import random -import string -import requests -import math -import json -from datetime import timedelta, date +from odoo.exceptions import UserError +import logging, random, string, requests, math, json _logger = logging.getLogger(__name__) @@ -28,7 +20,7 @@ class SaleOrder(models.Model): ], string='Approval Status', readonly=True, copy=False, index=True, tracking=3) carrier_id = fields.Many2one('delivery.carrier', string='Shipping Method') have_visit_service = fields.Boolean(string='Have Visit Service', help='To compute is customer get visit service', - compute='_compute_have_visit_service') + compute='_have_visit_service') delivery_amt = fields.Float('Delivery Amt') shipping_cost_covered = fields.Selection([ ('indoteknik', 'Indoteknik'), @@ -92,11 +84,15 @@ class SaleOrder(models.Model): source_id = fields.Many2one('utm.source', 'Source', domain="[('id', 'in', [32, 59, 60, 61])]") def _compute_purchase_total(self): + for order in self: total = 0 for line in order.order_line: total += line.vendor_subtotal order.purchase_total = total + end_time = time.time() + execution_time = end_time - start_time + print(f"Total execution time: {execution_time} seconds") def generate_payment_link_midtrans_sales_order(self): # midtrans_url = 'https://app.sandbox.midtrans.com/snap/v1/transactions' # dev - sandbox @@ -152,84 +148,28 @@ class SaleOrder(models.Model): return res - def calculate_so_status_beginning(self): - so_state = ['sale'] - sales = self.env['sale.order'].search([ - ('state', 'in', so_state),# must add validation so_status - ]) - for sale in sales: - sum_qty_ship = sum_qty_so = 0 - have_outstanding_pick = False - - for pick in sale.picking_ids: - if pick.state == 'draft' or pick.state == 'assigned' or pick.state == 'confirmed' or pick.state == 'waiting': - have_outstanding_pick = True - - for so_line in sale.order_line: - sum_qty_so += so_line.product_uom_qty - sum_qty_ship += so_line.qty_delivered - - if have_outstanding_pick: - if sum_qty_so > sum_qty_ship > 0: - sale.so_status = 'sebagian' - else: - sale.so_status = 'menunggu' - else: - sale.so_status = 'terproses' - _logger.info('Calculate SO Status %s' % sale.id) - - def _calculate_all_so_status(self, limit=500): - so_state = ['sale'] - sales = self.env['sale.order'].search([ - ('state', 'in', so_state), - # ('so_status', '!=', 'terproses'), - ], order='id desc', limit=limit) - for sale in sales: - sum_qty_ship = sum_qty_so = 0 - have_outstanding_pick = False - - for pick in sale.picking_ids: - if pick.state == 'draft' or pick.state == 'assigned' or pick.state == 'confirmed' or pick.state == 'waiting': - have_outstanding_pick = True - - for so_line in sale.order_line: - sum_qty_so += so_line.product_uom_qty - sum_qty_ship += so_line.qty_delivered - - if have_outstanding_pick: - if sum_qty_so > sum_qty_ship > 0: - sale.so_status = 'sebagian' - else: - sale.so_status = 'menunggu' - else: - sale.so_status = 'terproses' - _logger.info('Calculate All SO Status %s' % sale.id) - def calculate_so_status(self): so_state = ['sale'] - sales = self.env['sale.order'].search([ + sales = self.search([ ('state', 'in', so_state), ('so_status', '!=', 'terproses'), ]) + sales = self.browse(12656) for sale in sales: - sum_qty_ship = sum_qty_so = 0 - have_outstanding_pick = False - - for pick in sale.picking_ids: - if pick.state == 'draft' or pick.state == 'assigned' or pick.state == 'confirmed' or pick.state == 'waiting': - have_outstanding_pick = True + print(sale.check_due()) + continue + picking_states = {'draft', 'assigned', 'confirmed', 'waiting'} + have_outstanding_pick = any(x.state in picking_states for x in sale.picking_ids) - for so_line in sale.order_line: - sum_qty_so += so_line.product_uom_qty - sum_qty_ship += so_line.qty_delivered + sum_qty_so = sum(so_line.product_uom_qty for so_line in sale.order_line) + sum_qty_ship = sum(so_line.qty_delivered for so_line in sale.order_line) - if have_outstanding_pick: - if sum_qty_so > sum_qty_ship > 0: - sale.so_status = 'sebagian' - else: - sale.so_status = 'menunggu' - else: + if not have_outstanding_pick: sale.so_status = 'terproses' + elif sum_qty_so > sum_qty_ship > 0: + sale.so_status = 'sebagian' + else: + sale.so_status = 'menunggu' _logger.info('Calculate SO Status %s' % sale.id) @api.onchange('partner_shipping_id') @@ -267,64 +207,33 @@ class SaleOrder(models.Model): def _have_outstanding_invoice(self): invoice_state = ['posted', 'draft'] for order in self: - if not order.invoice_ids: - order.have_outstanding_invoice = False - for invoice in order.invoice_ids: - if invoice.state in invoice_state: - order.have_outstanding_invoice = True - else: - order.have_outstanding_invoice = False + order.have_outstanding_invoice = any(inv.state in invoice_state for inv in order.invoice_ids) def _have_outstanding_picking(self): picking_state = ['done', 'confirmed', 'draft'] for order in self: - if not order.picking_ids: - order.have_outstanding_picking = False - for picking in order.picking_ids: - if picking in picking_state: - order.have_outstanding_picking = True - else: - order.have_outstanding_picking = False + order.have_outstanding_picking = any(pick.state in picking_state for pick in order.picking_ids) def _have_outstanding_po(self): po_state = ['done', 'draft', 'purchase'] for order in self: - if not order.purchase_ids: - order.have_outstanding_po = False - for purchase in order.purchase_ids: - if purchase.state in po_state: - order.have_outstanding_po = True - else: - order.have_outstanding_po = False + order.have_outstanding_po = any(po.state in po_state for po in order.purchase_ids) - def _compute_have_visit_service(self): - limit = 20000000 - self.have_visit_service = False - if self.amount_total > limit: - self.have_visit_service = True + def _have_visit_service(self): + minimum_amount = 20000000 + for order in self: + order.have_visit_service = self.amount_total > minimum_amount def check_due(self): """To show the due amount and warning stage""" for order in self: - if order.partner_id.parent_id: - partner_id = order.partner_id.parent_id - else: - partner_id = order.partner_id - - if partner_id and partner_id.due_amount > 0 \ - and partner_id.active_limit \ - and partner_id.enable_credit_limit: - order.has_due = True + partner = order.partner_id.parent_id or order.partner_id + if partner and partner.active_limit and partner.enable_credit_limit: + order.has_due = partner.due_amount > 0 + if order.outstanding_amount >= partner.warning_stage and partner.warning_stage != 0: + order.is_warning = True else: order.has_due = False - if partner_id and partner_id.active_limit\ - and partner_id.enable_credit_limit: - if order.outstanding_amount >= partner_id.warning_stage: - if partner_id.warning_stage != 0: - order.is_warning = True - else: - order.is_warning = False - else: order.is_warning = False def sale_order_approve(self): @@ -333,44 +242,23 @@ class SaleOrder(models.Model): for order in self: if order.warehouse_id.id != 8: #GD Bandengan raise UserError('Gudang harus Bandengan') - if order.state == 'cancel' or order.state == 'done' or order.state == 'sale': + if order.state not in ['draft', 'sent']: raise UserError("Status harus draft atau sent") if not order.partner_invoice_id.npwp: raise UserError("NPWP harus diisi di master data konsumen, jika non pkp dapat diisi 00.000.000.0-000.000") if '-' not in order.npwp or '.' not in order.npwp: raise UserError("Isi NPWP Dengan Benar!") - if order.partner_id.parent_id: - if not order.partner_id.parent_id.property_payment_term_id: - raise UserError("Payment Term pada Master Data Customer harus diisi") - if not order.partner_id.parent_id.active_limit: - raise UserError("Credit Limit pada Master Data Customer harus diisi") - if order.payment_term_id != order.partner_id.parent_id.property_payment_term_id: - raise UserError("Payment Term berbeda pada Master Data Customer") - else: - if not order.partner_id.property_payment_term_id: - raise UserError("Payment Term pada Master Data Customer harus diisi") - if not order.partner_id.active_limit: - raise UserError("Credit Limit pada Master Data Customer harus diisi") - if order.payment_term_id != order.partner_id.property_payment_term_id: - raise UserError("Payment Term berbeda pada Master Data Customer") - if not order.sales_tax_id: - raise UserError("Tax di Header harus diisi") - if not order.carrier_id: - raise UserError("Shipping Method harus diisi") - for line in order.order_line: - if line.product_id.id == 385544: - raise UserError('Produk Sementara Tidak Bisa Di Confirm atau Ask Approval') - if not line.product_id or line.product_id.type == 'service': - continue - # must add product can sell validation - if not line.product_id.product_tmpl_id.sale_ok: - raise UserError('Product %s belum bisa dijual, harap hubungi finance' % line.product_id.display_name) - if line.product_id.id == 224484: - raise UserError(_('Tidak bisa Confirm menggunakan Produk Sementara')) - if not line.vendor_id or not line.purchase_price: - raise UserError(_('Isi Vendor dan Harga Beli sebelum Request Approval')) - + partner = order.partner_id.parent_id or order.partner_id + if not partner.property_payment_term_id: + raise UserError("Payment Term pada Master Data Customer harus diisi") + if not partner.active_limit: + raise UserError("Credit Limit pada Master Data Customer harus diisi") + if order.payment_term_id != partner.property_payment_term_id: + raise UserError("Payment Term berbeda pada Master Data Customer") + + order.order_line.validate_confirm() + if order.validate_partner_invoice_due(): return self._notification_has_unapprove_due() @@ -380,8 +268,8 @@ class SaleOrder(models.Model): elif order._notification_margin_manager(): order.approval_status = 'pengajuan1' return self._notification_has_margin_manager() - else: - raise UserError("Bisa langsung Confirm") + + raise UserError("Bisa langsung Confirm") def action_cancel(self): # TODO stephan prevent cancel if have invoice, do, and po @@ -475,34 +363,20 @@ class SaleOrder(models.Model): } def _set_sppkp_npwp_contact(self): - parent_id = self.partner_id.parent_id - parent_id = parent_id if parent_id else self.partner_id + partner = self.partner_id.parent_id or self.partner_id - parent_id.customer_type = self.customer_type - parent_id.npwp = self.npwp - parent_id.sppkp = self.sppkp + partner.customer_type = self.customer_type + partner.npwp = self.npwp + partner.sppkp = self.sppkp def action_confirm(self): for order in self: if order.warehouse_id.id != 8: #GD Bandengan raise UserError('Gudang harus Bandengan') - if not order.sales_tax_id: - raise UserError("Tax di Header harus diisi") - if not order.carrier_id: - raise UserError("Shipping Method harus diisi") if '-' not in order.npwp or '.' not in order.npwp: raise UserError("Isi NPWP Dengan Benar!") - for line in order.order_line: - if not line.product_id or line.product_id.type == 'service': - continue - # must add product can sell validation - if not line.product_id.product_tmpl_id.sale_ok: - raise UserError('Product %s belum bisa dijual, harap hubungi finance' % line.product_id.display_name) - if line.product_id.id == 224484: - raise UserError(_('Tidak bisa Confirm menggunakan Produk Sementara')) - if not line.vendor_id or not line.purchase_price or not line.purchase_tax_id: - raise UserError(_('Isi Vendor, Harga Beli, dan Tax sebelum Request Approval')) + order.order_line.validate_confirm() if order.validate_partner_invoice_due(): return self._notification_has_unapprove_due() @@ -777,3 +651,14 @@ class SaleOrderLine(models.Model): # negative discounts (= surcharge) are included in the display price return max(base_price, final_price) + + def validate_confirm(self): + for line in self: + if line.product_id.id in [385544, 224484]: + raise UserError('Produk Sementara Tidak Bisa Di Confirm atau Ask Approval') + if not line.product_id or line.product_id.type == 'service': + continue + if not line.product_id.product_tmpl_id.sale_ok: + raise UserError('Product %s belum bisa dijual, harap hubungi finance' % line.product_id.display_name) + if not line.vendor_id or not line.purchase_price: + raise UserError(_('Isi Vendor dan Harga Beli sebelum Request Approval')) |
