dhis2-devs team mailing list archive
-
dhis2-devs team
-
Mailing list archive
-
Message #39018
[Branch ~dhis2-devs-core/dhis2/trunk] Rev 19808: Event analytics. Reimplemented program indicators. Evaluating per event before performing aggrega...
Merge authors:
Lars Helge Øverland (larshelge)
------------------------------------------------------------
revno: 19808 [merge]
committer: Lars Helge Overland <larshelge@xxxxxxxxx>
branch nick: dhis2
timestamp: Thu 2015-08-20 22:55:35 -0400
message:
Event analytics. Reimplemented program indicators. Evaluating per event before performing aggregation.
modified:
dhis-2/dhis-api/src/main/java/org/hisp/dhis/analytics/AggregationType.java
dhis-2/dhis-api/src/main/java/org/hisp/dhis/common/DimensionType.java
dhis-2/dhis-api/src/main/java/org/hisp/dhis/program/ProgramIndicator.java
dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/DataQueryParams.java
dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/QueryPlanner.java
dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/data/DefaultAnalyticsService.java
dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/data/DefaultQueryPlanner.java
dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/event/EventQueryParams.java
dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/event/data/DefaultEventQueryPlanner.java
dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/event/data/JdbcEventAnalyticsManager.java
dhis-2/dhis-services/dhis-service-core/src/main/resources/i18n_global.properties
dhis-2/dhis-services/dhis-service-core/src/main/resources/org/hisp/dhis/program/hibernate/ProgramIndicator.hbm.xml
dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-program/src/main/java/org/hisp/dhis/trackedentity/action/programindicator/AddProgramIndicatorAction.java
dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-program/src/main/java/org/hisp/dhis/trackedentity/action/programindicator/UpdateProgramIndicatorAction.java
dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-program/src/main/webapp/dhis-web-maintenance-program/addProgramIndicator.vm
dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-program/src/main/webapp/dhis-web-maintenance-program/updateProgramIndicator.vm
--
lp:dhis2
https://code.launchpad.net/~dhis2-devs-core/dhis2/trunk
Your team DHIS 2 developers is subscribed to branch lp:dhis2.
To unsubscribe from this branch go to https://code.launchpad.net/~dhis2-devs-core/dhis2/trunk/+edit-subscription
=== modified file 'dhis-2/dhis-api/src/main/java/org/hisp/dhis/analytics/AggregationType.java'
--- dhis-2/dhis-api/src/main/java/org/hisp/dhis/analytics/AggregationType.java 2015-08-20 20:05:43 +0000
+++ dhis-2/dhis-api/src/main/java/org/hisp/dhis/analytics/AggregationType.java 2015-08-21 01:47:02 +0000
@@ -43,6 +43,7 @@
MAX( "max" ),
NONE( "none" ),
DEFAULT( "default" ),
+ CUSTOM( "custom" ),
// Internal types
@@ -63,7 +64,7 @@
{
return value;
}
-
+
public static AggregationType fromValue( String value )
{
for ( AggregationType type : AggregationType.values() )
=== modified file 'dhis-2/dhis-api/src/main/java/org/hisp/dhis/common/DimensionType.java'
--- dhis-2/dhis-api/src/main/java/org/hisp/dhis/common/DimensionType.java 2015-07-15 06:49:50 +0000
+++ dhis-2/dhis-api/src/main/java/org/hisp/dhis/common/DimensionType.java 2015-08-21 01:47:02 +0000
@@ -36,6 +36,7 @@
DATA_X,
PROGRAM_DATAELEMENT,
PROGRAM_ATTRIBUTE,
+ PROGRAM_INDICATOR,
DATA_COLLAPSED,
CATEGORY_OPTION_COMBO,
ATTRIBUTE_OPTION_COMBO,
=== modified file 'dhis-2/dhis-api/src/main/java/org/hisp/dhis/program/ProgramIndicator.java'
--- dhis-2/dhis-api/src/main/java/org/hisp/dhis/program/ProgramIndicator.java 2015-08-20 15:49:48 +0000
+++ dhis-2/dhis-api/src/main/java/org/hisp/dhis/program/ProgramIndicator.java 2015-08-21 01:47:02 +0000
@@ -36,6 +36,7 @@
import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlProperty;
import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlRootElement;
+import org.hisp.dhis.analytics.AggregationType;
import org.hisp.dhis.common.BaseIdentifiableObject;
import org.hisp.dhis.common.BaseNameableObject;
import org.hisp.dhis.common.DxfNamespaces;
@@ -87,6 +88,8 @@
private String expression;
private String filter;
+
+ private AggregationType aggregationType;
/**
* Number of decimals to use for indicator value, null implies default.
@@ -103,7 +106,6 @@
public ProgramIndicator()
{
-
}
// -------------------------------------------------------------------------
@@ -119,6 +121,14 @@
{
return decimals != null && decimals >= 0;
}
+
+ /**
+ * Returns aggregation type, if not exists returns AVERAGE.
+ */
+ public AggregationType getAggregationTypeFallback()
+ {
+ return aggregationType != null ? aggregationType : AggregationType.AVERAGE;
+ }
// -------------------------------------------------------------------------
// Getters && Setters
@@ -180,6 +190,19 @@
@JsonProperty
@JsonView( { DetailedView.class, ExportView.class } )
@JacksonXmlProperty( namespace = DxfNamespaces.DXF_2_0 )
+ public AggregationType getAggregationType()
+ {
+ return aggregationType;
+ }
+
+ public void setAggregationType( AggregationType aggregationType )
+ {
+ this.aggregationType = aggregationType;
+ }
+
+ @JsonProperty
+ @JsonView( { DetailedView.class, ExportView.class } )
+ @JacksonXmlProperty( namespace = DxfNamespaces.DXF_2_0 )
public Integer getDecimals()
{
return decimals;
=== modified file 'dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/DataQueryParams.java'
--- dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/DataQueryParams.java 2015-08-10 21:57:49 +0000
+++ dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/DataQueryParams.java 2015-08-21 01:47:02 +0000
@@ -244,11 +244,6 @@
*/
protected transient Map<OrganisationUnit, Integer> dataApprovalLevels = new HashMap<>();
- /**
- * Filter expression.
- */
- protected transient String filterExpression;
-
// -------------------------------------------------------------------------
// Constructors
// -------------------------------------------------------------------------
@@ -287,7 +282,6 @@
params.dataPeriodType = this.dataPeriodType;
params.skipPartitioning = this.skipPartitioning;
params.dataApprovalLevels = new HashMap<>( this.dataApprovalLevels );
- params.filterExpression = this.filterExpression;
return params;
}
@@ -1003,15 +997,7 @@
{
return programStage != null;
}
-
- /**
- * Indicates whether this object has a filter expression.
- */
- public boolean hasFilterExpression()
- {
- return filterExpression != null;
- }
-
+
// -------------------------------------------------------------------------
// Static methods
// -------------------------------------------------------------------------
@@ -1483,16 +1469,6 @@
this.dataApprovalLevels = dataApprovalLevels;
}
- public String getFilterExpression()
- {
- return filterExpression;
- }
-
- public void setFilterExpression( String filterExpression )
- {
- this.filterExpression = filterExpression;
- }
-
// -------------------------------------------------------------------------
// Get and set helpers for dimensions or filter
// -------------------------------------------------------------------------
=== modified file 'dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/QueryPlanner.java'
--- dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/QueryPlanner.java 2015-07-10 15:56:26 +0000
+++ dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/QueryPlanner.java 2015-08-21 01:47:02 +0000
@@ -105,13 +105,6 @@
List<DataQueryParams> groupByOrgUnitLevel( DataQueryParams params );
/**
- * If program indicators appear as dimensions; groups the given query into
- * sub queries based on the filter of the program indicators. Sets the
- * program indicator filter on queries which contain program indicators.
- */
- List<DataQueryParams> groupByFilterExpression( DataQueryParams params );
-
- /**
* Groups the given query into sub queries based on its periods and which
* partition it should be executed against. Sets the partition table name on
* each query. Queries are grouped based on periods if appearing as a
=== modified file 'dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/data/DefaultAnalyticsService.java'
--- dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/data/DefaultAnalyticsService.java 2015-08-18 11:56:04 +0000
+++ dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/data/DefaultAnalyticsService.java 2015-08-21 01:47:02 +0000
@@ -56,6 +56,7 @@
import static org.hisp.dhis.common.IdentifiableObjectUtils.getUids;
import static org.hisp.dhis.common.NameableObjectUtils.asList;
import static org.hisp.dhis.common.NameableObjectUtils.asTypedList;
+import static org.hisp.dhis.commons.collection.ListUtils.sort;
import static org.hisp.dhis.commons.util.TextUtils.splitSafe;
import static org.hisp.dhis.organisationunit.OrganisationUnit.KEY_LEVEL;
import static org.hisp.dhis.organisationunit.OrganisationUnit.KEY_ORGUNIT_GROUP;
@@ -67,7 +68,6 @@
import static org.hisp.dhis.period.PeriodType.getPeriodTypeFromIsoString;
import static org.hisp.dhis.reporttable.ReportTable.IRT2D;
import static org.hisp.dhis.reporttable.ReportTable.addIfEmpty;
-import static org.hisp.dhis.commons.collection.ListUtils.sort;
import java.util.ArrayList;
import java.util.Collection;
@@ -101,7 +101,6 @@
import org.hisp.dhis.common.CombinationGenerator;
import org.hisp.dhis.common.DataDimensionItem;
import org.hisp.dhis.common.DataDimensionItem.DataDimensionItemType;
-import org.hisp.dhis.common.comparator.IdentifiableObjectNameComparator;
import org.hisp.dhis.common.DimensionType;
import org.hisp.dhis.common.DimensionalObject;
import org.hisp.dhis.common.DimensionalObjectUtils;
@@ -115,6 +114,7 @@
import org.hisp.dhis.common.MapMap;
import org.hisp.dhis.common.NameableObject;
import org.hisp.dhis.common.NameableObjectUtils;
+import org.hisp.dhis.common.comparator.IdentifiableObjectNameComparator;
import org.hisp.dhis.commons.collection.ListUtils;
import org.hisp.dhis.commons.collection.UniqueArrayList;
import org.hisp.dhis.commons.util.DebugUtils;
@@ -136,7 +136,6 @@
import org.hisp.dhis.period.RelativePeriodEnum;
import org.hisp.dhis.period.RelativePeriods;
import org.hisp.dhis.period.comparator.AscendingPeriodEndDateComparator;
-import org.hisp.dhis.program.ProgramIndicator;
import org.hisp.dhis.program.ProgramIndicatorService;
import org.hisp.dhis.program.ProgramService;
import org.hisp.dhis.program.ProgramStageService;
@@ -255,9 +254,7 @@
addDataSetValues( params, grid );
- addProgramIndicatorValues( params, grid );
-
- addProgramDataElementAttributeValues( params, grid );
+ addProgramDataElementAttributeIndicatorValues( params, grid );
addDynamicDimensionValues( params, grid );
@@ -510,85 +507,19 @@
}
/**
- * Adds program indicator values to the given grid based on the given data query
- * parameters.
- *
- * @param params the data query parameters.
- * @param grid the grid.
- */
- private void addProgramIndicatorValues( DataQueryParams params, Grid grid )
- {
- if ( !params.getProgramIndicators().isEmpty() && !params.isSkipData() )
- {
- // -----------------------------------------------------------------
- // Run queries with different filter expression separately
- // -----------------------------------------------------------------
-
- List<DataQueryParams> queries = queryPlanner.groupByFilterExpression( params );
-
- for ( DataQueryParams query : queries )
- {
- DataQueryParams dataSourceParams = query.instance();
- dataSourceParams.retainDataDimension( DataDimensionItemType.PROGRAM_INDICATOR );
-
- List<ProgramIndicator> indicators = asTypedList( dataSourceParams.getProgramIndicators() );
-
- //TODO constants
-
- // -----------------------------------------------------------------
- // Get indicator values
- // -----------------------------------------------------------------
-
- List<List<DimensionItem>> dimensionItemPermutations = dataSourceParams.getDimensionItemPermutations();
-
- Map<String, Map<String, Double>> permutationOperandValueMap = getProgramPermutationOperandValueMap( dataSourceParams );
-
- for ( ProgramIndicator indicator : indicators )
- {
- for ( List<DimensionItem> dimensionItems : dimensionItemPermutations )
- {
- String permKey = DimensionItem.asItemKey( dimensionItems );
-
- Map<String, Double> valueMap = permutationOperandValueMap.get( permKey );
-
- if ( valueMap == null )
- {
- continue;
- }
-
- Double value = programIndicatorService.getProgramIndicatorValue( indicator, valueMap );
-
- if ( value != null )
- {
- List<DimensionItem> row = new ArrayList<>( dimensionItems );
-
- row.add( DX_INDEX, new DimensionItem( DATA_X_DIM_ID, indicator ) );
-
- Double roundedValue = indicator.hasDecimals() ? MathUtils.getRounded( value, indicator.getDecimals() ) : MathUtils.getRounded( value );
-
- grid.addRow();
- grid.addValues( DimensionItem.getItemIdentifiers( row ) );
- grid.addValue( dataSourceParams.isSkipRounding() ? value : roundedValue );
- }
- }
- }
- }
- }
- }
-
- /**
* Adds program data element values to the given grid based on the given data
* query parameters.
*
* @param params the data query parameters.
* @param grid the grid.
*/
- private void addProgramDataElementAttributeValues( DataQueryParams params, Grid grid )
+ private void addProgramDataElementAttributeIndicatorValues( DataQueryParams params, Grid grid )
{
- if ( !params.getAllProgramDataElementsAndAttributes().isEmpty() && !params.isSkipData() )
+ if ( ( !params.getAllProgramDataElementsAndAttributes().isEmpty() || !params.getProgramIndicators().isEmpty() ) && !params.isSkipData() )
{
DataQueryParams dataSourceParams = params.instance();
- dataSourceParams.retainDataDimensions( DataDimensionItemType.PROGRAM_DATA_ELEMENT, DataDimensionItemType.PROGRAM_ATTRIBUTE );
+ dataSourceParams.retainDataDimensions( DataDimensionItemType.PROGRAM_DATA_ELEMENT,
+ DataDimensionItemType.PROGRAM_ATTRIBUTE, DataDimensionItemType.PROGRAM_INDICATOR );
EventQueryParams eventQueryParams = EventQueryParams.fromDataQueryParams( dataSourceParams );
@@ -1376,41 +1307,6 @@
}
/**
- * Returns a mapping of permutation keys and mappings of program data elements
- * / program attributes and values based on the given query.
- *
- * @param params the data query parameters.
- */
- private Map<String, Map<String, Double>> getProgramPermutationOperandValueMap( DataQueryParams params )
- {
- Map<String, Map<String, Double>> permutationMap = new HashMap<>();
-
- List<ProgramIndicator> programIndicators = asTypedList( params.getProgramIndicators() );
- List<NameableObject> dataElements = asList( programIndicatorService.getDataElementsInIndicators( programIndicators ) );
- List<NameableObject> attributes = asList( programIndicatorService.getAttributesInIndicators( programIndicators ) );
- List<NameableObject> dataItems = ListUtils.union( dataElements, attributes );
-
- if ( !dataElements.isEmpty() || !attributes.isEmpty() )
- {
- DataQueryParams dataSourceParams = params.instance().removeDimension( DATA_X_DIM_ID );
-
- dataSourceParams.getDimensions().add( DX_INDEX, new BaseDimensionalObject(
- DATA_X_DIM_ID, DimensionType.DATA_X, dataItems ) );
-
- EventQueryParams eventQueryParams = EventQueryParams.fromDataQueryParams( dataSourceParams );
- eventQueryParams.setSkipRounding( true );
-
- Grid grid = eventAnalyticsService.getAggregatedEventData( eventQueryParams );
-
- Map<String, Double> valueMap = grid.getAsMap( grid.getWidth() - 1, DIMENSION_SEP );
-
- permutationMap.putAll( DataQueryParams.getPermutationProgramValueMap( valueMap ) );
- }
-
- return permutationMap;
- }
-
- /**
* Returns a mapping of dimension keys and aggregated values for the data
* element totals part of the indicators in the given query.
*
=== modified file 'dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/data/DefaultQueryPlanner.java'
--- dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/data/DefaultQueryPlanner.java 2015-07-10 21:29:06 +0000
+++ dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/data/DefaultQueryPlanner.java 2015-08-21 01:47:02 +0000
@@ -72,7 +72,6 @@
import org.hisp.dhis.organisationunit.OrganisationUnitService;
import org.hisp.dhis.period.Period;
import org.hisp.dhis.period.PeriodType;
-import org.hisp.dhis.program.ProgramIndicator;
import org.hisp.dhis.program.ProgramIndicatorService;
import org.hisp.dhis.setting.SystemSettingManager;
import org.hisp.dhis.system.filter.AggregatableDataElementFilter;
@@ -539,37 +538,6 @@
return queries;
}
-
- @Override
- public List<DataQueryParams> groupByFilterExpression( DataQueryParams params )
- {
- List<DataQueryParams> queries = new ArrayList<>();
-
- if ( !params.getProgramIndicators().isEmpty() )
- {
- ListMap<String, NameableObject> filterProgramIndicatorMap = getFilterProgramIndicatorMap( params.getProgramIndicators() );
-
- for ( String filter : filterProgramIndicatorMap.keySet() )
- {
- DataQueryParams query = params.instance();
- query.setProgramIndicators( filterProgramIndicatorMap.get( filter ) );
- query.setFilterExpression( programIndicatorService.getAnalyticsSQl( filter ) );
- queries.add( query );
- }
- }
- else
- {
- queries.add( params.instance() );
- return queries;
- }
-
- if ( queries.size() > 1 )
- {
- log.debug( "Split on filter expression: " + queries.size() );
- }
-
- return queries;
- }
private List<DataQueryParams> groupByDataType( DataQueryParams params )
{
@@ -776,26 +744,6 @@
}
/**
- * Creates a mapping between filter and program indicator for the given
- * program indicators.
- */
- private ListMap<String, NameableObject> getFilterProgramIndicatorMap( List<NameableObject> programIndicators )
- {
- ListMap<String, NameableObject> map = new ListMap<>();
-
- for ( NameableObject programIndicator : programIndicators )
- {
- ProgramIndicator indicator = (ProgramIndicator) programIndicator;
-
- String filter = indicator.getFilter();
-
- map.putValue( filter, indicator );
- }
-
- return map;
- }
-
- /**
* Creates a mapping between data type and data element for the given data elements.
*/
private ListMap<DataType, NameableObject> getDataTypeDataElementMap( List<NameableObject> dataElements )
=== modified file 'dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/event/EventQueryParams.java'
--- dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/event/EventQueryParams.java 2015-08-20 20:05:43 +0000
+++ dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/event/EventQueryParams.java 2015-08-21 02:55:35 +0000
@@ -28,8 +28,8 @@
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
+import static org.hisp.dhis.common.DimensionalObject.PERIOD_DIM_ID;
import static org.hisp.dhis.common.DimensionalObject.DATA_X_DIM_ID;
-import static org.hisp.dhis.common.DimensionalObject.PERIOD_DIM_ID;
import java.util.ArrayList;
import java.util.Date;
@@ -52,6 +52,7 @@
import org.hisp.dhis.option.OptionSet;
import org.hisp.dhis.organisationunit.OrganisationUnit;
import org.hisp.dhis.period.Period;
+import org.hisp.dhis.program.ProgramIndicator;
import org.hisp.dhis.trackedentity.TrackedEntityAttribute;
/**
@@ -67,8 +68,12 @@
private List<QueryItem> items = new ArrayList<>();
private List<QueryItem> itemFilters = new ArrayList<>();
-
+
private DimensionalObject value;
+
+ private List<ProgramIndicator> itemProgramIndicators = new ArrayList<>();
+
+ private ProgramIndicator programIndicator;
private List<String> asc = new ArrayList<>();
@@ -113,7 +118,6 @@
params.partitions = new Partitions( this.partitions );
params.periodType = this.periodType;
- params.filterExpression = this.filterExpression;
params.program = this.program;
params.programStage = this.programStage;
@@ -122,6 +126,8 @@
params.items = new ArrayList<>( this.items );
params.itemFilters = new ArrayList<>( this.itemFilters );
params.value = this.value;
+ params.itemProgramIndicators = new ArrayList<>( this.itemProgramIndicators );
+ params.programIndicator = this.programIndicator;
params.asc = new ArrayList<>( this.asc );
params.desc = new ArrayList<>( this.desc );
params.organisationUnitMode = this.organisationUnitMode;
@@ -159,7 +165,7 @@
TrackedEntityAttribute element = (TrackedEntityAttribute) object;
QueryItem item = new QueryItem( element, element.getLegendSet(), element.getValueType(), element.getAggregationType(), element.getOptionSet() );
params.getItems().add( item );
- }
+ }
for ( NameableObject object : dataQueryParams.getFilterProgramDataElements() )
{
@@ -175,6 +181,12 @@
params.getItemFilters().add( item );
}
+ for ( NameableObject object : dataQueryParams.getProgramIndicators() )
+ {
+ ProgramIndicator programIndicator = (ProgramIndicator) object;
+ params.getItemProgramIndicators().add( programIndicator );
+ }
+
params.setAggregateData( true );
params.removeDimension( DATA_X_DIM_ID );
@@ -311,6 +323,7 @@
public boolean isAggregationType( AggregationType aggregationType )
{
AggregationType type = getAggregationTypeFallback();
+
return type != null && type.equals( aggregationType );
}
@@ -390,7 +403,12 @@
{
return value != null;
}
-
+
+ public boolean hasProgramIndicatorDimension()
+ {
+ return programIndicator != null;
+ }
+
/**
* Indicates whether the program of this query requires registration of
* tracked entity instances.
@@ -419,6 +437,8 @@
"Items: " + items + ", " +
"Item filters: " + itemFilters + ", " +
"Value: " + value + ", " +
+ "Item program indicators: " + itemProgramIndicators + ", " +
+ "Program indicator: " + programIndicator + ", " +
"Aggregation type: " + aggregationType + ", " +
"Dimensions: " + dimensions + ", " +
"Filters: " + filters + "]";
@@ -478,6 +498,26 @@
this.value = value;
}
+ public List<ProgramIndicator> getItemProgramIndicators()
+ {
+ return itemProgramIndicators;
+ }
+
+ public void setItemProgramIndicators( List<ProgramIndicator> itemProgramIndicators )
+ {
+ this.itemProgramIndicators = itemProgramIndicators;
+ }
+
+ public ProgramIndicator getProgramIndicator()
+ {
+ return programIndicator;
+ }
+
+ public void setProgramIndicator( ProgramIndicator programIndicator )
+ {
+ this.programIndicator = programIndicator;
+ }
+
public List<String> getAsc()
{
return asc;
=== modified file 'dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/event/data/DefaultEventQueryPlanner.java'
--- dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/event/data/DefaultEventQueryPlanner.java 2015-08-07 17:59:15 +0000
+++ dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/event/data/DefaultEventQueryPlanner.java 2015-08-21 02:55:35 +0000
@@ -51,6 +51,7 @@
import org.hisp.dhis.organisationunit.OrganisationUnit;
import org.hisp.dhis.organisationunit.OrganisationUnitService;
import org.hisp.dhis.period.Period;
+import org.hisp.dhis.program.ProgramIndicator;
import org.hisp.dhis.setting.SystemSettingManager;
import org.springframework.beans.factory.annotation.Autowired;
@@ -266,9 +267,19 @@
{
EventQueryParams query = params.instance();
query.getItems().clear();
+ query.getItemProgramIndicators().clear();
query.setValue( item.getItem() );
queries.add( query );
}
+
+ for ( ProgramIndicator programIndicator : params.getItemProgramIndicators() )
+ {
+ EventQueryParams query = params.instance();
+ query.getItems().clear();
+ query.getItemProgramIndicators().clear();
+ query.setProgramIndicator( programIndicator );
+ queries.add( query );
+ }
}
else if ( params.isCollapseDataDimensions() && !params.getItems().isEmpty() )
{
=== modified file 'dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/event/data/JdbcEventAnalyticsManager.java'
--- dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/event/data/JdbcEventAnalyticsManager.java 2015-08-20 20:05:43 +0000
+++ dhis-2/dhis-services/dhis-service-analytics/src/main/java/org/hisp/dhis/analytics/event/data/JdbcEventAnalyticsManager.java 2015-08-21 02:55:35 +0000
@@ -56,8 +56,8 @@
import org.hisp.dhis.legend.Legend;
import org.hisp.dhis.option.Option;
import org.hisp.dhis.organisationunit.OrganisationUnit;
+import org.hisp.dhis.program.ProgramIndicatorService;
import org.hisp.dhis.system.util.MathUtils;
-import org.hisp.dhis.system.util.ValidationUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.jdbc.BadSqlGrammarException;
import org.springframework.jdbc.core.JdbcTemplate;
@@ -85,6 +85,9 @@
@Autowired
private StatementBuilder statementBuilder;
+ @Autowired
+ private ProgramIndicatorService programIndicatorService;
+
// -------------------------------------------------------------------------
// EventAnalyticsManager implementation
// -------------------------------------------------------------------------
@@ -158,7 +161,14 @@
if ( params.isAggregateData() )
{
- grid.addValue( params.getValue().getUid() );
+ if ( params.hasValueDimension() )
+ {
+ grid.addValue( params.getValue().getUid() );
+ }
+ else if ( params.hasProgramIndicatorDimension() )
+ {
+ grid.addValue( params.getProgramIndicator().getUid() );
+ }
}
else
{
@@ -176,7 +186,7 @@
grid.addValue( dimensionValue );
}
- if ( params.hasValueDimension() )
+ if ( params.hasValueDimension() || params.hasProgramIndicatorDimension() )
{
double value = rowSet.getDouble( "value" );
grid.addValue( params.isSkipRounding() ? value : MathUtils.getRounded( value ) );
@@ -316,11 +326,21 @@
if ( params.hasValueDimension() ) // && isNumeric
{
- String column = statementBuilder.columnQuote( params.getValue().getUid() );
-
String function = params.getAggregationTypeFallback().getValue();
- return function + "(" + column + ")";
+ String expression = statementBuilder.columnQuote( params.getValue().getUid() );
+
+ return function + "(" + expression + ")";
+ }
+ else if ( params.hasProgramIndicatorDimension() )
+ {
+ String function = params.getProgramIndicator().getAggregationTypeFallback().getValue();
+
+ String expression = programIndicatorService.getAnalyticsSQl( params.getProgramIndicator().getExpression() );
+
+ return function + "(" + expression + ")";
+
+ //TODO check if expression is valid and safe SQL
}
else
{
@@ -483,9 +503,11 @@
// Filter expression
// ---------------------------------------------------------------------
- if ( params.hasFilterExpression() && ValidationUtils.expressionIsValidSQl( params.getFilterExpression() ) )
+ if ( params.hasProgramIndicatorDimension() && params.getProgramIndicator().hasFilter() )
{
- String sqlFilter = ExpressionUtils.asSql( params.getFilterExpression() );
+ String filter = programIndicatorService.getAnalyticsSQl( params.getProgramIndicator().getFilter() );
+
+ String sqlFilter = ExpressionUtils.asSql( filter );
sql += "and (" + sqlFilter + ") ";
}
=== modified file 'dhis-2/dhis-services/dhis-service-core/src/main/resources/i18n_global.properties'
--- dhis-2/dhis-services/dhis-service-core/src/main/resources/i18n_global.properties 2015-08-18 20:08:20 +0000
+++ dhis-2/dhis-services/dhis-service-core/src/main/resources/i18n_global.properties 2015-08-21 02:55:35 +0000
@@ -557,6 +557,7 @@
bool=Yes/No
none=None
yes_only = Yes Only
+custom=Custom
#-- User account --------------------------------------------------------------#
=== modified file 'dhis-2/dhis-services/dhis-service-core/src/main/resources/org/hisp/dhis/program/hibernate/ProgramIndicator.hbm.xml'
--- dhis-2/dhis-services/dhis-service-core/src/main/resources/org/hisp/dhis/program/hibernate/ProgramIndicator.hbm.xml 2015-08-07 15:23:36 +0000
+++ dhis-2/dhis-services/dhis-service-core/src/main/resources/org/hisp/dhis/program/hibernate/ProgramIndicator.hbm.xml 2015-08-21 02:55:35 +0000
@@ -28,6 +28,13 @@
<property name="filter" type="text" />
+ <property name="aggregationType" length="40">
+ <type name="org.hibernate.type.EnumType">
+ <param name="enumClass">org.hisp.dhis.analytics.AggregationType</param>
+ <param name="type">12</param>
+ </type>
+ </property>
+
<property name="decimals" />
<property name="displayInForm" />
=== modified file 'dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-program/src/main/java/org/hisp/dhis/trackedentity/action/programindicator/AddProgramIndicatorAction.java'
--- dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-program/src/main/java/org/hisp/dhis/trackedentity/action/programindicator/AddProgramIndicatorAction.java 2015-08-07 15:23:36 +0000
+++ dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-program/src/main/java/org/hisp/dhis/trackedentity/action/programindicator/AddProgramIndicatorAction.java 2015-08-21 02:55:35 +0000
@@ -32,6 +32,7 @@
import java.util.regex.Pattern;
import org.apache.commons.lang3.StringUtils;
+import org.hisp.dhis.analytics.AggregationType;
import org.hisp.dhis.program.Program;
import org.hisp.dhis.program.ProgramIndicator;
import org.hisp.dhis.program.ProgramIndicatorService;
@@ -128,7 +129,14 @@
{
this.filter = filter;
}
+
+ private String aggregationType;
+ public void setAggregationType( String aggregationType )
+ {
+ this.aggregationType = aggregationType;
+ }
+
private Integer decimals;
public void setDecimals( Integer decimals )
@@ -183,6 +191,7 @@
indicator.setValueType( StringUtils.trimToNull( valueType ) );
indicator.setExpression( StringUtils.trimToNull( expression ) );
indicator.setFilter( StringUtils.trimToNull( filter ) );
+ indicator.setAggregationType( AggregationType.valueOf( aggregationType ) );
indicator.setDecimals( decimals );
indicator.setDisplayInForm( displayInForm );
indicator.setRootDate( StringUtils.trimToNull( rootDate ) );
=== modified file 'dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-program/src/main/java/org/hisp/dhis/trackedentity/action/programindicator/UpdateProgramIndicatorAction.java'
--- dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-program/src/main/java/org/hisp/dhis/trackedentity/action/programindicator/UpdateProgramIndicatorAction.java 2015-08-07 15:23:36 +0000
+++ dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-program/src/main/java/org/hisp/dhis/trackedentity/action/programindicator/UpdateProgramIndicatorAction.java 2015-08-21 02:55:35 +0000
@@ -32,6 +32,7 @@
import java.util.regex.Pattern;
import org.apache.commons.lang.StringUtils;
+import org.hisp.dhis.analytics.AggregationType;
import org.hisp.dhis.program.ProgramIndicator;
import org.hisp.dhis.program.ProgramIndicatorService;
@@ -115,6 +116,13 @@
this.filter = filter;
}
+ private String aggregationType;
+
+ public void setAggregationType( String aggregationType )
+ {
+ this.aggregationType = aggregationType;
+ }
+
private Integer decimals;
public void setDecimals( Integer decimals )
@@ -174,6 +182,7 @@
indicator.setValueType( StringUtils.trimToNull( valueType ) );
indicator.setExpression( StringUtils.trimToNull( expression ) );
indicator.setFilter( StringUtils.trimToNull( filter ) );
+ indicator.setAggregationType( AggregationType.valueOf( aggregationType ) );
indicator.setDecimals( decimals );
indicator.setDisplayInForm( displayInForm );
indicator.setRootDate( StringUtils.trimToNull( rootDate ) );
=== modified file 'dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-program/src/main/webapp/dhis-web-maintenance-program/addProgramIndicator.vm'
--- dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-program/src/main/webapp/dhis-web-maintenance-program/addProgramIndicator.vm 2015-08-07 15:23:36 +0000
+++ dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-program/src/main/webapp/dhis-web-maintenance-program/addProgramIndicator.vm 2015-08-21 02:55:35 +0000
@@ -63,6 +63,21 @@
<td></td>
</tr>
<tr>
+ <td><label for="aggregationType">$i18n.getString( "aggregation_type" )</label></td>
+ <td>
+ <select id="aggregationType" name="aggregationType">
+ <option value="AVERAGE">$i18n.getString( "average" )</option>
+ <option value="SUM">$i18n.getString( "sum" )</option>
+ <option value="COUNT">$i18n.getString( "count" )</option>
+ <option value="STDDEV">$i18n.getString( "stddev" )</option>
+ <option value="VARIANCE">$i18n.getString( "variance" )</option>
+ <option value="MIN">$i18n.getString( "min" )</option>
+ <option value="MAX">$i18n.getString( "max" )</option>
+ <option value="MAX">$i18n.getString( "custom" )</option>
+ </select>
+ </td>
+ </tr>
+ <tr>
<td><label for="decimals">$i18n.getString( "decimals_in_data_output" )</label></td>
<td>
<select id="decimals" name="decimals">
=== modified file 'dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-program/src/main/webapp/dhis-web-maintenance-program/updateProgramIndicator.vm'
--- dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-program/src/main/webapp/dhis-web-maintenance-program/updateProgramIndicator.vm 2015-08-07 15:23:36 +0000
+++ dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-program/src/main/webapp/dhis-web-maintenance-program/updateProgramIndicator.vm 2015-08-21 02:55:35 +0000
@@ -63,6 +63,20 @@
<td></td>
</tr>
<tr>
+ <td><label for="aggregationType">$i18n.getString( "aggregation_type" )</label></td>
+ <td>
+ <select id="aggregationType" name="aggregationType">
+ <option value="AVERAGE"#if( $programIndicator.aggregationType == 'AVERAGE' ) selected="selected"#end>$i18n.getString( "average" )</option>
+ <option value="SUM"#if( $programIndicator.aggregationType == 'SUM' ) selected="selected"#end>$i18n.getString( "sum" )</option>
+ <option value="COUNT"#if( $programIndicator.aggregationType == 'COUNT' ) selected="selected"#end>$i18n.getString( "count" )</option>
+ <option value="STDDEV"#if( $programIndicator.aggregationType == 'STDDEV' ) selected="selected"#end>$i18n.getString( "stddev" )</option>
+ <option value="VARIANCE"#if( $programIndicator.aggregationType == 'VARIANCE' ) selected="selected"#end>$i18n.getString( "variance" )</option>
+ <option value="MIN"#if( $programIndicator.aggregationType == 'MIN' ) selected="selected"#end>$i18n.getString( "min" )</option>
+ <option value="MAX"#if( $programIndicator.aggregationType == 'MAX' ) selected="selected"#end>$i18n.getString( "max" )</option>
+ </select>
+ </td>
+ </tr>
+ <tr>
<td><label for="decimals">$i18n.getString( "decimals_in_data_output" )</label></td>
<td>
<select id="decimals" name="decimals">