details: https://code.openbravo.com/erp/devel/pi/rev/290c9b12a211
changeset: 21111:290c9b12a211
user: Augusto Mauch <augusto.mauch <at> openbravo.com>
date: Wed Sep 11 11:03:58 2013 +0200
summary: Adaptive Filtering Project
This changeset enables the use of adaptive filtering in Openbravo OBViewGrids.
The adaptive filtering allows to do client side filtering and sorting of the
grid records if the dataset is small enough. Not only the filtering and sorting
is almost immediate, but the server load is reduced severily as the server is
no longer required to do those tasks.
diffstat:
modules/org.openbravo.client.application/web/org.openbravo.client.application/js/grid/ob-grid.js
| 9 +-
modules/org.openbravo.client.application/web/org.openbravo.client.application/js/grid/ob-view-grid.js
| 53 +++-
modules/org.openbravo.client.application/web/org.openbravo.client.application/js/main/ob-standard-view.js
| 4 +
modules/org.openbravo.client.application/web/org.openbravo.client.application/js/utilities/ob-utilities.js
| 20 +
modules/org.openbravo.client.kernel/src/org/openbravo/client/kernel/reference/ForeignKeyUIDefinition.java
| 5 +
modules/org.openbravo.client.kernel/src/org/openbravo/client/kernel/reference/YesNoUIDefinition.java
| 1 +
modules/org.openbravo.service.datasource/src/org/openbravo/service/datasource/DefaultDataSourceService.java
| 12 +-
modules/org.openbravo.userinterface.smartclient/web/org.openbravo.userinterface.smartclient/js/ob-smartclient.js
| 124 +++++++++-
8 files changed, 209 insertions(+), 19 deletions(-)
diffs (truncated from 370 to 300 lines):
diff -r a555fcd23cc9 -r 290c9b12a211
modules/org.openbravo.client.application/web/org.openbravo.client.application/js/grid/ob-grid.js
---
a/modules/org.openbravo.client.application/web/org.openbravo.client.application/js/grid/ob-grid.js
Wed Sep 11 12:18:04 2013 +0200
+++
b/modules/org.openbravo.client.application/web/org.openbravo.client.application/js/grid/ob-grid.js
Wed Sep 11 11:03:58 2013 +0200
@@ -508,10 +508,17 @@
var i = 0,
fld, length;
if (!keepFilterClause) {
+ // forcing fetch from server in case default filters are removed, in
other
+ // cases adaptive filtering can be used if possible
+ if (this.data) {
+ this.data.forceRefresh = this.filterClause || this.sqlFilterClause;
+ delete this.data.context.params._where;
+ }
+
delete this.filterClause;
delete this.sqlFilterClause;
}
- this.forceRefresh = true;
+
if (this.filterEditor) {
if (this.filterEditor.getEditForm()) {
this.filterEditor.getEditForm().clearValues();
diff -r a555fcd23cc9 -r 290c9b12a211
modules/org.openbravo.client.application/web/org.openbravo.client.application/js/grid/ob-view-grid.js
---
a/modules/org.openbravo.client.application/web/org.openbravo.client.application/js/grid/ob-view-grid.js
Wed Sep 11 12:18:04 2013 +0200
+++
b/modules/org.openbravo.client.application/web/org.openbravo.client.application/js/grid/ob-view-grid.js
Wed Sep 11 11:03:58 2013 +0200
@@ -63,6 +63,8 @@
// prevent this.
editGrid: true,
+ textMatchStyle: 'substring',
+
// ** {{{ editLinkFieldProperties }}} **
// The properties of the ListGridField created for the edit links.
editLinkFieldProperties: {
@@ -196,8 +198,8 @@
// that the _dummy criteria can mean that new/updated records are not
// shown in the grid
neverDropUpdatedRows: true,
- useClientFiltering: false,
- useClientSorting: false,
+ useClientFiltering: true,
+ useClientSorting: true,
fetchDelay: 300,
// overridden to update the context/request properties for the fetch
@@ -279,6 +281,14 @@
this.localData[dsResponse.totalRows] = null;
}
return newData;
+ },
+
+ shouldUseClientFiltering: function () {
+ if (this.forceRefresh) {
+ // forcing fetch from server
+ return false;
+ }
+ return this.Super('shouldUseClientFiltering', arguments);
}
},
@@ -1835,19 +1845,6 @@
// add a dummy criteria to force a fetch
criteria.criteria.push(isc.OBRestDataSource.getDummyCriterion());
- } else if (this.forceRefresh) {
- // add a dummy criteria to force a fetch
- criteria.criteria.push(isc.OBRestDataSource.getDummyCriterion());
- delete this.forceRefresh;
- } else {
- // remove the _dummy
- length = criteria.criteria.length;
- for (i = 0; i < length; i++) {
- if (criteria.criteria[i].fieldName ===
isc.OBRestDataSource.DUMMY_CRITERION_NAME) {
- criteria.criteria.removeAt(i);
- break;
- }
- }
}
// note pass in criteria otherwise infinite looping!
@@ -1956,6 +1953,15 @@
},
onFetchData: function (criteria, requestProperties) {
+ if (this.data && this.data.forceRefresh) {
+ // to force fetch from server, remove all cached data
+ delete this.data.forceRefresh;
+ delete this.data.localData;
+ delete this.data.allRows;
+ this.data.totalRows = 0;
+ this.data.cachedRows = 0;
+ }
+
requestProperties = requestProperties || {};
requestProperties.params =
this.getFetchRequestParams(requestProperties.params);
},
@@ -2642,6 +2648,16 @@
addToCacheData: function (record, rowNum) {
// originalData is used when the grid is grouped
var data = this.originalData || this.data;
+
+ // When a new record is inserted and added to cache, existent cache of
+ // rows received from server is replaced with current localData.
+ // Not doing it causes problems when localData does not match allRows
+ // beacause it has been restricted in client through adaptive filters.
+ data.allRows = data.localData;
+ data.allRowsCriteria = data.criteria || {};
+ data.cachedRows = data.localData.length;
+ data.totalRows = data.localData.length;
+
data.insertCacheData(record, rowNum);
},
@@ -3147,6 +3163,8 @@
this.recomputeCanvasComponents(rowNum);
+ this.body.markForRedraw();
+
return ret;
},
@@ -3454,6 +3472,11 @@
layout.editButton.setErrorState(record[isc.OBViewGrid.ERROR_MESSAGE_PROP]);
layout.editButton.setErrorMessage(record[isc.OBViewGrid.ERROR_MESSAGE_PROP]);
record.editColumnLayout = layout;
+
+ if (this.selection && this.selection.lastSelectionItem &&
this.selection.lastSelectionItem._new) {
+ this.selection.lastSelectionItem.editColumnLayout = layout;
+ }
+
if (record._new) {
layout.showSaveCancel();
} else {
diff -r a555fcd23cc9 -r 290c9b12a211
modules/org.openbravo.client.application/web/org.openbravo.client.application/js/main/ob-standard-view.js
---
a/modules/org.openbravo.client.application/web/org.openbravo.client.application/js/main/ob-standard-view.js
Wed Sep 11 12:18:04 2013 +0200
+++
b/modules/org.openbravo.client.application/web/org.openbravo.client.application/js/main/ob-standard-view.js
Wed Sep 11 11:03:58 2013 +0200
@@ -2414,6 +2414,10 @@
fld.filterEditorType = type.filterEditorType;
}
+ if (type.sortNormalizer) {
+ fld.sortNormalizer = type.sortNormalizer;
+ }
+
if (!fld.filterEditorProperties) {
fld.filterEditorProperties = {};
}
diff -r a555fcd23cc9 -r 290c9b12a211
modules/org.openbravo.client.application/web/org.openbravo.client.application/js/utilities/ob-utilities.js
---
a/modules/org.openbravo.client.application/web/org.openbravo.client.application/js/utilities/ob-utilities.js
Wed Sep 11 12:18:04 2013 +0200
+++
b/modules/org.openbravo.client.application/web/org.openbravo.client.application/js/utilities/ob-utilities.js
Wed Sep 11 11:03:58 2013 +0200
@@ -1200,4 +1200,24 @@
}
return -1;
+};
+
+OB.Utilities.yesNoSortNormalizer = function (item, field, context) {
+ var value = item[field];
+ if (value === true) {
+ return 1;
+ } else if (value === false) {
+ return 2;
+ } else {
+ return 3;
+ }
+};
+
+OB.Utilities.enumSortNormalizer = function (item, field, context) {
+ var value = item[field],
+ undef;
+ if (value === null || value === undef) {
+ return '-'; // hack to sort nulls last
+ }
+ return ' ' + value;
};
\ No newline at end of file
diff -r a555fcd23cc9 -r 290c9b12a211
modules/org.openbravo.client.kernel/src/org/openbravo/client/kernel/reference/ForeignKeyUIDefinition.java
---
a/modules/org.openbravo.client.kernel/src/org/openbravo/client/kernel/reference/ForeignKeyUIDefinition.java
Wed Sep 11 12:18:04 2013 +0200
+++
b/modules/org.openbravo.client.kernel/src/org/openbravo/client/kernel/reference/ForeignKeyUIDefinition.java
Wed Sep 11 11:03:58 2013 +0200
@@ -76,4 +76,9 @@
protected String getSuperGridFieldName(Field field) {
return super.getGridFieldName(field);
}
+
+ @Override
+ public String getTypeProperties() {
+ return "sortNormalizer: function (item, field, context){ return
OB.Utilities.enumSortNormalizer(item, field, context);},";
+ }
}
diff -r a555fcd23cc9 -r 290c9b12a211
modules/org.openbravo.client.kernel/src/org/openbravo/client/kernel/reference/YesNoUIDefinition.java
---
a/modules/org.openbravo.client.kernel/src/org/openbravo/client/kernel/reference/YesNoUIDefinition.java
Wed Sep 11 12:18:04 2013 +0200
+++
b/modules/org.openbravo.client.kernel/src/org/openbravo/client/kernel/reference/YesNoUIDefinition.java
Wed Sep 11 11:03:58 2013 +0200
@@ -65,6 +65,7 @@
@Override
public String getTypeProperties() {
return " valueMap: [null, true, false],"
+ + "sortNormalizer: function (item, field, context){ return
OB.Utilities.yesNoSortNormalizer(item, field, context);},"
+ "shortDisplayFormatter: function(value, field, component, record) {"
+ "return OB.Utilities.getYesNoDisplayValue(value);" + "}, "
+ "createClassicString: function(value) {return
OB.Utilities.getClassicValue(value);},"
diff -r a555fcd23cc9 -r 290c9b12a211
modules/org.openbravo.service.datasource/src/org/openbravo/service/datasource/DefaultDataSourceService.java
---
a/modules/org.openbravo.service.datasource/src/org/openbravo/service/datasource/DefaultDataSourceService.java
Wed Sep 11 12:18:04 2013 +0200
+++
b/modules/org.openbravo.service.datasource/src/org/openbravo/service/datasource/DefaultDataSourceService.java
Wed Sep 11 11:03:58 2013 +0200
@@ -277,8 +277,12 @@
if (entity == null) {
dsProperties = super.getDataSourceProperties(parameters);
} else {
- dsProperties = getInitialProperties(entity,
- parameters.containsKey(DataSourceConstants.MINIMAL_PROPERTY_OUTPUT));
+ if (false) {
+ dsProperties = getInitialProperties(entity,
+
parameters.containsKey(DataSourceConstants.MINIMAL_PROPERTY_OUTPUT));
+ } else {
+ dsProperties = getInitialProperties(entity, false);
+ }
}
// now see if there are additional properties, these are often property
paths
@@ -312,6 +316,10 @@
// than the original property
for (String additionalProp : additionalProps) {
final Property property = DalUtil.getPropertyFromPath(entity,
additionalProp);
+ if (property == null) {
+ log4j.warn("Couldn't find propery from additional property: " +
additionalProp);
+ continue;
+ }
final DataSourceProperty dsProperty =
DataSourceProperty.createFromProperty(property);
dsProperty.setAdditional(true);
dsProperty.setName(additionalProp.replace(DalUtil.DOT,
DalUtil.FIELDSEPARATOR));
diff -r a555fcd23cc9 -r 290c9b12a211
modules/org.openbravo.userinterface.smartclient/web/org.openbravo.userinterface.smartclient/js/ob-smartclient.js
---
a/modules/org.openbravo.userinterface.smartclient/web/org.openbravo.userinterface.smartclient/js/ob-smartclient.js
Wed Sep 11 12:18:04 2013 +0200
+++
b/modules/org.openbravo.userinterface.smartclient/web/org.openbravo.userinterface.smartclient/js/ob-smartclient.js
Wed Sep 11 11:03:58 2013 +0200
@@ -74,6 +74,25 @@
}
});
+isc.ResultSet.addProperties({
+ _original_removeCacheData: isc.ResultSet.getPrototype().removeCacheData,
+ removeCacheData: function (updateData) {
+ var filteringOnClient = this.allRows !== null,
+ i, index, ds;
+ this._original_removeCacheData(updateData);
+ if (filteringOnClient) {
+ ds = this.getDataSource();
+ // remove any rows that were present in the cache
+ for (i = 0; i < updateData.length; i++) {
+ index = ds.findByKeys(updateData[i], this.localData);
+ if (index !== -1) {
+ this.localData.removeAt(index);
+ }
+ }
+ }
+ }
+});
+
isc.Canvas.addProperties({
@@ -785,4 +804,107 @@
}
return this._fieldMatchesFilter(fieldValue, filterValue,
requestProperties);
}
-});
\ No newline at end of file
+});
+
+// When filtering strings in backend, spaces are replaced by % in the resultant
+// ilike expression. For example if filter is "jo sm" the query will be
+// "ilike '%jo%sm%'", so "John Smith" would be found. When filtering in client
+// Smartclient doesn't do this conversion. This code, overwrittes Smartclioent
+// string comparator to work like in backend.
+(function () {
+ var i, containsNoBlanks, originalCondition, stringComparisonNoBlanks,
operators;
+
+ // Replaces isc.contains in the custom string comparator. Blank spaces are
not
+ // part of the comparision, but they separate different tokens to be found
in
+ // the text. It returns true in case the tested text contains, in order, all
the
+ // tokens separated by blank spaces.
+ containsNoBlanks = function (tested, test) {
+ var tokens, token, i, pendingToTest, idx;
+ if (!tested) {
+ return true;
+ }
+
+ tokens = test.split(' ');
+ pendingToTest = tested;
+ for (i = 0; i < tokens.length; i++) {
+ token = tokens[i];
+ idx = pendingToTest.indexOf(token);
+ if (token && idx === -1) {
+ return false;
+ }
+ pendingToTest = pendingToTest.substring(idx + token.length);
+ }
+ return true;
+ };
+
+ // Copied from SmartClient's DataSource.js. The only difference is how
contains
+ // is computed.
------------------------------------------------------------------------------
How ServiceNow helps IT people transform IT departments:
1. Consolidate legacy IT systems to a single system of record for IT
2. Standardize and globalize service processes across IT
3. Implement zero-touch automation to replace manual, redundant tasks
http://pubads.g.doubleclick.net/gampad/clk?id=51271111&iu=/4140/ostg.clktrk
_______________________________________________
Openbravo-commits mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/openbravo-commits