Merge pull request #19973 from deepeshgarg007/budget_variance_dimension

feat: Dynamic filters for dimensions in budget variance report
This commit is contained in:
Saqib 2019-12-24 12:57:50 +05:30 committed by GitHub
commit 977489697d
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 36 additions and 28 deletions

View File

@ -46,13 +46,24 @@ frappe.query_reports["Budget Variance Report"] = {
fieldtype: "Select", fieldtype: "Select",
options: ["Cost Center", "Project"], options: ["Cost Center", "Project"],
default: "Cost Center", default: "Cost Center",
reqd: 1 reqd: 1,
on_change: function() {
frappe.query_report.set_filter_value("budget_against_filter", []);
frappe.query_report.refresh();
}
}, },
{ {
fieldname: "cost_center", fieldname:"budget_against_filter",
label: __("Cost Center"), label: __('Dimension Filter'),
fieldtype: "Link", fieldtype: "MultiSelectList",
options: "Cost Center" get_data: function(txt) {
if (!frappe.query_report.filters) return;
let budget_against = frappe.query_report.get_filter_value('budget_against');
if (!budget_against) return;
return frappe.db.get_link_options(budget_against, txt);
}
}, },
{ {
fieldname:"show_cumulative", fieldname:"show_cumulative",

View File

@ -12,22 +12,22 @@ from six import iteritems
from pprint import pprint from pprint import pprint
def execute(filters=None): def execute(filters=None):
if not filters: filters = {} if not filters: filters = {}
validate_filters(filters)
columns = get_columns(filters) columns = get_columns(filters)
if filters.get("cost_center"): if filters.get("budget_against_filter"):
cost_centers = [filters.get("cost_center")] dimensions = filters.get("budget_against_filter")
else: else:
cost_centers = get_cost_centers(filters) dimensions = get_cost_centers(filters)
period_month_ranges = get_period_month_ranges(filters["period"], filters["from_fiscal_year"]) period_month_ranges = get_period_month_ranges(filters["period"], filters["from_fiscal_year"])
cam_map = get_cost_center_account_month_map(filters) cam_map = get_dimension_account_month_map(filters)
data = [] data = []
for cost_center in cost_centers: for dimension in dimensions:
cost_center_items = cam_map.get(cost_center) dimension_items = cam_map.get(dimension)
if cost_center_items: if dimension_items:
for account, monthwise_data in iteritems(cost_center_items): for account, monthwise_data in iteritems(dimension_items):
row = [cost_center, account] row = [dimension, account]
totals = [0, 0, 0] totals = [0, 0, 0]
for year in get_fiscal_years(filters): for year in get_fiscal_years(filters):
last_total = 0 last_total = 0
@ -55,10 +55,6 @@ def execute(filters=None):
return columns, data return columns, data
def validate_filters(filters):
if filters.get("budget_against") != "Cost Center" and filters.get("cost_center"):
frappe.throw(_("Filter based on Cost Center is only applicable if Budget Against is selected as Cost Center"))
def get_columns(filters): def get_columns(filters):
columns = [_(filters.get("budget_against")) + ":Link/%s:150"%(filters.get("budget_against")), _("Account") + ":Link/Account:150"] columns = [_(filters.get("budget_against")) + ":Link/%s:150"%(filters.get("budget_against")), _("Account") + ":Link/Account:150"]
@ -98,11 +94,12 @@ def get_cost_centers(filters):
else: else:
return frappe.db.sql_list("""select name from `tab{tab}`""".format(tab=filters.get("budget_against"))) #nosec return frappe.db.sql_list("""select name from `tab{tab}`""".format(tab=filters.get("budget_against"))) #nosec
#Get cost center & target details #Get dimension & target details
def get_cost_center_target_details(filters): def get_dimension_target_details(filters):
cond = "" cond = ""
if filters.get("cost_center"): if filters.get("budget_against_filter"):
cond += " and b.cost_center=%s" % frappe.db.escape(filters.get("cost_center")) cond += " and b.{budget_against} in (%s)".format(budget_against = \
frappe.scrub(filters.get('budget_against'))) % ', '.join(['%s']* len(filters.get('budget_against_filter')))
return frappe.db.sql(""" return frappe.db.sql("""
select b.{budget_against} as budget_against, b.monthly_distribution, ba.account, ba.budget_amount,b.fiscal_year select b.{budget_against} as budget_against, b.monthly_distribution, ba.account, ba.budget_amount,b.fiscal_year
@ -110,8 +107,8 @@ def get_cost_center_target_details(filters):
where b.name=ba.parent and b.docstatus = 1 and b.fiscal_year between %s and %s where b.name=ba.parent and b.docstatus = 1 and b.fiscal_year between %s and %s
and b.budget_against = %s and b.company=%s {cond} order by b.fiscal_year and b.budget_against = %s and b.company=%s {cond} order by b.fiscal_year
""".format(budget_against=filters.get("budget_against").replace(" ", "_").lower(), cond=cond), """.format(budget_against=filters.get("budget_against").replace(" ", "_").lower(), cond=cond),
(filters.from_fiscal_year,filters.to_fiscal_year,filters.budget_against, filters.company), as_dict=True) tuple([filters.from_fiscal_year,filters.to_fiscal_year,filters.budget_against, filters.company] + filters.get('budget_against_filter')),
as_dict=True)
#Get target distribution details of accounts of cost center #Get target distribution details of accounts of cost center
@ -153,14 +150,14 @@ def get_actual_details(name, filters):
return cc_actual_details return cc_actual_details
def get_cost_center_account_month_map(filters): def get_dimension_account_month_map(filters):
import datetime import datetime
cost_center_target_details = get_cost_center_target_details(filters) dimension_target_details = get_dimension_target_details(filters)
tdd = get_target_distribution_details(filters) tdd = get_target_distribution_details(filters)
cam_map = {} cam_map = {}
for ccd in cost_center_target_details: for ccd in dimension_target_details:
actual_details = get_actual_details(ccd.budget_against, filters) actual_details = get_actual_details(ccd.budget_against, filters)
for month_id in range(1, 13): for month_id in range(1, 13):