monasca-common/java/monasca-common-model/src/main/java/monasca/common/model/alarm/AlarmSubExpressionListener....

171 lines
5.2 KiB
Java

/*
* Copyright (c) 2014 Hewlett-Packard Development Company, L.P.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
* implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package monasca.common.model.alarm;
import java.util.ArrayList;
import java.util.List;
import java.util.SortedMap;
import java.util.TreeMap;
import monasca.common.model.metric.MetricDefinition;
/**
* Complex alarm parser lister for sub expression extraction.
*/
class AlarmSubExpressionListener extends AlarmExpressionBaseListener {
private final boolean simpleExpression;
private AggregateFunction function;
private String namespace;
private SortedMap<String, String> dimensions = new TreeMap<String, String>();
private AlarmOperator operator;
private double threshold;
private int period = AlarmSubExpression.DEFAULT_PERIOD;
private int periods = AlarmSubExpression.DEFAULT_PERIODS;
private List<Object> elements = new ArrayList<Object>();
AlarmSubExpressionListener(boolean simpleExpression) {
this.simpleExpression = simpleExpression;
}
private void saveSubExpression() {
AlarmSubExpression subExpression = new AlarmSubExpression(function, new MetricDefinition(
namespace, dimensions), operator, threshold, period, periods);
elements.add(subExpression);
function = null;
namespace = null;
dimensions = new TreeMap<String, String>();
operator = null;
threshold = 0;
period = AlarmSubExpression.DEFAULT_PERIOD;
periods = AlarmSubExpression.DEFAULT_PERIODS;
}
@Override
public void exitRelationalExprFwd(AlarmExpressionParser.RelationalExprFwdContext ctx) {
// This is *right now* basically the same as a min or max function, convert it
if (operator == AlarmOperator.GT || operator == AlarmOperator.GTE)
function = AggregateFunction.MAX;
else
function = AggregateFunction.MIN;
saveSubExpression();
}
@Override
public void exitRelationalExprFuncFwd(AlarmExpressionParser.RelationalExprFuncFwdContext ctx) {
saveSubExpression();
}
@Override
public void enterFunctionType(AlarmExpressionParser.FunctionTypeContext ctx) {
function = AggregateFunction.valueOf(ctx.getChild(0).getText().toUpperCase());
}
@Override
public void enterNamespace(AlarmExpressionParser.NamespaceContext ctx) {
namespace = ctx.getChild(0).getText();
}
@Override
public void enterDimension(AlarmExpressionParser.DimensionContext ctx) {
StringBuilder dimensionName = new StringBuilder();
dimensionName.append(ctx.getChild(0).getText());
int i = 1;
while (!ctx.getChild(i).getText().equals("=")) {
dimensionName.append(' ');
dimensionName.append(ctx.getChild(i).getText());
i++;
}
// move past the '=' token
i++;
StringBuilder dimensionValue = new StringBuilder();
dimensionValue.append(ctx.getChild(i).getText());
i++;
while (i < ctx.getChildCount()) {
dimensionValue.append(' ');
dimensionValue.append(ctx.getChild(i).getText());
i++;
}
if (dimensions.put(dimensionName.toString(), dimensionValue.toString()) != null)
throw new IllegalArgumentException("More than one value was given for dimension "
+ dimensionName);
}
@Override
public void enterPeriod(AlarmExpressionParser.PeriodContext ctx) {
period = Integer.valueOf(ctx.getChild(0).getText());
}
@Override
public void enterRepeat(AlarmExpressionParser.RepeatContext ctx) {
periods = Integer.valueOf(ctx.getChild(0).getText());
}
@Override
public void enterLt(AlarmExpressionParser.LtContext ctx) {
assertSimpleExpression();
operator = AlarmOperator.LT;
}
@Override
public void enterLte(AlarmExpressionParser.LteContext ctx) {
assertSimpleExpression();
operator = AlarmOperator.LTE;
}
@Override
public void enterGt(AlarmExpressionParser.GtContext ctx) {
assertSimpleExpression();
operator = AlarmOperator.GT;
}
@Override
public void enterGte(AlarmExpressionParser.GteContext ctx) {
assertSimpleExpression();
operator = AlarmOperator.GTE;
}
@Override
public void exitLiteral(AlarmExpressionParser.LiteralContext ctx) {
threshold = Double.valueOf(ctx.getChild(0).getText());
}
@Override
public void exitOrExpr(AlarmExpressionParser.OrExprContext ctx) {
elements.add(BooleanOperator.OR);
}
@Override
public void exitAndExpr(AlarmExpressionParser.AndExprContext ctx) {
elements.add(BooleanOperator.AND);
}
/**
* Returns the operator and operand elements of the expression in postfix order. Elements will be
* of types AlarmSubExpression and BooleanOperator.
*/
List<Object> getElements() {
return elements;
}
private void assertSimpleExpression() {
if (simpleExpression && !elements.isEmpty())
throw new IllegalArgumentException("Expected a simple expression");
}
}