From fca5c08671169703d935161fc4bb0c5c05548a62 Mon Sep 17 00:00:00 2001 From: Miqdad Date: Tue, 23 Sep 2025 08:32:19 +0700 Subject: fix validation error when creating SO in midnight --- indoteknik_custom/models/sale_order.py | 88 +++++++++++++++++++++++++--------- 1 file changed, 66 insertions(+), 22 deletions(-) (limited to 'indoteknik_custom/models/sale_order.py') diff --git a/indoteknik_custom/models/sale_order.py b/indoteknik_custom/models/sale_order.py index 39830ffc..02ceb62b 100755 --- a/indoteknik_custom/models/sale_order.py +++ b/indoteknik_custom/models/sale_order.py @@ -1700,57 +1700,101 @@ class SaleOrder(models.Model): # .format(eta_minimum.strftime('%d-%m-%Y'), eta_minimum.strftime('%d-%m-%Y')) # ) + # def _validate_expected_ready_ship_date(self): + # """ + # Pastikan expected_ready_to_ship tidak lebih awal dari SLA minimum. + # Dipanggil setiap onchange / simpan SO. + # """ + # for rec in self: + # # ───────────────────────────────────────────────────── + # # 1. Hanya validasi kalau field sudah terisi + # # (quotation baru / belum ada tanggal → abaikan) + # # ───────────────────────────────────────────────────── + # if not rec.expected_ready_to_ship: + # continue + # + # current_date = datetime.now() + # + # # ───────────────────────────────────────────────────── + # # 2. Hitung SLA berdasarkan product lines (jika ada) + # # ───────────────────────────────────────────────────── + # products = rec.order_line + # if products: + # sla_data = rec.calculate_sla_by_vendor(products) + # max_sla_time = sla_data.get('slatime', 1) + # else: + # # belum ada item → gunakan default 1 hari + # max_sla_time = 1 + # + # # offset hari libur / weekend + # offset, is3pm = rec.get_days_until_next_business_day(current_date) + # min_days = max_sla_time + offset - 1 + # eta_minimum = current_date + timedelta(days=min_days) + # + # # ───────────────────────────────────────────────────── + # # 3. Validasi - raise error bila terlalu cepat + # # ───────────────────────────────────────────────────── + # if rec.expected_ready_to_ship.date() < eta_minimum.date(): + # # set otomatis ke tanggal minimum supaya user tidak perlu + # # menekan Save dua kali + # rec.expected_ready_to_ship = eta_minimum + # + # raise ValidationError( + # _("Tanggal 'Expected Ready to Ship' tidak boleh " + # "lebih kecil dari %(tgl)s. Mohon pilih minimal %(tgl)s.") + # % {'tgl': eta_minimum.strftime('%d-%m-%Y')} + # ) + # else: + # # sinkronkan ke field commitment_date + # rec.commitment_date = rec.expected_ready_to_ship + def _validate_expected_ready_ship_date(self): """ Pastikan expected_ready_to_ship tidak lebih awal dari SLA minimum. Dipanggil setiap onchange / simpan SO. """ for rec in self: - # ───────────────────────────────────────────────────── - # 1. Hanya validasi kalau field sudah terisi - # (quotation baru / belum ada tanggal → abaikan) - # ───────────────────────────────────────────────────── if not rec.expected_ready_to_ship: continue - current_date = datetime.now() + # ADDED: gunakan "sekarang" lokal user, bukan datetime.now() server + current_date = fields.Datetime.context_timestamp(rec, fields.Datetime.now()) - # ───────────────────────────────────────────────────── - # 2. Hitung SLA berdasarkan product lines (jika ada) - # ───────────────────────────────────────────────────── + # Hitung SLA products = rec.order_line if products: sla_data = rec.calculate_sla_by_vendor(products) max_sla_time = sla_data.get('slatime', 1) else: - # belum ada item → gunakan default 1 hari max_sla_time = 1 - # offset hari libur / weekend + # offset hari libur/weekend offset, is3pm = rec.get_days_until_next_business_day(current_date) min_days = max_sla_time + offset - 1 eta_minimum = current_date + timedelta(days=min_days) - # ───────────────────────────────────────────────────── - # 3. Validasi - raise error bila terlalu cepat - # ───────────────────────────────────────────────────── - if rec.expected_ready_to_ship.date() < eta_minimum.date(): - # set otomatis ke tanggal minimum supaya user tidak perlu - # menekan Save dua kali - rec.expected_ready_to_ship = eta_minimum + if rec._fields['expected_ready_to_ship'].type == 'date': + exp_date_local = rec.expected_ready_to_ship + else: + exp_date_local = fields.Datetime.context_timestamp( + rec, rec.expected_ready_to_ship + ).date() + + if exp_date_local < eta_minimum.date(): + # (opsional) auto-set ke minimum → konversi balik ke UTC naive bila field Datetime + if rec._fields['expected_ready_to_ship'].type == 'date': + rec.expected_ready_to_ship = eta_minimum.date() + else: + rec.expected_ready_to_ship = eta_minimum.astimezone(pytz.UTC).replace(tzinfo=None) raise ValidationError( _("Tanggal 'Expected Ready to Ship' tidak boleh " - "lebih kecil dari %(tgl)s. Mohon pilih minimal %(tgl)s.") + "lebih kecil dari %(tgl)s. Mohon pilih minimal %(tgl)s.") % {'tgl': eta_minimum.strftime('%d-%m-%Y')} ) else: - # sinkronkan ke field commitment_date rec.commitment_date = rec.expected_ready_to_ship - - - @api.onchange('expected_ready_to_ship') #Hangle Onchange form Expected Ready to Ship def _onchange_expected_ready_ship_date(self): self._validate_expected_ready_ship_date() -- cgit v1.2.3 From 22c5def88445676675e1978e77471ef939f46daa Mon Sep 17 00:00:00 2001 From: Azka Nathan Date: Wed, 24 Sep 2025 09:37:15 +0700 Subject: pushh --- indoteknik_custom/models/sale_order.py | 22 ++++++++++++++++++++-- 1 file changed, 20 insertions(+), 2 deletions(-) (limited to 'indoteknik_custom/models/sale_order.py') diff --git a/indoteknik_custom/models/sale_order.py b/indoteknik_custom/models/sale_order.py index 02ceb62b..fd872b53 100755 --- a/indoteknik_custom/models/sale_order.py +++ b/indoteknik_custom/models/sale_order.py @@ -398,6 +398,23 @@ class SaleOrder(models.Model): compute="_compute_partner_is_cbd_locked" ) + def action_open_partial_delivery_wizard(self): + self.ensure_one() + pickings = self.picking_ids.filtered(lambda p: p.state not in ['done', 'cancel'] and p.name and 'BU/PICK/' in p.name) + return { + 'type': 'ir.actions.act_window', + 'name': 'Partial Delivery', + 'res_model': 'partial.delivery.wizard', + 'view_mode': 'form', + 'target': 'new', + 'context': { + 'default_sale_id': self.id, + # kasih langsung list of int biar ga ribet di wizard + 'default_picking_ids': pickings.ids, + } + } + + @api.depends('partner_id.is_cbd_locked') def _compute_partner_is_cbd_locked(self): for order in self: @@ -1795,6 +1812,7 @@ class SaleOrder(models.Model): else: rec.commitment_date = rec.expected_ready_to_ship + @api.onchange('expected_ready_to_ship') #Hangle Onchange form Expected Ready to Ship def _onchange_expected_ready_ship_date(self): self._validate_expected_ready_ship_date() @@ -2258,7 +2276,7 @@ class SaleOrder(models.Model): raise UserError("Terdapat DUPLIKASI data pada Product {}".format(line.product_id.display_name)) def sale_order_approve(self): - self.check_duplicate_product() + # self.check_duplicate_product() self.check_product_bom() self.check_credit_limit() self.check_limit_so_to_invoice() @@ -2528,7 +2546,7 @@ class SaleOrder(models.Model): for order in self: order._validate_delivery_amt() order._validate_uniform_taxes() - order.check_duplicate_product() + # order.check_duplicate_product() order.check_product_bom() order.check_credit_limit() order.check_limit_so_to_invoice() -- cgit v1.2.3 From 80f811a7ccca771990fcbf59df6e92dc8e0acc14 Mon Sep 17 00:00:00 2001 From: Miqdad Date: Wed, 24 Sep 2025 09:41:18 +0700 Subject: balikin validate erts --- indoteknik_custom/models/sale_order.py | 132 ++++++++++++++++----------------- 1 file changed, 66 insertions(+), 66 deletions(-) (limited to 'indoteknik_custom/models/sale_order.py') diff --git a/indoteknik_custom/models/sale_order.py b/indoteknik_custom/models/sale_order.py index fd872b53..85f0d274 100755 --- a/indoteknik_custom/models/sale_order.py +++ b/indoteknik_custom/models/sale_order.py @@ -1717,101 +1717,101 @@ class SaleOrder(models.Model): # .format(eta_minimum.strftime('%d-%m-%Y'), eta_minimum.strftime('%d-%m-%Y')) # ) - # def _validate_expected_ready_ship_date(self): - # """ - # Pastikan expected_ready_to_ship tidak lebih awal dari SLA minimum. - # Dipanggil setiap onchange / simpan SO. - # """ - # for rec in self: - # # ───────────────────────────────────────────────────── - # # 1. Hanya validasi kalau field sudah terisi - # # (quotation baru / belum ada tanggal → abaikan) - # # ───────────────────────────────────────────────────── - # if not rec.expected_ready_to_ship: - # continue - # - # current_date = datetime.now() - # - # # ───────────────────────────────────────────────────── - # # 2. Hitung SLA berdasarkan product lines (jika ada) - # # ───────────────────────────────────────────────────── - # products = rec.order_line - # if products: - # sla_data = rec.calculate_sla_by_vendor(products) - # max_sla_time = sla_data.get('slatime', 1) - # else: - # # belum ada item → gunakan default 1 hari - # max_sla_time = 1 - # - # # offset hari libur / weekend - # offset, is3pm = rec.get_days_until_next_business_day(current_date) - # min_days = max_sla_time + offset - 1 - # eta_minimum = current_date + timedelta(days=min_days) - # - # # ───────────────────────────────────────────────────── - # # 3. Validasi - raise error bila terlalu cepat - # # ───────────────────────────────────────────────────── - # if rec.expected_ready_to_ship.date() < eta_minimum.date(): - # # set otomatis ke tanggal minimum supaya user tidak perlu - # # menekan Save dua kali - # rec.expected_ready_to_ship = eta_minimum - # - # raise ValidationError( - # _("Tanggal 'Expected Ready to Ship' tidak boleh " - # "lebih kecil dari %(tgl)s. Mohon pilih minimal %(tgl)s.") - # % {'tgl': eta_minimum.strftime('%d-%m-%Y')} - # ) - # else: - # # sinkronkan ke field commitment_date - # rec.commitment_date = rec.expected_ready_to_ship - def _validate_expected_ready_ship_date(self): """ Pastikan expected_ready_to_ship tidak lebih awal dari SLA minimum. Dipanggil setiap onchange / simpan SO. """ for rec in self: + # ───────────────────────────────────────────────────── + # 1. Hanya validasi kalau field sudah terisi + # (quotation baru / belum ada tanggal → abaikan) + # ───────────────────────────────────────────────────── if not rec.expected_ready_to_ship: continue - # ADDED: gunakan "sekarang" lokal user, bukan datetime.now() server - current_date = fields.Datetime.context_timestamp(rec, fields.Datetime.now()) + current_date = datetime.now() - # Hitung SLA + # ───────────────────────────────────────────────────── + # 2. Hitung SLA berdasarkan product lines (jika ada) + # ───────────────────────────────────────────────────── products = rec.order_line if products: sla_data = rec.calculate_sla_by_vendor(products) max_sla_time = sla_data.get('slatime', 1) else: + # belum ada item → gunakan default 1 hari max_sla_time = 1 - # offset hari libur/weekend + # offset hari libur / weekend offset, is3pm = rec.get_days_until_next_business_day(current_date) min_days = max_sla_time + offset - 1 eta_minimum = current_date + timedelta(days=min_days) - if rec._fields['expected_ready_to_ship'].type == 'date': - exp_date_local = rec.expected_ready_to_ship - else: - exp_date_local = fields.Datetime.context_timestamp( - rec, rec.expected_ready_to_ship - ).date() - - if exp_date_local < eta_minimum.date(): - # (opsional) auto-set ke minimum → konversi balik ke UTC naive bila field Datetime - if rec._fields['expected_ready_to_ship'].type == 'date': - rec.expected_ready_to_ship = eta_minimum.date() - else: - rec.expected_ready_to_ship = eta_minimum.astimezone(pytz.UTC).replace(tzinfo=None) + # ───────────────────────────────────────────────────── + # 3. Validasi - raise error bila terlalu cepat + # ───────────────────────────────────────────────────── + if rec.expected_ready_to_ship.date() < eta_minimum.date(): + # set otomatis ke tanggal minimum supaya user tidak perlu + # menekan Save dua kali + rec.expected_ready_to_ship = eta_minimum raise ValidationError( _("Tanggal 'Expected Ready to Ship' tidak boleh " - "lebih kecil dari %(tgl)s. Mohon pilih minimal %(tgl)s.") + "lebih kecil dari %(tgl)s. Mohon pilih minimal %(tgl)s.") % {'tgl': eta_minimum.strftime('%d-%m-%Y')} ) else: + # sinkronkan ke field commitment_date rec.commitment_date = rec.expected_ready_to_ship + # def _validate_expected_ready_ship_date(self): + # """ + # Pastikan expected_ready_to_ship tidak lebih awal dari SLA minimum. + # Dipanggil setiap onchange / simpan SO. + # """ + # for rec in self: + # if not rec.expected_ready_to_ship: + # continue + # + # # ADDED: gunakan "sekarang" lokal user, bukan datetime.now() server + # current_date = fields.Datetime.context_timestamp(rec, fields.Datetime.now()) + # + # # Hitung SLA + # products = rec.order_line + # if products: + # sla_data = rec.calculate_sla_by_vendor(products) + # max_sla_time = sla_data.get('slatime', 1) + # else: + # max_sla_time = 1 + # + # # offset hari libur/weekend + # offset, is3pm = rec.get_days_until_next_business_day(current_date) + # min_days = max_sla_time + offset - 1 + # eta_minimum = current_date + timedelta(days=min_days) + # + # if rec._fields['expected_ready_to_ship'].type == 'date': + # exp_date_local = rec.expected_ready_to_ship + # else: + # exp_date_local = fields.Datetime.context_timestamp( + # rec, rec.expected_ready_to_ship + # ).date() + # + # if exp_date_local < eta_minimum.date(): + # # (opsional) auto-set ke minimum → konversi balik ke UTC naive bila field Datetime + # if rec._fields['expected_ready_to_ship'].type == 'date': + # rec.expected_ready_to_ship = eta_minimum.date() + # else: + # rec.expected_ready_to_ship = eta_minimum.astimezone(pytz.UTC).replace(tzinfo=None) + # + # raise ValidationError( + # _("Tanggal 'Expected Ready to Ship' tidak boleh " + # "lebih kecil dari %(tgl)s. Mohon pilih minimal %(tgl)s.") + # % {'tgl': eta_minimum.strftime('%d-%m-%Y')} + # ) + # else: + # rec.commitment_date = rec.expected_ready_to_ship + @api.onchange('expected_ready_to_ship') #Hangle Onchange form Expected Ready to Ship def _onchange_expected_ready_ship_date(self): -- cgit v1.2.3 From 5dc3710a5008cbbd3d2e6cbc1fca12bc0bd31eda Mon Sep 17 00:00:00 2001 From: FIN-IT_AndriFP Date: Wed, 24 Sep 2025 13:29:15 +0700 Subject: (andri) fix validasi --- indoteknik_custom/models/sale_order.py | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) (limited to 'indoteknik_custom/models/sale_order.py') diff --git a/indoteknik_custom/models/sale_order.py b/indoteknik_custom/models/sale_order.py index 85f0d274..f80941d2 100755 --- a/indoteknik_custom/models/sale_order.py +++ b/indoteknik_custom/models/sale_order.py @@ -423,13 +423,13 @@ class SaleOrder(models.Model): @api.constrains('payment_term_id', 'partner_id', 'state') def _check_cbd_lock_sale_order(self): - # cbd_term = self.env['account.payment.term'].browse(26) + cbd_term = self.env['account.payment.term'].browse(26) for rec in self: if rec.state == 'draft' and rec.partner_id.is_cbd_locked: - # if rec.payment_term_id and rec.payment_term_id != cbd_term: - raise ValidationError( - "Customer ini terkunci ke CBD, hanya boleh pakai Payment Term CBD." - ) + if rec.payment_term_id and rec.payment_term_id != cbd_term: + raise ValidationError( + "Customer ini terkunci ke CBD, hanya boleh pakai Payment Term CBD." + ) @api.depends('invoice_ids.payment_state', 'invoice_ids.amount_total', 'invoice_ids.amount_residual') def _compute_payment_state_custom(self): -- cgit v1.2.3