[Report]Added permission to reports for showing data according to the user properties

This commit is contained in:
Akhilesh Darjee 2013-07-09 11:55:25 +05:30
parent ae34001988
commit dca4e59e77
2 changed files with 89 additions and 11 deletions

View file

@ -24,10 +24,12 @@ from __future__ import unicode_literals
import webnotes
import os, json
import types
from webnotes import _
from webnotes.modules import scrub, get_module_path
from webnotes.utils import flt, cint
import webnotes.widgets.reportview
@webnotes.whitelist()
def get_script(report_name):
@ -67,6 +69,8 @@ def run(report_name, filters=None):
method_name = scrub(webnotes.conn.get_value("DocType", report.ref_doctype, "module")) \
+ ".report." + scrub(report.name) + "." + scrub(report.name) + ".execute"
columns, result = webnotes.get_method(method_name)(filters or {})
result = get_filtered_data(report.ref_doctype, columns, result)
if cint(report.add_total_row) and result:
result = add_total_row(result, columns)
@ -88,4 +92,64 @@ def add_total_row(result, columns):
total_row[0] = "Total"
result.append(total_row)
return result
return result
def get_filtered_data(ref_doctype, columns, data):
result = []
linked_doctypes = get_linked_doctypes(columns)
match_filters = get_user_match_filters(linked_doctypes, ref_doctype)
if match_filters:
matched_columns = get_matched_columns(linked_doctypes, match_filters)
for row in data:
match = True
for col, idx in matched_columns.items():
if row[idx] not in match_filters[col]:
match = False
if match:
result.append(row)
else:
for row in data:
result.append(row)
return result
def get_linked_doctypes(columns):
linked_doctypes = {}
for idx, col in enumerate(columns):
if "Link" in col:
link_dt = col.split(":")[1].split("/")[1]
linked_doctypes[link_dt] = idx
return linked_doctypes
def get_user_match_filters(doctypes, ref_doctype):
match_filters = {}
doctypes_meta = {}
tables = []
doctypes[ref_doctype] = None
for dt in doctypes:
tables.append("`tab" + dt + "`")
doctypes_meta[dt] = webnotes.model.doctype.get(dt)
webnotes.widgets.reportview.tables = tables
webnotes.widgets.reportview.doctypes = doctypes_meta
for dt in doctypes:
match_filters = webnotes.widgets.reportview.build_match_conditions(dt,
None, False, match_filters)
return match_filters
def get_matched_columns(linked_doctypes, match_filters):
col_idx_map = {}
for dt, idx in linked_doctypes.items():
link_field = dt.lower().replace(" ", "_")
if link_field in match_filters:
col_idx_map[link_field] = idx
return col_idx_map

View file

@ -123,7 +123,7 @@ def load_doctypes():
import webnotes.model.doctype
roles = webnotes.get_roles()
for t in tables:
if t.startswith('`'):
doctype = t[4:-1]
@ -190,8 +190,9 @@ def build_filter_conditions(filters, conditions):
conditions.append('ifnull(' + tname + '.' + f[1] + ",0) " + f[2] \
+ " " + cstr(f[3]))
def build_match_conditions(doctype, fields=None):
def build_match_conditions(doctype, fields=None, as_condition=True, match_filters={}):
"""add match conditions if applicable"""
global roles
match_conditions = []
match = True
@ -199,7 +200,10 @@ def build_match_conditions(doctype, fields=None):
global tables
tables = get_tables(doctype, fields)
load_doctypes()
if not roles:
roles = webnotes.get_roles()
for d in doctypes[doctype]:
if d.doctype == 'DocPerm' and d.parent == doctype:
if d.role in roles:
@ -208,20 +212,30 @@ def build_match_conditions(doctype, fields=None):
document_key, default_key = d.match.split(":")
else:
default_key = document_key = d.match
for v in webnotes.defaults.get_user_default_as_list(default_key) or ["** No Match **"]:
match_conditions.append('`tab%s`.%s="%s"' % (doctype,
document_key, v))
for v in webnotes.defaults.get_user_default_as_list(default_key, \
webnotes.session.user) or ["** No Match **"]:
if as_condition:
match_conditions.append('`tab%s`.%s="%s"' % (doctype,
document_key, v))
else:
if v:
match_filters.setdefault(document_key, [])
if v not in match_filters[document_key]:
match_filters[document_key].append(v)
elif d.read == 1 and d.permlevel == 0:
# don't restrict if another read permission at level 0
# exists without a match restriction
match = False
if match_conditions and match:
return '('+ ' or '.join(match_conditions) +')'
if as_condition:
if match_conditions and match:
return '('+ ' or '.join(match_conditions) +')'
else:
return ""
else:
return ""
return match_filters
def get_tables(doctype, fields):
"""extract tables from fields"""