feat: api to get additional filters

This commit is contained in:
prssanna 2020-05-22 15:10:51 +05:30
parent 53e2e60cab
commit 4c16b2a608
6 changed files with 83 additions and 11 deletions

View file

@ -85,6 +85,7 @@ def get_bootinfo():
bootinfo.points = get_energy_points(frappe.session.user)
bootinfo.frequently_visited_links = frequently_visited_links()
bootinfo.link_preview_doctypes = get_link_preview_doctypes()
bootinfo.filters_config = get_filters_config()
return bootinfo
@ -297,3 +298,10 @@ def get_link_preview_doctypes():
link_preview_doctypes.append(custom.doc_type)
return link_preview_doctypes
def get_filters_config():
filter_config = frappe._dict()
filter_hooks = frappe.get_hooks('filters_config')
for hook in filter_hooks:
filter_config.update(frappe.get_attr(hook)())
return filter_config

View file

@ -355,7 +355,9 @@ class DatabaseQuery(object):
ifnull(`tabDocType`.`fieldname`, fallback) operator "value"
"""
f = get_filter(self.doctype, f)
from frappe.boot import get_filters_config
additional_filters_config = get_filters_config()
f = get_filter(self.doctype, f, additional_filters_config)
tname = ('`tab' + f.doctype + '`')
if not tname in self.tables:
@ -369,7 +371,9 @@ class DatabaseQuery(object):
can_be_null = True
# prepare in condition
if f.operator.lower() in additional_filters_config:
f.update(get_additional_filter_field(additional_filters_config, f, f.value))
if f.operator.lower() in ('ancestors of', 'descendants of', 'not ancestors of', 'not descendants of'):
values = f.value or ''
@ -853,4 +857,14 @@ def get_between_date_filter(value, df=None):
frappe.db.format_date(from_date),
frappe.db.format_date(to_date))
return data
return data
def get_additional_filter_field(additional_filters_config, f, value):
additional_filter = additional_filters_config[f.operator.lower()]
f = frappe._dict(frappe.get_attr(additional_filter['get_field'])())
if f.query_value:
for option in f.options:
option = frappe._dict(option)
if option.value == value:
f.value = option.query_value
return f

View file

@ -338,6 +338,11 @@ frappe.views.BaseList = class BaseList {
: [];
}
get_filter_value(fieldname) {
return this.get_filters_for_args().filter(f=> f[1] == fieldname)[0] &&
this.get_filters_for_args().filter(f=> f[1] == fieldname)[0][3];
}
get_args() {
return {
doctype: this.doctype,

View file

@ -6,6 +6,12 @@ frappe.ui.Filter = class {
}
this.utils = frappe.ui.filter_utils;
this.set_conditions();
this.set_conditions_from_config();
this.make();
}
set_conditions() {
this.conditions = [
["=", __("Equals")],
["!=", __("Not Equals")],
@ -43,10 +49,21 @@ frappe.ui.Filter = class {
Color: ["Between", 'Previous', 'Current', 'Next'],
Check: this.conditions.map(c => c[0]).filter(c => c !== '=')
};
this.make();
this.make_select();
this.set_events();
this.setup();
}
set_conditions_from_config() {
if (frappe.boot.filters_config) {
this.filters_config = frappe.boot.filters_config;
for (let key of Object.keys(this.filters_config)) {
const filter = this.filters_config[key];
this.conditions.push([key, __(`{0}`, [filter.label])]);
for (let fieldtype of Object.keys(this.invalid_condition_map)) {
if (!filter.fieldtypes.includes(fieldtype)) {
this.invalid_condition_map[fieldtype].push(filter.label);
}
}
}
}
}
make() {
@ -54,6 +71,10 @@ frappe.ui.Filter = class {
conditions: this.conditions
}))
.appendTo(this.parent.find('.filter-edit-area'));
this.make_select();
this.set_events();
this.setup();
}
make_select() {
@ -121,6 +142,7 @@ frappe.ui.Filter = class {
}
freeze() {
console.log('freeze here')
this.update_filter_tag();
}
@ -230,7 +252,22 @@ frappe.ui.Filter = class {
];
}
this.make_field(df, cur.fieldtype);
if (this.filters_config[condition] && this.filters_config[condition].fieldtypes.includes(this.field.df.fieldtype)) {
let args = {};
if (this.filters_config[condition].depends_on) {
const field_name = this.filters_config[condition].depends_on;
const filter_value = this.base_list.get_filter_value(field_name);
args[field_name] = filter_value;
}
frappe.xcall(this.filters_config[condition].get_field, args).then(field => {
df.fieldtype = field.fieldtype;
df.options = field.options;
df.fieldname = fieldname;
this.make_field(df, cur.fieldtype);
});
} else {
this.make_field(df, cur.fieldtype);
}
}
make_field(df, old_fieldtype) {

View file

@ -103,7 +103,8 @@ frappe.ui.FilterGroup = class {
},
filter_items: (doctype, fieldname) => {
return !this.filter_exists([doctype, fieldname]);
}
},
base_list: this.base_list
};
let filter = new frappe.ui.Filter(args);
this.filters.push(filter);
@ -132,7 +133,7 @@ frappe.ui.FilterGroup = class {
get_filters() {
return this.filters.filter(f => f.field).map(f => {
f.freeze();
// f.freeze();
return f.get_value();
});
// {}: this.list.update_standard_filters(values);

View file

@ -1011,7 +1011,7 @@ def compare(val1, condition, val2):
return ret
def get_filter(doctype, f):
def get_filter(doctype, f, filters_config=None):
"""Returns a _dict like
{
@ -1047,6 +1047,13 @@ def get_filter(doctype, f):
valid_operators = ("=", "!=", ">", "<", ">=", "<=", "like", "not like", "in", "not in", "is",
"between", "descendants of", "ancestors of", "not descendants of", "not ancestors of", "previous", "current", "next")
if filters_config:
additional_operators = []
for key in filters_config:
additional_operators.append(key.lower())
valid_operators = tuple(set(valid_operators + tuple(additional_operators)))
if f.operator.lower() not in valid_operators:
frappe.throw(frappe._("Operator must be one of {0}").format(", ".join(valid_operators)))