def test_recommended_item_for_guest_user(self): "Check if added recommended items are fetched correctly for guest user." item_code = "Test Mobile Phone" web_item = create_regular_web_item(item_code) # price visible to guests setup_e_commerce_settings({ "enable_recommendations": 1, "show_price": 1, "hide_price_for_guest": 0 }) # create recommended web item and price for it recommended_web_item = create_regular_web_item("Test Mobile Phone 1") make_web_item_price(item_code="Test Mobile Phone 1") # add recommended item to first web item web_item.append("recommended_items", {"website_item": recommended_web_item.name}) web_item.save() frappe.set_user("Guest") frappe.local.shopping_cart_settings = None e_commerce_settings = get_shopping_cart_settings() recommended_items = web_item.get_recommended_items(e_commerce_settings) # test results if show price is enabled self.assertEqual(len(recommended_items), 1) self.assertTrue(bool( recommended_items[0].get("price_info"))) # price fetched # price hidden from guests frappe.set_user("Administrator") setup_e_commerce_settings({"hide_price_for_guest": 1}) frappe.set_user("Guest") frappe.local.shopping_cart_settings = None e_commerce_settings = get_shopping_cart_settings() recommended_items = web_item.get_recommended_items(e_commerce_settings) # test results if show price is enabled self.assertEqual(len(recommended_items), 1) self.assertFalse(bool( recommended_items[0].get("price_info"))) # price fetched # tear down frappe.set_user("Administrator") web_item.delete() recommended_web_item.delete() frappe.get_cached_doc("Item", "Test Mobile Phone 1").delete()
def test_recommended_item(self): "Check if added recommended items are fetched correctly." item_code = "Test Mobile Phone" web_item = create_regular_web_item(item_code) setup_e_commerce_settings({ "enable_recommendations": 1, "show_price": 1 }) # create recommended web item and price for it recommended_web_item = create_regular_web_item("Test Mobile Phone 1") make_web_item_price(item_code="Test Mobile Phone 1") # add recommended item to first web item web_item.append("recommended_items", {"website_item": recommended_web_item.name}) web_item.save() frappe.local.shopping_cart_settings = None e_commerce_settings = get_shopping_cart_settings() recommended_items = web_item.get_recommended_items(e_commerce_settings) # test results if show price is enabled self.assertEqual(len(recommended_items), 1) recomm_item = recommended_items[0] self.assertEqual(recomm_item.get("website_item_name"), "Test Mobile Phone 1") self.assertTrue(bool(recomm_item.get("price_info"))) # price fetched price_info = recomm_item.get("price_info") self.assertEqual(price_info.get("price_list_rate"), 1000) self.assertEqual(price_info.get("formatted_price"), "₹ 1,000.00") # test results if show price is disabled setup_e_commerce_settings({"show_price": 0}) frappe.local.shopping_cart_settings = None e_commerce_settings = get_shopping_cart_settings() recommended_items = web_item.get_recommended_items(e_commerce_settings) self.assertEqual(len(recommended_items), 1) self.assertFalse(bool( recommended_items[0].get("price_info"))) # price not fetched # tear down web_item.delete() recommended_web_item.delete() frappe.get_cached_doc("Item", "Test Mobile Phone 1").delete()
def request_for_quotation(): quotation = _get_cart_quotation() quotation.flags.ignore_permissions = True if get_shopping_cart_settings().save_quotations_as_draft: quotation.save() else: quotation.submit() return quotation.name
def _get_cart_quotation(party=None): """Return the open Quotation of type "Shopping Cart" or make a new one""" if not party: party = get_party() quotation = frappe.get_all( "Quotation", fields=["name"], filters={ "party_name": party.name, "contact_email": frappe.session.user, "order_type": "Shopping Cart", "docstatus": 0, }, order_by="modified desc", limit_page_length=1, ) if quotation: qdoc = frappe.get_doc("Quotation", quotation[0].name) else: company = frappe.db.get_value("E Commerce Settings", None, ["company"]) qdoc = frappe.get_doc({ "doctype": "Quotation", "naming_series": get_shopping_cart_settings().quotation_series or "QTN-CART-", "quotation_to": party.doctype, "company": company, "order_type": "Shopping Cart", "status": "Draft", "docstatus": 0, "__islocal": 1, "party_name": party.name, }) qdoc.contact_person = frappe.db.get_value( "Contact", {"email_id": frappe.session.user}) qdoc.contact_email = frappe.session.user qdoc.flags.ignore_permissions = True qdoc.run_method("set_missing_values") apply_cart_settings(party, qdoc) return qdoc
def get_context(context): is_guest = frappe.session.user == "Guest" settings = get_shopping_cart_settings() items = get_wishlist_items() if not is_guest else [] selling_price_list = _set_price_list(settings) if not is_guest else None items = set_stock_price_details(items, settings, selling_price_list) context.body_class = "product-page" context.items = items context.settings = settings context.no_cache = 1
def get_context(context): context.body_class = "product-page" context.no_cache = 1 context.full_page = True context.reviews = None if frappe.form_dict and frappe.form_dict.get("web_item"): context.web_item = frappe.form_dict.get("web_item") context.user_is_customer = check_if_user_is_customer() context.enable_reviews = get_shopping_cart_settings().enable_reviews if context.enable_reviews: reviews_data = get_item_reviews(context.web_item) context.update(reviews_data)
def get_item_reviews(web_item, start=0, end=10, data=None): "Get Website Item Review Data." start, end = cint(start), cint(end) settings = get_shopping_cart_settings() # Get cached reviews for first page (start=0) # avoid cache when page is different from_cache = not bool(start) if not data: data = frappe._dict() if settings and settings.get("enable_reviews"): reviews_cache = frappe.cache().hget("item_reviews", web_item) if from_cache and reviews_cache: data = reviews_cache else: data = get_queried_reviews(web_item, start, end, data) if from_cache: set_reviews_in_cache(web_item, data) return data
def get_party(user=None): if not user: user = frappe.session.user contact_name = get_contact_name(user) party = None if contact_name: contact = frappe.get_doc("Contact", contact_name) if contact.links: party_doctype = contact.links[0].link_doctype party = contact.links[0].link_name cart_settings = frappe.get_doc("E Commerce Settings") debtors_account = "" if cart_settings.enable_checkout: debtors_account = get_debtors_account(cart_settings) if party: return frappe.get_doc(party_doctype, party) else: if not cart_settings.enabled: frappe.local.flags.redirect_location = "/contact" raise frappe.Redirect customer = frappe.new_doc("Customer") fullname = get_fullname(user) customer.update({ "customer_name": fullname, "customer_type": "Individual", "customer_group": get_shopping_cart_settings().default_customer_group, "territory": get_root_of("Territory"), }) if debtors_account: customer.update({ "accounts": [{ "company": cart_settings.company, "account": debtors_account }] }) customer.flags.ignore_mandatory = True customer.insert(ignore_permissions=True) contact = frappe.new_doc("Contact") contact.update({ "first_name": fullname, "email_ids": [{ "email_id": user, "is_primary": 1 }] }) contact.append("links", dict(link_doctype="Customer", link_name=customer.name)) contact.flags.ignore_mandatory = True contact.insert(ignore_permissions=True) return customer
def create_customer_or_supplier(): '''Based on the default Role (Customer, Supplier), create a Customer / Supplier. Called on_session_creation hook. ''' user = frappe.session.user if frappe.db.get_value('User', user, 'user_type') != 'Website User': return user_roles = frappe.get_roles() portal_settings = frappe.get_single('Portal Settings') default_role = portal_settings.default_role if default_role not in ['Customer', 'Supplier']: return # create customer / supplier if the user has that role if portal_settings.default_role and portal_settings.default_role in user_roles: doctype = portal_settings.default_role else: doctype = None if not doctype: return if party_exists(doctype, user): return party = frappe.new_doc(doctype) fullname = frappe.utils.get_fullname(user) if doctype == 'Customer': cart_settings = get_shopping_cart_settings() if cart_settings.enable_checkout: debtors_account = get_debtors_account(cart_settings) else: debtors_account = '' party.update({ "customer_name": fullname, "customer_type": "Individual", "customer_group": cart_settings.default_customer_group, "territory": get_root_of("Territory") }) if debtors_account: party.update({ "accounts": [{ "company": cart_settings.company, "account": debtors_account }] }) else: party.update({ "supplier_name": fullname, "supplier_group": "All Supplier Groups", "supplier_type": "Individual" }) party.flags.ignore_mandatory = True party.insert(ignore_permissions=True) alternate_doctype = "Customer" if doctype == "Supplier" else "Supplier" if party_exists(alternate_doctype, user): # if user is both customer and supplier, alter fullname to avoid contact name duplication fullname += "-" + doctype create_party_contact(doctype, fullname, user, party.name) return party
def get_product_info_for_website(item_code, skip_quotation_creation=False): """get product price / stock info for website""" cart_settings = get_shopping_cart_settings() if not cart_settings.enabled: # return settings even if cart is disabled return frappe._dict({ "product_info": {}, "cart_settings": cart_settings }) cart_quotation = frappe._dict() if not skip_quotation_creation: cart_quotation = _get_cart_quotation() selling_price_list = (cart_quotation.get("selling_price_list") if cart_quotation else _set_price_list( cart_settings, None)) price = {} if cart_settings.show_price: is_guest = frappe.session.user == "Guest" # Show Price if logged in. # If not logged in, check if price is hidden for guest. if not is_guest or not cart_settings.hide_price_for_guest: price = get_price(item_code, selling_price_list, cart_settings.default_customer_group, cart_settings.company) stock_status = None if cart_settings.show_stock_availability: on_backorder = frappe.get_cached_value("Website Item", {"item_code": item_code}, "on_backorder") if on_backorder: stock_status = frappe._dict({"on_backorder": True}) else: stock_status = get_web_item_qty_in_stock(item_code, "website_warehouse") product_info = { "price": price, "qty": 0, "uom": frappe.db.get_value("Item", item_code, "stock_uom"), "sales_uom": frappe.db.get_value("Item", item_code, "sales_uom"), } if stock_status: if stock_status.on_backorder: product_info["on_backorder"] = True else: product_info["stock_qty"] = stock_status.stock_qty product_info["in_stock"] = ( stock_status.in_stock if stock_status.is_stock_item else get_non_stock_item_status(item_code, "website_warehouse")) product_info["show_stock_qty"] = show_quantity_in_website() if product_info["price"]: if frappe.session.user != "Guest": item = cart_quotation.get({"item_code": item_code }) if cart_quotation else None if item: product_info["qty"] = item[0].qty return frappe._dict({ "product_info": product_info, "cart_settings": cart_settings })
def get_next_attribute_and_values(item_code, selected_attributes): """Find the count of Items that match the selected attributes. Also, find the attribute values that are not applicable for further searching. If less than equal to 10 items are found, return item_codes of those items. If one item is matched exactly, return item_code of that item. """ selected_attributes = frappe.parse_json(selected_attributes) item_cache = ItemVariantsCacheManager(item_code) item_variants_data = item_cache.get_item_variants_data() attributes = get_item_attributes(item_code) attribute_list = [a.attribute for a in attributes] filtered_items = get_items_with_selected_attributes( item_code, selected_attributes) next_attribute = None for attribute in attribute_list: if attribute not in selected_attributes: next_attribute = attribute break valid_options_for_attributes = frappe._dict() for a in attribute_list: valid_options_for_attributes[a] = set() selected_attribute = selected_attributes.get(a, None) if selected_attribute: # already selected attribute values are valid options valid_options_for_attributes[a].add(selected_attribute) for row in item_variants_data: item_code, attribute, attribute_value = row if (item_code in filtered_items and attribute not in selected_attributes and attribute in attribute_list): valid_options_for_attributes[attribute].add(attribute_value) optional_attributes = item_cache.get_optional_attributes() exact_match = [] # search for exact match if all selected attributes are required attributes if len(selected_attributes.keys()) >= (len(attribute_list) - len(optional_attributes)): item_attribute_value_map = item_cache.get_item_attribute_value_map() for item_code, attr_dict in item_attribute_value_map.items(): if item_code in filtered_items and set(attr_dict.keys()) == set( selected_attributes.keys()): exact_match.append(item_code) filtered_items_count = len(filtered_items) # get product info if exact match # from erpnext.e_commerce.shopping_cart.product_info import get_product_info_for_website if exact_match: cart_settings = get_shopping_cart_settings() product_info = get_item_variant_price_dict(exact_match[0], cart_settings) if product_info: product_info["allow_items_not_in_stock"] = cint( cart_settings.allow_items_not_in_stock) else: product_info = None return { "next_attribute": next_attribute, "valid_options_for_attributes": valid_options_for_attributes, "filtered_items_count": filtered_items_count, "filtered_items": filtered_items if filtered_items_count < 10 else [], "exact_match": exact_match, "product_info": product_info, }