mirror of
https://github.com/frappe/erpnext.git
synced 2026-06-03 12:19:12 +00:00
Merge pull request #37544 from frappe/version-13-hotfix
chore: release v13
This commit is contained in:
@@ -4,12 +4,7 @@
|
|||||||
|
|
||||||
import frappe
|
import frappe
|
||||||
from frappe import _, msgprint, scrub
|
from frappe import _, msgprint, scrub
|
||||||
from frappe.contacts.doctype.address.address import (
|
from frappe.contacts.doctype.address.address import get_company_address, get_default_address
|
||||||
get_address_display,
|
|
||||||
get_company_address,
|
|
||||||
get_default_address,
|
|
||||||
)
|
|
||||||
from frappe.contacts.doctype.contact.contact import get_contact_details
|
|
||||||
from frappe.core.doctype.user_permission.user_permission import get_permitted_documents
|
from frappe.core.doctype.user_permission.user_permission import get_permitted_documents
|
||||||
from frappe.model.utils import get_fetch_values
|
from frappe.model.utils import get_fetch_values
|
||||||
from frappe.utils import (
|
from frappe.utils import (
|
||||||
@@ -120,6 +115,7 @@ def _get_party_details(
|
|||||||
party_address,
|
party_address,
|
||||||
company_address,
|
company_address,
|
||||||
shipping_address,
|
shipping_address,
|
||||||
|
ignore_permissions=ignore_permissions,
|
||||||
)
|
)
|
||||||
set_contact_details(party_details, party, party_type)
|
set_contact_details(party_details, party, party_type)
|
||||||
set_other_values(party_details, party, party_type)
|
set_other_values(party_details, party, party_type)
|
||||||
@@ -183,6 +179,8 @@ def set_address_details(
|
|||||||
party_address=None,
|
party_address=None,
|
||||||
company_address=None,
|
company_address=None,
|
||||||
shipping_address=None,
|
shipping_address=None,
|
||||||
|
*,
|
||||||
|
ignore_permissions=False
|
||||||
):
|
):
|
||||||
billing_address_field = (
|
billing_address_field = (
|
||||||
"customer_address" if party_type == "Lead" else party_type.lower() + "_address"
|
"customer_address" if party_type == "Lead" else party_type.lower() + "_address"
|
||||||
@@ -195,13 +193,17 @@ def set_address_details(
|
|||||||
get_fetch_values(doctype, billing_address_field, party_details[billing_address_field])
|
get_fetch_values(doctype, billing_address_field, party_details[billing_address_field])
|
||||||
)
|
)
|
||||||
# address display
|
# address display
|
||||||
party_details.address_display = get_address_display(party_details[billing_address_field])
|
party_details.address_display = render_address(
|
||||||
|
party_details[billing_address_field], check_permissions=not ignore_permissions
|
||||||
|
)
|
||||||
# shipping address
|
# shipping address
|
||||||
if party_type in ["Customer", "Lead"]:
|
if party_type in ["Customer", "Lead"]:
|
||||||
party_details.shipping_address_name = shipping_address or get_party_shipping_address(
|
party_details.shipping_address_name = shipping_address or get_party_shipping_address(
|
||||||
party_type, party.name
|
party_type, party.name
|
||||||
)
|
)
|
||||||
party_details.shipping_address = get_address_display(party_details["shipping_address_name"])
|
party_details.shipping_address = render_address(
|
||||||
|
party_details["shipping_address_name"], check_permissions=not ignore_permissions
|
||||||
|
)
|
||||||
if doctype:
|
if doctype:
|
||||||
party_details.update(
|
party_details.update(
|
||||||
get_fetch_values(doctype, "shipping_address_name", party_details.shipping_address_name)
|
get_fetch_values(doctype, "shipping_address_name", party_details.shipping_address_name)
|
||||||
@@ -224,7 +226,7 @@ def set_address_details(
|
|||||||
party_details.update(
|
party_details.update(
|
||||||
{
|
{
|
||||||
"shipping_address": shipping_address,
|
"shipping_address": shipping_address,
|
||||||
"shipping_address_display": get_address_display(shipping_address),
|
"shipping_address_display": render_address(shipping_address),
|
||||||
**get_fetch_values(doctype, "shipping_address", shipping_address),
|
**get_fetch_values(doctype, "shipping_address", shipping_address),
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
@@ -235,7 +237,8 @@ def set_address_details(
|
|||||||
{
|
{
|
||||||
"billing_address": party_details.company_address,
|
"billing_address": party_details.company_address,
|
||||||
"billing_address_display": (
|
"billing_address_display": (
|
||||||
party_details.company_address_display or get_address_display(party_details.company_address)
|
party_details.company_address_display
|
||||||
|
or render_address(party_details.company_address, check_permissions=True)
|
||||||
),
|
),
|
||||||
**get_fetch_values(doctype, "billing_address", party_details.company_address),
|
**get_fetch_values(doctype, "billing_address", party_details.company_address),
|
||||||
}
|
}
|
||||||
@@ -277,7 +280,34 @@ def set_contact_details(party_details, party, party_type):
|
|||||||
}
|
}
|
||||||
)
|
)
|
||||||
else:
|
else:
|
||||||
party_details.update(get_contact_details(party_details.contact_person))
|
fields = [
|
||||||
|
"name as contact_person",
|
||||||
|
"salutation",
|
||||||
|
"first_name",
|
||||||
|
"last_name",
|
||||||
|
"email_id as contact_email",
|
||||||
|
"mobile_no as contact_mobile",
|
||||||
|
"phone as contact_phone",
|
||||||
|
"designation as contact_designation",
|
||||||
|
"department as contact_department",
|
||||||
|
]
|
||||||
|
|
||||||
|
contact_details = frappe.db.get_value(
|
||||||
|
"Contact", party_details.contact_person, fields, as_dict=True
|
||||||
|
)
|
||||||
|
|
||||||
|
contact_details.contact_display = " ".join(
|
||||||
|
filter(
|
||||||
|
None,
|
||||||
|
[
|
||||||
|
contact_details.get("salutation"),
|
||||||
|
contact_details.get("first_name"),
|
||||||
|
contact_details.get("last_name"),
|
||||||
|
],
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
party_details.update(contact_details)
|
||||||
|
|
||||||
|
|
||||||
def set_other_values(party_details, party, party_type):
|
def set_other_values(party_details, party, party_type):
|
||||||
@@ -938,3 +968,13 @@ def add_party_account(party_type, party, company, account):
|
|||||||
doc.append("accounts", accounts)
|
doc.append("accounts", accounts)
|
||||||
|
|
||||||
doc.save()
|
doc.save()
|
||||||
|
|
||||||
|
|
||||||
|
def render_address(address, check_permissions=True):
|
||||||
|
try:
|
||||||
|
from frappe.contacts.doctype.address.address import render_address as _render
|
||||||
|
except ImportError:
|
||||||
|
# Older frappe versions where this function is not available
|
||||||
|
from frappe.contacts.doctype.address.address import get_address_display as _render
|
||||||
|
|
||||||
|
return frappe.call(_render, address, check_permissions=check_permissions)
|
||||||
|
|||||||
@@ -457,6 +457,8 @@ class GrossProfitGenerator(object):
|
|||||||
new_row.qty += flt(row.qty)
|
new_row.qty += flt(row.qty)
|
||||||
new_row.buying_amount += flt(row.buying_amount, self.currency_precision)
|
new_row.buying_amount += flt(row.buying_amount, self.currency_precision)
|
||||||
new_row.base_amount += flt(row.base_amount, self.currency_precision)
|
new_row.base_amount += flt(row.base_amount, self.currency_precision)
|
||||||
|
if self.filters.get("group_by") == "Sales Person":
|
||||||
|
new_row.allocated_amount += flt(row.allocated_amount, self.currency_precision)
|
||||||
new_row = self.set_average_rate(new_row)
|
new_row = self.set_average_rate(new_row)
|
||||||
self.grouped_data.append(new_row)
|
self.grouped_data.append(new_row)
|
||||||
else:
|
else:
|
||||||
|
|||||||
@@ -4,9 +4,9 @@
|
|||||||
|
|
||||||
import frappe
|
import frappe
|
||||||
from frappe import _, bold, throw
|
from frappe import _, bold, throw
|
||||||
from frappe.contacts.doctype.address.address import get_address_display
|
|
||||||
from frappe.utils import cint, cstr, flt, get_link_to_form, nowtime
|
from frappe.utils import cint, cstr, flt, get_link_to_form, nowtime
|
||||||
|
|
||||||
|
from erpnext.accounts.party import render_address
|
||||||
from erpnext.controllers.accounts_controller import get_taxes_and_charges
|
from erpnext.controllers.accounts_controller import get_taxes_and_charges
|
||||||
from erpnext.controllers.sales_and_purchase_return import get_rate_for_return
|
from erpnext.controllers.sales_and_purchase_return import get_rate_for_return
|
||||||
from erpnext.controllers.stock_controller import StockController
|
from erpnext.controllers.stock_controller import StockController
|
||||||
@@ -583,7 +583,9 @@ class SellingController(StockController):
|
|||||||
|
|
||||||
for address_field, address_display_field in address_dict.items():
|
for address_field, address_display_field in address_dict.items():
|
||||||
if self.get(address_field):
|
if self.get(address_field):
|
||||||
self.set(address_display_field, get_address_display(self.get(address_field)))
|
self.set(
|
||||||
|
address_display_field, render_address(self.get(address_field), check_permissions=False)
|
||||||
|
)
|
||||||
|
|
||||||
def validate_for_duplicate_items(self):
|
def validate_for_duplicate_items(self):
|
||||||
check_list, chk_dupl_itm = [], []
|
check_list, chk_dupl_itm = [], []
|
||||||
|
|||||||
@@ -4,6 +4,7 @@
|
|||||||
|
|
||||||
import frappe
|
import frappe
|
||||||
from frappe import _
|
from frappe import _
|
||||||
|
from frappe.query_builder.functions import Concat_ws, Date
|
||||||
|
|
||||||
|
|
||||||
def execute(filters=None):
|
def execute(filters=None):
|
||||||
@@ -69,53 +70,41 @@ def get_columns():
|
|||||||
|
|
||||||
|
|
||||||
def get_data(filters):
|
def get_data(filters):
|
||||||
return frappe.db.sql(
|
lead = frappe.qb.DocType("Lead")
|
||||||
"""
|
address = frappe.qb.DocType("Address")
|
||||||
SELECT
|
dynamic_link = frappe.qb.DocType("Dynamic Link")
|
||||||
`tabLead`.name,
|
|
||||||
`tabLead`.lead_name,
|
query = (
|
||||||
`tabLead`.status,
|
frappe.qb.from_(lead)
|
||||||
`tabLead`.lead_owner,
|
.left_join(dynamic_link)
|
||||||
`tabLead`.territory,
|
.on((lead.name == dynamic_link.link_name) & (dynamic_link.parenttype == "Address"))
|
||||||
`tabLead`.source,
|
.left_join(address)
|
||||||
`tabLead`.email_id,
|
.on(address.name == dynamic_link.parent)
|
||||||
`tabLead`.mobile_no,
|
.select(
|
||||||
`tabLead`.phone,
|
lead.name,
|
||||||
`tabLead`.owner,
|
lead.lead_name,
|
||||||
`tabLead`.company,
|
lead.status,
|
||||||
concat_ws(', ',
|
lead.lead_owner,
|
||||||
trim(',' from `tabAddress`.address_line1),
|
lead.territory,
|
||||||
trim(',' from tabAddress.address_line2)
|
lead.source,
|
||||||
) AS address,
|
lead.email_id,
|
||||||
`tabAddress`.state,
|
lead.mobile_no,
|
||||||
`tabAddress`.pincode,
|
lead.phone,
|
||||||
`tabAddress`.country
|
lead.owner,
|
||||||
FROM
|
lead.company,
|
||||||
`tabLead` left join `tabDynamic Link` on (
|
(Concat_ws(", ", address.address_line1, address.address_line2)).as_("address"),
|
||||||
`tabLead`.name = `tabDynamic Link`.link_name and
|
address.state,
|
||||||
`tabDynamic Link`.parenttype = 'Address')
|
address.pincode,
|
||||||
left join `tabAddress` on (
|
address.country,
|
||||||
`tabAddress`.name=`tabDynamic Link`.parent)
|
)
|
||||||
WHERE
|
.where(lead.company == filters.company)
|
||||||
company = %(company)s
|
.where(Date(lead.creation).between(filters.from_date, filters.to_date))
|
||||||
AND DATE(`tabLead`.creation) BETWEEN %(from_date)s AND %(to_date)s
|
|
||||||
{conditions}
|
|
||||||
ORDER BY
|
|
||||||
`tabLead`.creation asc """.format(
|
|
||||||
conditions=get_conditions(filters)
|
|
||||||
),
|
|
||||||
filters,
|
|
||||||
as_dict=1,
|
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
def get_conditions(filters):
|
|
||||||
conditions = []
|
|
||||||
|
|
||||||
if filters.get("territory"):
|
if filters.get("territory"):
|
||||||
conditions.append(" and `tabLead`.territory=%(territory)s")
|
query = query.where(lead.territory == filters.get("territory"))
|
||||||
|
|
||||||
if filters.get("status"):
|
if filters.get("status"):
|
||||||
conditions.append(" and `tabLead`.status=%(status)s")
|
query = query.where(lead.status == filters.get("status"))
|
||||||
|
|
||||||
return " ".join(conditions) if conditions else ""
|
return query.run(as_dict=1)
|
||||||
|
|||||||
@@ -17,7 +17,6 @@ from erpnext.e_commerce.shopping_cart.cart import (
|
|||||||
request_for_quotation,
|
request_for_quotation,
|
||||||
update_cart,
|
update_cart,
|
||||||
)
|
)
|
||||||
from erpnext.tests.utils import create_test_contact_and_address
|
|
||||||
|
|
||||||
|
|
||||||
class TestShoppingCart(unittest.TestCase):
|
class TestShoppingCart(unittest.TestCase):
|
||||||
@@ -28,7 +27,6 @@ class TestShoppingCart(unittest.TestCase):
|
|||||||
|
|
||||||
def setUp(self):
|
def setUp(self):
|
||||||
frappe.set_user("Administrator")
|
frappe.set_user("Administrator")
|
||||||
create_test_contact_and_address()
|
|
||||||
self.enable_shopping_cart()
|
self.enable_shopping_cart()
|
||||||
if not frappe.db.exists("Website Item", {"item_code": "_Test Item"}):
|
if not frappe.db.exists("Website Item", {"item_code": "_Test Item"}):
|
||||||
make_website_item(frappe.get_cached_doc("Item", "_Test Item"))
|
make_website_item(frappe.get_cached_doc("Item", "_Test Item"))
|
||||||
@@ -46,48 +44,57 @@ class TestShoppingCart(unittest.TestCase):
|
|||||||
frappe.db.sql("delete from `tabTax Rule`")
|
frappe.db.sql("delete from `tabTax Rule`")
|
||||||
|
|
||||||
def test_get_cart_new_user(self):
|
def test_get_cart_new_user(self):
|
||||||
self.login_as_new_user()
|
self.login_as_customer(
|
||||||
|
"test_contact_two_customer@example.com", "_Test Contact 2 For _Test Customer"
|
||||||
|
)
|
||||||
|
create_address_and_contact(
|
||||||
|
address_title="_Test Address for Customer 2",
|
||||||
|
first_name="_Test Contact for Customer 2",
|
||||||
|
email="test_contact_two_customer@example.com",
|
||||||
|
customer="_Test Customer 2",
|
||||||
|
)
|
||||||
# test if lead is created and quotation with new lead is fetched
|
# test if lead is created and quotation with new lead is fetched
|
||||||
quotation = _get_cart_quotation()
|
customer = frappe.get_doc("Customer", "_Test Customer 2")
|
||||||
|
quotation = _get_cart_quotation(party=customer)
|
||||||
self.assertEqual(quotation.quotation_to, "Customer")
|
self.assertEqual(quotation.quotation_to, "Customer")
|
||||||
self.assertEqual(
|
self.assertEqual(
|
||||||
quotation.contact_person,
|
quotation.contact_person,
|
||||||
frappe.db.get_value("Contact", dict(email_id="test_cart_user@example.com")),
|
frappe.db.get_value("Contact", dict(email_id="test_contact_two_customer@example.com")),
|
||||||
)
|
)
|
||||||
self.assertEqual(quotation.contact_email, frappe.session.user)
|
self.assertEqual(quotation.contact_email, frappe.session.user)
|
||||||
|
|
||||||
return quotation
|
return quotation
|
||||||
|
|
||||||
def test_get_cart_customer(self):
|
def test_get_cart_customer(self, customer="_Test Customer 2"):
|
||||||
def validate_quotation():
|
def validate_quotation(customer_name):
|
||||||
# test if quotation with customer is fetched
|
# test if quotation with customer is fetched
|
||||||
quotation = _get_cart_quotation()
|
party = frappe.get_doc("Customer", customer_name)
|
||||||
|
quotation = _get_cart_quotation(party=party)
|
||||||
self.assertEqual(quotation.quotation_to, "Customer")
|
self.assertEqual(quotation.quotation_to, "Customer")
|
||||||
self.assertEqual(quotation.party_name, "_Test Customer")
|
self.assertEqual(quotation.party_name, customer_name)
|
||||||
self.assertEqual(quotation.contact_email, frappe.session.user)
|
self.assertEqual(quotation.contact_email, frappe.session.user)
|
||||||
return quotation
|
return quotation
|
||||||
|
|
||||||
self.login_as_customer(
|
quotation = validate_quotation(customer)
|
||||||
"test_contact_two_customer@example.com", "_Test Contact 2 For _Test Customer"
|
|
||||||
)
|
|
||||||
validate_quotation()
|
|
||||||
|
|
||||||
self.login_as_customer()
|
|
||||||
quotation = validate_quotation()
|
|
||||||
|
|
||||||
return quotation
|
return quotation
|
||||||
|
|
||||||
def test_add_to_cart(self):
|
def test_add_to_cart(self):
|
||||||
self.login_as_customer()
|
self.login_as_customer(
|
||||||
|
"test_contact_two_customer@example.com", "_Test Contact 2 For _Test Customer"
|
||||||
|
)
|
||||||
|
create_address_and_contact(
|
||||||
|
address_title="_Test Address for Customer 2",
|
||||||
|
first_name="_Test Contact for Customer 2",
|
||||||
|
email="test_contact_two_customer@example.com",
|
||||||
|
customer="_Test Customer 2",
|
||||||
|
)
|
||||||
# clear existing quotations
|
# clear existing quotations
|
||||||
self.clear_existing_quotations()
|
self.clear_existing_quotations()
|
||||||
|
|
||||||
# add first item
|
# add first item
|
||||||
update_cart("_Test Item", 1)
|
update_cart("_Test Item", 1)
|
||||||
|
|
||||||
quotation = self.test_get_cart_customer()
|
quotation = self.test_get_cart_customer("_Test Customer 2")
|
||||||
|
|
||||||
self.assertEqual(quotation.get("items")[0].item_code, "_Test Item")
|
self.assertEqual(quotation.get("items")[0].item_code, "_Test Item")
|
||||||
self.assertEqual(quotation.get("items")[0].qty, 1)
|
self.assertEqual(quotation.get("items")[0].qty, 1)
|
||||||
@@ -95,7 +102,7 @@ class TestShoppingCart(unittest.TestCase):
|
|||||||
|
|
||||||
# add second item
|
# add second item
|
||||||
update_cart("_Test Item 2", 1)
|
update_cart("_Test Item 2", 1)
|
||||||
quotation = self.test_get_cart_customer()
|
quotation = self.test_get_cart_customer("_Test Customer 2")
|
||||||
self.assertEqual(quotation.get("items")[1].item_code, "_Test Item 2")
|
self.assertEqual(quotation.get("items")[1].item_code, "_Test Item 2")
|
||||||
self.assertEqual(quotation.get("items")[1].qty, 1)
|
self.assertEqual(quotation.get("items")[1].qty, 1)
|
||||||
self.assertEqual(quotation.get("items")[1].amount, 20)
|
self.assertEqual(quotation.get("items")[1].amount, 20)
|
||||||
@@ -108,7 +115,7 @@ class TestShoppingCart(unittest.TestCase):
|
|||||||
|
|
||||||
# update first item
|
# update first item
|
||||||
update_cart("_Test Item", 5)
|
update_cart("_Test Item", 5)
|
||||||
quotation = self.test_get_cart_customer()
|
quotation = self.test_get_cart_customer("_Test Customer 2")
|
||||||
self.assertEqual(quotation.get("items")[0].item_code, "_Test Item")
|
self.assertEqual(quotation.get("items")[0].item_code, "_Test Item")
|
||||||
self.assertEqual(quotation.get("items")[0].qty, 5)
|
self.assertEqual(quotation.get("items")[0].qty, 5)
|
||||||
self.assertEqual(quotation.get("items")[0].amount, 50)
|
self.assertEqual(quotation.get("items")[0].amount, 50)
|
||||||
@@ -121,7 +128,7 @@ class TestShoppingCart(unittest.TestCase):
|
|||||||
|
|
||||||
# remove first item
|
# remove first item
|
||||||
update_cart("_Test Item", 0)
|
update_cart("_Test Item", 0)
|
||||||
quotation = self.test_get_cart_customer()
|
quotation = self.test_get_cart_customer("_Test Customer 2")
|
||||||
|
|
||||||
self.assertEqual(quotation.get("items")[0].item_code, "_Test Item 2")
|
self.assertEqual(quotation.get("items")[0].item_code, "_Test Item 2")
|
||||||
self.assertEqual(quotation.get("items")[0].qty, 1)
|
self.assertEqual(quotation.get("items")[0].qty, 1)
|
||||||
@@ -129,9 +136,20 @@ class TestShoppingCart(unittest.TestCase):
|
|||||||
self.assertEqual(quotation.net_total, 20)
|
self.assertEqual(quotation.net_total, 20)
|
||||||
self.assertEqual(len(quotation.get("items")), 1)
|
self.assertEqual(len(quotation.get("items")), 1)
|
||||||
|
|
||||||
|
@unittest.skip("Flaky in CI")
|
||||||
def test_tax_rule(self):
|
def test_tax_rule(self):
|
||||||
self.create_tax_rule()
|
self.create_tax_rule()
|
||||||
self.login_as_customer()
|
|
||||||
|
self.login_as_customer(
|
||||||
|
"test_contact_two_customer@example.com", "_Test Contact 2 For _Test Customer"
|
||||||
|
)
|
||||||
|
create_address_and_contact(
|
||||||
|
address_title="_Test Address for Customer 2",
|
||||||
|
first_name="_Test Contact for Customer 2",
|
||||||
|
email="test_contact_two_customer@example.com",
|
||||||
|
customer="_Test Customer 2",
|
||||||
|
)
|
||||||
|
|
||||||
quotation = self.create_quotation()
|
quotation = self.create_quotation()
|
||||||
|
|
||||||
from erpnext.accounts.party import set_taxes
|
from erpnext.accounts.party import set_taxes
|
||||||
@@ -319,7 +337,7 @@ class TestShoppingCart(unittest.TestCase):
|
|||||||
if frappe.db.exists("User", email):
|
if frappe.db.exists("User", email):
|
||||||
return
|
return
|
||||||
|
|
||||||
frappe.get_doc(
|
user = frappe.get_doc(
|
||||||
{
|
{
|
||||||
"doctype": "User",
|
"doctype": "User",
|
||||||
"user_type": "Website User",
|
"user_type": "Website User",
|
||||||
@@ -329,6 +347,40 @@ class TestShoppingCart(unittest.TestCase):
|
|||||||
}
|
}
|
||||||
).insert(ignore_permissions=True)
|
).insert(ignore_permissions=True)
|
||||||
|
|
||||||
|
user.add_roles("Customer")
|
||||||
|
|
||||||
|
|
||||||
|
def create_address_and_contact(**kwargs):
|
||||||
|
if not frappe.db.get_value("Address", {"address_title": kwargs.get("address_title")}):
|
||||||
|
frappe.get_doc(
|
||||||
|
{
|
||||||
|
"doctype": "Address",
|
||||||
|
"address_title": kwargs.get("address_title"),
|
||||||
|
"address_type": kwargs.get("address_type") or "Office",
|
||||||
|
"address_line1": kwargs.get("address_line1") or "Station Road",
|
||||||
|
"city": kwargs.get("city") or "_Test City",
|
||||||
|
"state": kwargs.get("state") or "Test State",
|
||||||
|
"country": kwargs.get("country") or "India",
|
||||||
|
"links": [
|
||||||
|
{"link_doctype": "Customer", "link_name": kwargs.get("customer") or "_Test Customer"}
|
||||||
|
],
|
||||||
|
}
|
||||||
|
).insert()
|
||||||
|
|
||||||
|
if not frappe.db.get_value("Contact", {"first_name": kwargs.get("first_name")}):
|
||||||
|
contact = frappe.get_doc(
|
||||||
|
{
|
||||||
|
"doctype": "Contact",
|
||||||
|
"first_name": kwargs.get("first_name"),
|
||||||
|
"links": [
|
||||||
|
{"link_doctype": "Customer", "link_name": kwargs.get("customer") or "_Test Customer"}
|
||||||
|
],
|
||||||
|
}
|
||||||
|
)
|
||||||
|
contact.add_email(kwargs.get("email") or "test_contact_customer@example.com", is_primary=True)
|
||||||
|
contact.add_phone(kwargs.get("phone") or "+91 0000000000", is_primary_phone=True)
|
||||||
|
contact.insert()
|
||||||
|
|
||||||
|
|
||||||
test_dependencies = [
|
test_dependencies = [
|
||||||
"Sales Taxes and Charges Template",
|
"Sales Taxes and Charges Template",
|
||||||
|
|||||||
@@ -378,3 +378,4 @@ erpnext.patches.v13_0.update_schedule_type_in_loans
|
|||||||
erpnext.patches.v13_0.update_asset_value_for_manual_depr_entries
|
erpnext.patches.v13_0.update_asset_value_for_manual_depr_entries
|
||||||
erpnext.patches.v13_0.update_docs_link
|
erpnext.patches.v13_0.update_docs_link
|
||||||
erpnext.patches.v13_0.correct_asset_value_if_je_with_workflow
|
erpnext.patches.v13_0.correct_asset_value_if_je_with_workflow
|
||||||
|
execute:frappe.db.set_value("Accounts Settings", "Accounts Settings", "service_provider", "frankfurter.app")
|
||||||
|
|||||||
@@ -33,6 +33,7 @@ def after_install():
|
|||||||
add_standard_navbar_items()
|
add_standard_navbar_items()
|
||||||
add_app_name()
|
add_app_name()
|
||||||
add_non_standard_user_types()
|
add_non_standard_user_types()
|
||||||
|
update_roles()
|
||||||
frappe.db.commit()
|
frappe.db.commit()
|
||||||
|
|
||||||
|
|
||||||
@@ -237,6 +238,12 @@ def create_custom_role(data):
|
|||||||
).insert(ignore_permissions=True)
|
).insert(ignore_permissions=True)
|
||||||
|
|
||||||
|
|
||||||
|
def update_roles():
|
||||||
|
website_user_roles = ("Customer", "Supplier")
|
||||||
|
for role in website_user_roles:
|
||||||
|
frappe.db.set_value("Role", role, "desk_access", 0)
|
||||||
|
|
||||||
|
|
||||||
def create_user_type(user_type, data):
|
def create_user_type(user_type, data):
|
||||||
if frappe.db.exists("User Type", user_type):
|
if frappe.db.exists("User Type", user_type):
|
||||||
doc = frappe.get_cached_doc("User Type", user_type)
|
doc = frappe.get_cached_doc("User Type", user_type)
|
||||||
|
|||||||
@@ -659,7 +659,7 @@ class update_entries_after(object):
|
|||||||
)
|
)
|
||||||
|
|
||||||
if self.valuation_method == "Moving Average":
|
if self.valuation_method == "Moving Average":
|
||||||
rate = self.data[self.args.warehouse].previous_sle.valuation_rate
|
rate = flt(self.data[self.args.warehouse].previous_sle.valuation_rate)
|
||||||
else:
|
else:
|
||||||
rate = get_rate_for_return(
|
rate = get_rate_for_return(
|
||||||
sle.voucher_type,
|
sle.voucher_type,
|
||||||
|
|||||||
@@ -7,7 +7,7 @@
|
|||||||
{% if d.thumbnail or d.image %}
|
{% if d.thumbnail or d.image %}
|
||||||
{{ product_image(d.thumbnail or d.image, no_border=True) }}
|
{{ product_image(d.thumbnail or d.image, no_border=True) }}
|
||||||
{% else %}
|
{% else %}
|
||||||
<div class="no-image-cart-item" style="min-height: 100px;">
|
<div class="no-image-cart-item" style="min-height: 50px;">
|
||||||
{{ frappe.utils.get_abbr(d.item_name) or "NA" }}
|
{{ frappe.utils.get_abbr(d.item_name) or "NA" }}
|
||||||
</div>
|
</div>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
|
|||||||
@@ -81,7 +81,7 @@ rfq = Class.extend({
|
|||||||
doc: doc
|
doc: doc
|
||||||
},
|
},
|
||||||
btn: this,
|
btn: this,
|
||||||
callback: function(r){
|
callback: function(r) {
|
||||||
frappe.unfreeze();
|
frappe.unfreeze();
|
||||||
if(r.message){
|
if(r.message){
|
||||||
$('.btn-sm').hide()
|
$('.btn-sm').hide()
|
||||||
|
|||||||
@@ -1,19 +1,25 @@
|
|||||||
{% from "erpnext/templates/includes/macros.html" import product_image_square, product_image %}
|
{% from "erpnext/templates/includes/macros.html" import product_image_square, product_image %}
|
||||||
|
|
||||||
{% macro item_name_and_description(d, doc) %}
|
{% macro item_name_and_description(d, doc) %}
|
||||||
<div class="row">
|
<div class="row">
|
||||||
<div class="col-3">
|
<div class="col-3">
|
||||||
{{ product_image(d.image) }}
|
{% if d.image %}
|
||||||
</div>
|
{{ product_image(d.image) }}
|
||||||
<div class="col-9">
|
{% else %}
|
||||||
{{ d.item_code }}
|
<div class="website-image h-100 w-100" style="background-color:var(--gray-100);text-align: center;line-height: 3.6;">
|
||||||
<p class="text-muted small">{{ d.description }}</p>
|
{{ frappe.utils.get_abbr(d.item_name)}}
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
</div>
|
||||||
|
<div class="col-9">
|
||||||
|
{{ d.item_code }}
|
||||||
|
<p class="text-muted small">{{ d.description }}</p>
|
||||||
{% set supplier_part_no = frappe.db.get_value("Item Supplier", {'parent': d.item_code, 'supplier': doc.supplier}, "supplier_part_no") %}
|
{% set supplier_part_no = frappe.db.get_value("Item Supplier", {'parent': d.item_code, 'supplier': doc.supplier}, "supplier_part_no") %}
|
||||||
<p class="text-muted small supplier-part-no">
|
<p class="text-muted small supplier-part-no">
|
||||||
{% if supplier_part_no %}
|
{% if supplier_part_no %}
|
||||||
{{_("Supplier Part No") + ": "+ supplier_part_no}}
|
{{_("Supplier Part No") + ": "+ supplier_part_no}}
|
||||||
{% endif %}
|
{% endif %}
|
||||||
</p>
|
</p>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{% endmacro %}
|
{% endmacro %}
|
||||||
|
|||||||
@@ -153,7 +153,6 @@
|
|||||||
</div>
|
</div>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
|
|
||||||
|
|
||||||
{% if attachments %}
|
{% if attachments %}
|
||||||
<div class="order-item-table">
|
<div class="order-item-table">
|
||||||
<div class="row order-items order-item-header text-muted">
|
<div class="row order-items order-item-header text-muted">
|
||||||
@@ -181,6 +180,7 @@
|
|||||||
{% endif %}
|
{% endif %}
|
||||||
{% endblock %}
|
{% endblock %}
|
||||||
|
|
||||||
|
|
||||||
{% block script %}
|
{% block script %}
|
||||||
<script> {% include "templates/pages/order.js" %} </script>
|
<script> {% include "templates/pages/order.js" %} </script>
|
||||||
<script>
|
<script>
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
{% extends "templates/web.html" %}
|
{% extends "templates/web.html" %}
|
||||||
|
|
||||||
{% block header %}
|
{% block header %}
|
||||||
<h1>{{ doc.name }}</h1>
|
<h1 style="margin-top: 10px;">{{ doc.name }}</h1>
|
||||||
{% endblock %}
|
{% endblock %}
|
||||||
|
|
||||||
{% block script %}
|
{% block script %}
|
||||||
@@ -16,7 +16,7 @@
|
|||||||
{% if doc.items %}
|
{% if doc.items %}
|
||||||
<button class="btn btn-primary btn-sm"
|
<button class="btn btn-primary btn-sm"
|
||||||
type="button">
|
type="button">
|
||||||
{{ _("Submit") }}</button>
|
{{ _("Make Quotation") }}</button>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
{% endblock %}
|
{% endblock %}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user