Merge branch 'develop' into get_incoming_rate_v14_fix

This commit is contained in:
Hossein Yousefian 2023-04-20 16:50:34 +03:30 committed by GitHub
commit 984eb2a0dd
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
16 changed files with 145 additions and 28 deletions

View File

@ -1,3 +1,4 @@
import functools
import inspect
import frappe
@ -120,12 +121,14 @@ def get_region(company=None):
You can also set global company flag in `frappe.flags.company`
"""
if company or frappe.flags.company:
return frappe.get_cached_value("Company", company or frappe.flags.company, "country")
elif frappe.flags.country:
return frappe.flags.country
else:
return frappe.get_system_settings("country")
if not company:
company = frappe.local.flags.company
if company:
return frappe.get_cached_value("Company", company, "country")
return frappe.flags.country or frappe.get_system_settings("country")
def allow_regional(fn):
@ -136,6 +139,7 @@ def allow_regional(fn):
def myfunction():
pass"""
@functools.wraps(fn)
def caller(*args, **kwargs):
overrides = frappe.get_hooks("regional_overrides", {}).get(get_region())
function_path = f"{inspect.getmodule(fn).__name__}.{fn.__name__}"

View File

@ -60,6 +60,7 @@ class PaymentEntry(AccountsController):
def validate(self):
self.setup_party_account_field()
self.set_missing_values()
self.set_missing_ref_details()
self.validate_payment_type()
self.validate_party_details()
self.set_exchange_rate()
@ -219,11 +220,16 @@ class PaymentEntry(AccountsController):
else self.paid_to_account_currency
)
self.set_missing_ref_details()
def set_missing_ref_details(self, force=False):
def set_missing_ref_details(
self, force: bool = False, update_ref_details_only_for: list | None = None
) -> None:
for d in self.get("references"):
if d.allocated_amount:
if update_ref_details_only_for and (
not (d.reference_doctype, d.reference_name) in update_ref_details_only_for
):
continue
ref_details = get_reference_details(
d.reference_doctype, d.reference_name, self.party_account_currency
)
@ -1811,6 +1817,7 @@ def get_payment_entry(
pe.setup_party_account_field()
pe.set_missing_values()
pe.set_missing_ref_details()
update_accounting_dimensions(pe, doc)

View File

@ -259,6 +259,8 @@ def set_address_details(
)
if doctype in TRANSACTION_TYPES:
# required to set correct region
frappe.flags.company = company
get_regional_address_details(party_details, doctype, company)
return party_address, shipping_address

View File

@ -646,6 +646,7 @@ def update_reference_in_payment_entry(d, payment_entry, do_not_save=False):
payment_entry.flags.ignore_validate_update_after_submit = True
payment_entry.setup_party_account_field()
payment_entry.set_missing_values()
payment_entry.set_missing_ref_details()
payment_entry.set_amounts()
if not do_not_save:

View File

@ -976,6 +976,8 @@ def get_itemised_tax_breakup_html(doc):
@frappe.whitelist()
def get_round_off_applicable_accounts(company, account_list):
# required to set correct region
frappe.flags.company = company
account_list = get_regional_round_off_accounts(company, account_list)
return account_list

View File

@ -411,7 +411,6 @@ frappe.ui.form.on("BOM", {
}
frm.set_value("process_loss_qty", qty);
frm.set_value("add_process_loss_cost_in_fg", qty ? 1: 0);
}
});

View File

@ -625,20 +625,18 @@ erpnext.work_order = {
// all materials transferred for manufacturing, make this primary
finish_btn.addClass('btn-primary');
}
} else {
frappe.db.get_doc("Manufacturing Settings").then((doc) => {
let allowance_percentage = doc.overproduction_percentage_for_work_order;
} else if (frm.doc.__onload && frm.doc.__onload.overproduction_percentage) {
let allowance_percentage = frm.doc.__onload.overproduction_percentage;
if (allowance_percentage > 0) {
let allowed_qty = frm.doc.qty + ((allowance_percentage / 100) * frm.doc.qty);
if (allowance_percentage > 0) {
let allowed_qty = frm.doc.qty + ((allowance_percentage / 100) * frm.doc.qty);
if ((flt(doc.produced_qty) < allowed_qty)) {
frm.add_custom_button(__('Finish'), function() {
erpnext.work_order.make_se(frm, 'Manufacture');
});
}
if ((flt(doc.produced_qty) < allowed_qty)) {
frm.add_custom_button(__('Finish'), function() {
erpnext.work_order.make_se(frm, 'Manufacture');
});
}
});
}
}
}
} else {

View File

@ -96,7 +96,6 @@
"read_only": 1
},
{
"depends_on": "eval:!doc.work_order || doc.docstatus == 1",
"fieldname": "employee_detail",
"fieldtype": "Section Break",
"label": "Employee Detail"
@ -311,7 +310,7 @@
"idx": 1,
"is_submittable": 1,
"links": [],
"modified": "2023-02-14 04:55:41.735991",
"modified": "2023-04-20 15:59:11.107831",
"modified_by": "Administrator",
"module": "Projects",
"name": "Timesheet",

View File

@ -616,7 +616,7 @@ def make_stock_entry(source_name, target_doc=None):
target.set_transfer_qty()
target.set_actual_qty()
target.calculate_rate_and_amount(raise_error_if_no_rate=False)
target.set_stock_entry_type()
target.stock_entry_type = target.purpose
target.set_job_card_data()
doclist = get_mapped_doc(

View File

@ -54,6 +54,8 @@ class TestMaterialRequest(FrappeTestCase):
mr.submit()
se = make_stock_entry(mr.name)
self.assertEqual(se.stock_entry_type, "Material Transfer")
self.assertEqual(se.purpose, "Material Transfer")
self.assertEqual(se.doctype, "Stock Entry")
self.assertEqual(len(se.get("items")), len(mr.get("items")))
@ -69,6 +71,8 @@ class TestMaterialRequest(FrappeTestCase):
in_transit_warehouse = get_in_transit_warehouse(mr.company)
se = make_in_transit_stock_entry(mr.name, in_transit_warehouse)
self.assertEqual(se.stock_entry_type, "Material Transfer")
self.assertEqual(se.purpose, "Material Transfer")
self.assertEqual(se.doctype, "Stock Entry")
for row in se.get("items"):
self.assertEqual(row.t_warehouse, in_transit_warehouse)

View File

@ -380,7 +380,19 @@ class PurchaseReceipt(BuyingController):
outgoing_amount = d.base_net_amount
if self.is_internal_supplier and d.valuation_rate:
outgoing_amount = d.valuation_rate * d.stock_qty
outgoing_amount = abs(
frappe.db.get_value(
"Stock Ledger Entry",
{
"voucher_type": "Purchase Receipt",
"voucher_no": self.name,
"voucher_detail_no": d.name,
"warehouse": d.from_warehouse,
"is_cancelled": 0,
},
"stock_value_difference",
)
)
credit_amount = outgoing_amount
if credit_amount:

View File

@ -1610,6 +1610,89 @@ class TestPurchaseReceipt(FrappeTestCase):
frappe.db.set_single_value("Stock Settings", "over_delivery_receipt_allowance", 0)
def test_internal_pr_gl_entries(self):
from erpnext.stock import get_warehouse_account_map
from erpnext.stock.doctype.delivery_note.delivery_note import make_inter_company_purchase_receipt
from erpnext.stock.doctype.delivery_note.test_delivery_note import create_delivery_note
from erpnext.stock.doctype.stock_entry.test_stock_entry import make_stock_entry
from erpnext.stock.doctype.stock_reconciliation.test_stock_reconciliation import (
create_stock_reconciliation,
)
prepare_data_for_internal_transfer()
customer = "_Test Internal Customer 2"
company = "_Test Company with perpetual inventory"
from_warehouse = create_warehouse("_Test Internal From Warehouse New", company=company)
target_warehouse = create_warehouse("_Test Internal GIT Warehouse New", company=company)
to_warehouse = create_warehouse("_Test Internal To Warehouse New", company=company)
item = make_item(properties={"is_stock_item": 1, "valuation_rate": 100})
make_stock_entry(
purpose="Material Receipt",
item_code=item.name,
qty=10,
company=company,
to_warehouse=from_warehouse,
posting_date=add_days(today(), -3),
)
# Step - 1: Create Delivery Note with Internal Customer
dn = create_delivery_note(
item_code=item.name,
company=company,
customer=customer,
cost_center="Main - TCP1",
expense_account="Cost of Goods Sold - TCP1",
qty=10,
rate=100,
warehouse=from_warehouse,
target_warehouse=target_warehouse,
posting_date=add_days(today(), -2),
)
# Step - 2: Create Internal Purchase Receipt
pr = make_inter_company_purchase_receipt(dn.name)
pr.items[0].qty = 10
pr.items[0].from_warehouse = target_warehouse
pr.items[0].warehouse = to_warehouse
pr.items[0].rejected_warehouse = from_warehouse
pr.save()
pr.submit()
# Step - 3: Create back-date Stock Reconciliation [After DN and Before PR]
create_stock_reconciliation(
item_code=item,
warehouse=target_warehouse,
qty=10,
rate=50,
company=company,
posting_date=add_days(today(), -1),
)
warehouse_account = get_warehouse_account_map(company)
stock_account_value = frappe.db.get_value(
"GL Entry",
{
"account": warehouse_account[target_warehouse]["account"],
"voucher_type": "Purchase Receipt",
"voucher_no": pr.name,
"is_cancelled": 0,
},
fieldname=["credit"],
)
stock_diff = frappe.db.get_value(
"Stock Ledger Entry",
{
"voucher_type": "Purchase Receipt",
"voucher_no": pr.name,
"is_cancelled": 0,
},
fieldname=["sum(stock_value_difference)"],
)
# Value of Stock Account should be equal to the sum of Stock Value Difference
self.assertEqual(stock_account_value, stock_diff)
def prepare_data_for_internal_transfer():
from erpnext.accounts.doctype.sales_invoice.test_sales_invoice import create_internal_supplier

View File

@ -2346,7 +2346,7 @@ def move_sample_to_retention_warehouse(company, items):
@frappe.whitelist()
def make_stock_in_entry(source_name, target_doc=None):
def set_missing_values(source, target):
target.set_stock_entry_type()
target.stock_entry_type = "Material Transfer"
target.set_missing_values()
def update_item(source_doc, target_doc, source_parent):

View File

@ -202,6 +202,9 @@ class TestStockEntry(FrappeTestCase):
)
end_transit_entry = make_stock_in_entry(transit_entry.name)
self.assertEqual(end_transit_entry.stock_entry_type, "Material Transfer")
self.assertEqual(end_transit_entry.purpose, "Material Transfer")
self.assertEqual(transit_entry.name, end_transit_entry.outgoing_stock_entry)
self.assertEqual(transit_entry.name, end_transit_entry.items[0].against_stock_entry)
self.assertEqual(transit_entry.items[0].name, end_transit_entry.items[0].ste_detail)

View File

@ -530,7 +530,9 @@ class TestStockReconciliation(FrappeTestCase, StockTestMixin):
# check if cancellation of stock reco is blocked
self.assertRaises(NegativeStockError, sr.cancel)
repost_exists = bool(frappe.db.exists("Repost Item Valuation", {"voucher_no": sr.name}))
repost_exists = bool(
frappe.db.exists("Repost Item Valuation", {"voucher_no": sr.name, "status": "Queued"})
)
self.assertFalse(repost_exists, msg="Negative stock validation not working on reco cancellation")
def test_intermediate_sr_bin_update(self):

View File

@ -1453,10 +1453,11 @@ def get_next_stock_reco(kwargs):
)
.orderby(CombineDatetime(sle.posting_date, sle.posting_time))
.orderby(sle.creation)
.limit(1)
)
if kwargs.get("batch_no"):
query.where(sle.batch_no == kwargs.get("batch_no"))
query = query.where(sle.batch_no == kwargs.get("batch_no"))
return query.run(as_dict=True)