fix: removed currency exchange rate settings and moved it to crm settings
(cherry picked from commit 5bee7022b22395b1da2e0de90746cff12e298748)
This commit is contained in:
parent
53781cbf1e
commit
c4df4d3253
@ -1,8 +0,0 @@
|
|||||||
// Copyright (c) 2025, Frappe Technologies Pvt. Ltd. and contributors
|
|
||||||
// For license information, please see license.txt
|
|
||||||
|
|
||||||
// frappe.ui.form.on("CRM Currency Exchange Settings", {
|
|
||||||
// refresh(frm) {
|
|
||||||
|
|
||||||
// },
|
|
||||||
// });
|
|
||||||
@ -1,54 +0,0 @@
|
|||||||
{
|
|
||||||
"actions": [],
|
|
||||||
"allow_rename": 1,
|
|
||||||
"creation": "2025-07-28 12:29:02.935286",
|
|
||||||
"doctype": "DocType",
|
|
||||||
"engine": "InnoDB",
|
|
||||||
"field_order": [
|
|
||||||
"service_provider",
|
|
||||||
"access_key"
|
|
||||||
],
|
|
||||||
"fields": [
|
|
||||||
{
|
|
||||||
"default": "frankfurter.app",
|
|
||||||
"fieldname": "service_provider",
|
|
||||||
"fieldtype": "Select",
|
|
||||||
"in_list_view": 1,
|
|
||||||
"label": "Service Provider",
|
|
||||||
"options": "frankfurter.app\nexchangerate.host",
|
|
||||||
"reqd": 1
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"depends_on": "eval:doc.service_provider == 'exchangerate.host';",
|
|
||||||
"fieldname": "access_key",
|
|
||||||
"fieldtype": "Data",
|
|
||||||
"label": "Access Key",
|
|
||||||
"mandatory_depends_on": "eval:doc.service_provider == 'exchangerate.host';"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"grid_page_length": 50,
|
|
||||||
"index_web_pages_for_search": 1,
|
|
||||||
"issingle": 1,
|
|
||||||
"links": [],
|
|
||||||
"modified": "2025-07-28 12:30:08.080590",
|
|
||||||
"modified_by": "Administrator",
|
|
||||||
"module": "FCRM",
|
|
||||||
"name": "CRM Currency Exchange Settings",
|
|
||||||
"owner": "Administrator",
|
|
||||||
"permissions": [
|
|
||||||
{
|
|
||||||
"create": 1,
|
|
||||||
"delete": 1,
|
|
||||||
"email": 1,
|
|
||||||
"print": 1,
|
|
||||||
"read": 1,
|
|
||||||
"role": "System Manager",
|
|
||||||
"share": 1,
|
|
||||||
"write": 1
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"row_format": "Dynamic",
|
|
||||||
"sort_field": "creation",
|
|
||||||
"sort_order": "DESC",
|
|
||||||
"states": []
|
|
||||||
}
|
|
||||||
@ -1,84 +0,0 @@
|
|||||||
# Copyright (c) 2025, Frappe Technologies Pvt. Ltd. and contributors
|
|
||||||
# For license information, please see license.txt
|
|
||||||
|
|
||||||
import frappe
|
|
||||||
import requests
|
|
||||||
from frappe import _
|
|
||||||
from frappe.model.document import Document
|
|
||||||
|
|
||||||
|
|
||||||
class CRMCurrencyExchangeSettings(Document):
|
|
||||||
pass
|
|
||||||
|
|
||||||
|
|
||||||
def get_exchange_rate(from_currency, to_currency, date=None):
|
|
||||||
if not date:
|
|
||||||
date = "latest"
|
|
||||||
|
|
||||||
api_used = "frankfurter"
|
|
||||||
|
|
||||||
api_endpoint = f"https://api.frankfurter.app/{date}?from={from_currency}&to={to_currency}"
|
|
||||||
res = requests.get(api_endpoint, timeout=5)
|
|
||||||
if res.ok:
|
|
||||||
data = res.json()
|
|
||||||
return data["rates"][to_currency]
|
|
||||||
|
|
||||||
# Fallback to exchangerate.host if Frankfurter API fails
|
|
||||||
ces = frappe.get_single("CRM Currency Exchange Settings")
|
|
||||||
if ces and ces.service_provider == "exchangerate.host":
|
|
||||||
api_used = "exchangerate.host"
|
|
||||||
if not ces.access_key:
|
|
||||||
frappe.throw(
|
|
||||||
_("Access Key is required for Service Provider: {0}").format(
|
|
||||||
frappe.bold(ces.service_provider)
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
params = {
|
|
||||||
"access_key": ces.access_key,
|
|
||||||
"from": from_currency,
|
|
||||||
"to": to_currency,
|
|
||||||
"amount": 1,
|
|
||||||
}
|
|
||||||
|
|
||||||
if date != "latest":
|
|
||||||
params["date"] = date
|
|
||||||
|
|
||||||
api_endpoint = "https://api.exchangerate.host/convert"
|
|
||||||
|
|
||||||
res = requests.get(api_endpoint, params=params, timeout=5)
|
|
||||||
if res.ok:
|
|
||||||
data = res.json()
|
|
||||||
return data["result"]
|
|
||||||
|
|
||||||
frappe.log_error(
|
|
||||||
title="Exchange Rate Fetch Error",
|
|
||||||
message=f"Failed to fetch exchange rate from {from_currency} to {to_currency} using {api_used} API.",
|
|
||||||
)
|
|
||||||
|
|
||||||
if api_used == "frankfurter":
|
|
||||||
user = frappe.session.user
|
|
||||||
is_manager = (
|
|
||||||
"System Manager" in frappe.get_roles(user)
|
|
||||||
or "Sales Manager" in frappe.get_roles(user)
|
|
||||||
or user == "Administrator"
|
|
||||||
)
|
|
||||||
|
|
||||||
if not is_manager:
|
|
||||||
frappe.throw(
|
|
||||||
_(
|
|
||||||
"Ask your manager to set up the Currency Exchange Provider, as default provider does not support currency conversion for {0} to {1}."
|
|
||||||
).format(from_currency, to_currency)
|
|
||||||
)
|
|
||||||
else:
|
|
||||||
frappe.throw(
|
|
||||||
_(
|
|
||||||
"Setup the Currency Exchange Provider as 'exchangerate.host' in settings, as default provider does not support currency conversion for {0} to {1}."
|
|
||||||
).format(from_currency, to_currency)
|
|
||||||
)
|
|
||||||
|
|
||||||
frappe.throw(
|
|
||||||
_(
|
|
||||||
"Failed to fetch exchange rate from {0} to {1} on {2}. Please check your internet connection or try again later."
|
|
||||||
).format(from_currency, to_currency, date)
|
|
||||||
)
|
|
||||||
@ -1,22 +0,0 @@
|
|||||||
# Copyright (c) 2025, Frappe Technologies Pvt. Ltd. and Contributors
|
|
||||||
# See license.txt
|
|
||||||
|
|
||||||
# import frappe
|
|
||||||
from frappe.tests import IntegrationTestCase
|
|
||||||
|
|
||||||
|
|
||||||
# On IntegrationTestCase, the doctype test records and all
|
|
||||||
# link-field test record dependencies are recursively loaded
|
|
||||||
# Use these module variables to add/remove to/from that list
|
|
||||||
EXTRA_TEST_RECORD_DEPENDENCIES = [] # eg. ["User"]
|
|
||||||
IGNORE_TEST_RECORD_DEPENDENCIES = [] # eg. ["User"]
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
class IntegrationTestCRMCurrencyExchangeSettings(IntegrationTestCase):
|
|
||||||
"""
|
|
||||||
Integration tests for CRMCurrencyExchangeSettings.
|
|
||||||
Use this class for testing interactions between multiple components.
|
|
||||||
"""
|
|
||||||
|
|
||||||
pass
|
|
||||||
@ -6,11 +6,9 @@ from frappe import _
|
|||||||
from frappe.desk.form.assign_to import add as assign
|
from frappe.desk.form.assign_to import add as assign
|
||||||
from frappe.model.document import Document
|
from frappe.model.document import Document
|
||||||
|
|
||||||
from crm.fcrm.doctype.crm_currency_exchange_settings.crm_currency_exchange_settings import get_exchange_rate
|
|
||||||
from crm.fcrm.doctype.crm_service_level_agreement.utils import get_sla
|
from crm.fcrm.doctype.crm_service_level_agreement.utils import get_sla
|
||||||
from crm.fcrm.doctype.crm_status_change_log.crm_status_change_log import (
|
from crm.fcrm.doctype.crm_status_change_log.crm_status_change_log import add_status_change_log
|
||||||
add_status_change_log,
|
from crm.fcrm.doctype.fcrm_settings.fcrm_settings import get_exchange_rate
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
class CRMDeal(Document):
|
class CRMDeal(Document):
|
||||||
|
|||||||
@ -4,7 +4,7 @@
|
|||||||
import frappe
|
import frappe
|
||||||
from frappe.model.document import Document
|
from frappe.model.document import Document
|
||||||
|
|
||||||
from crm.fcrm.doctype.crm_currency_exchange_settings.crm_currency_exchange_settings import get_exchange_rate
|
from crm.fcrm.doctype.fcrm_settings.fcrm_settings import get_exchange_rate
|
||||||
|
|
||||||
|
|
||||||
class CRMOrganization(Document):
|
class CRMOrganization(Document):
|
||||||
|
|||||||
@ -8,7 +8,12 @@
|
|||||||
"defaults_tab",
|
"defaults_tab",
|
||||||
"restore_defaults",
|
"restore_defaults",
|
||||||
"enable_forecasting",
|
"enable_forecasting",
|
||||||
|
"currency_tab",
|
||||||
"currency",
|
"currency",
|
||||||
|
"exchange_rate_provider_section",
|
||||||
|
"service_provider",
|
||||||
|
"column_break_vqck",
|
||||||
|
"access_key",
|
||||||
"branding_tab",
|
"branding_tab",
|
||||||
"brand_name",
|
"brand_name",
|
||||||
"brand_logo",
|
"brand_logo",
|
||||||
@ -72,13 +77,42 @@
|
|||||||
"in_list_view": 1,
|
"in_list_view": 1,
|
||||||
"label": "Currency",
|
"label": "Currency",
|
||||||
"options": "Currency"
|
"options": "Currency"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "currency_tab",
|
||||||
|
"fieldtype": "Tab Break",
|
||||||
|
"label": "Currency"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "exchange_rate_provider_section",
|
||||||
|
"fieldtype": "Section Break",
|
||||||
|
"label": "Exchange Rate Provider"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"default": "frankfurter.app",
|
||||||
|
"fieldname": "service_provider",
|
||||||
|
"fieldtype": "Select",
|
||||||
|
"label": "Service Provider",
|
||||||
|
"options": "frankfurter.app\nexchangerate.host",
|
||||||
|
"reqd": 1
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"depends_on": "eval:doc.service_provider == 'exchangerate.host';",
|
||||||
|
"fieldname": "access_key",
|
||||||
|
"fieldtype": "Data",
|
||||||
|
"label": "Access Key",
|
||||||
|
"mandatory_depends_on": "eval:doc.service_provider == 'exchangerate.host';"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "column_break_vqck",
|
||||||
|
"fieldtype": "Column Break"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"index_web_pages_for_search": 1,
|
"index_web_pages_for_search": 1,
|
||||||
"issingle": 1,
|
"issingle": 1,
|
||||||
"links": [],
|
"links": [],
|
||||||
"modified": "2025-07-13 11:58:34.857638",
|
"modified": "2025-07-28 17:04:24.585768",
|
||||||
"modified_by": "Administrator",
|
"modified_by": "shariq@frappe.io",
|
||||||
"module": "FCRM",
|
"module": "FCRM",
|
||||||
"name": "FCRM Settings",
|
"name": "FCRM Settings",
|
||||||
"owner": "Administrator",
|
"owner": "Administrator",
|
||||||
|
|||||||
@ -2,6 +2,7 @@
|
|||||||
# For license information, please see license.txt
|
# For license information, please see license.txt
|
||||||
|
|
||||||
import frappe
|
import frappe
|
||||||
|
import requests
|
||||||
from frappe import _
|
from frappe import _
|
||||||
from frappe.custom.doctype.property_setter.property_setter import delete_property_setter, make_property_setter
|
from frappe.custom.doctype.property_setter.property_setter import delete_property_setter, make_property_setter
|
||||||
from frappe.model.document import Document
|
from frappe.model.document import Document
|
||||||
@ -132,3 +133,76 @@ def get_forecasting_script():
|
|||||||
this.doc.probability = status.probability
|
this.doc.probability = status.probability
|
||||||
}
|
}
|
||||||
}"""
|
}"""
|
||||||
|
|
||||||
|
|
||||||
|
def get_exchange_rate(from_currency, to_currency, date=None):
|
||||||
|
if not date:
|
||||||
|
date = "latest"
|
||||||
|
|
||||||
|
api_used = "frankfurter"
|
||||||
|
|
||||||
|
api_endpoint = f"https://api.frankfurter.app/{date}?from={from_currency}&to={to_currency}"
|
||||||
|
res = requests.get(api_endpoint, timeout=5)
|
||||||
|
if res.ok:
|
||||||
|
data = res.json()
|
||||||
|
return data["rates"][to_currency]
|
||||||
|
|
||||||
|
# Fallback to exchangerate.host if Frankfurter API fails
|
||||||
|
settings = FCRMSettings("FCRM Settings")
|
||||||
|
if settings and settings.service_provider == "exchangerate.host":
|
||||||
|
api_used = "exchangerate.host"
|
||||||
|
if not settings.access_key:
|
||||||
|
frappe.throw(
|
||||||
|
_("Access Key is required for Service Provider: {0}").format(
|
||||||
|
frappe.bold(settings.service_provider)
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
params = {
|
||||||
|
"access_key": settings.access_key,
|
||||||
|
"from": from_currency,
|
||||||
|
"to": to_currency,
|
||||||
|
"amount": 1,
|
||||||
|
}
|
||||||
|
|
||||||
|
if date != "latest":
|
||||||
|
params["date"] = date
|
||||||
|
|
||||||
|
api_endpoint = "https://api.exchangerate.host/convert"
|
||||||
|
|
||||||
|
res = requests.get(api_endpoint, params=params, timeout=5)
|
||||||
|
if res.ok:
|
||||||
|
data = res.json()
|
||||||
|
return data["result"]
|
||||||
|
|
||||||
|
frappe.log_error(
|
||||||
|
title="Exchange Rate Fetch Error",
|
||||||
|
message=f"Failed to fetch exchange rate from {from_currency} to {to_currency} using {api_used} API.",
|
||||||
|
)
|
||||||
|
|
||||||
|
if api_used == "frankfurter":
|
||||||
|
user = frappe.session.user
|
||||||
|
is_manager = (
|
||||||
|
"System Manager" in frappe.get_roles(user)
|
||||||
|
or "Sales Manager" in frappe.get_roles(user)
|
||||||
|
or user == "Administrator"
|
||||||
|
)
|
||||||
|
|
||||||
|
if not is_manager:
|
||||||
|
frappe.throw(
|
||||||
|
_(
|
||||||
|
"Ask your manager to set up the Exchange Rate Provider, as default provider does not support currency conversion for {0} to {1}."
|
||||||
|
).format(from_currency, to_currency)
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
frappe.throw(
|
||||||
|
_(
|
||||||
|
"Setup the Exchange Rate Provider as 'Exchangerate Host' in settings, as default provider does not support currency conversion for {0} to {1}."
|
||||||
|
).format(from_currency, to_currency)
|
||||||
|
)
|
||||||
|
|
||||||
|
frappe.throw(
|
||||||
|
_(
|
||||||
|
"Failed to fetch exchange rate from {0} to {1} on {2}. Please check your internet connection or try again later."
|
||||||
|
).format(from_currency, to_currency, date)
|
||||||
|
)
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user