ag-grid
Version:
Advanced Data Grid / Data Table supporting Javascript / React / AngularJS / Web Components
74 lines (64 loc) • 3.13 kB
text/typescript
import {Logger, LoggerFactory} from "../logger";
import {Bean} from "../context/context";
import {Qualifier} from "../context/context";
('expressionService')
export class ExpressionService {
private expressionToFunctionCache = <any>{};
private logger: Logger;
private setBeans('loggerFactory') loggerFactory: LoggerFactory) {
(this.logger = loggerFactory.create('ExpressionService');
}
public evaluate(expressionOrFunc: Function | string, params: any): any {
if (typeof expressionOrFunc === 'function') {
// valueGetter is a function, so just call it
let func = <Function> expressionOrFunc;
return func(params);
} else if (typeof expressionOrFunc === 'string') {
// valueGetter is an expression, so execute the expression
let expression = <string> expressionOrFunc;
return this.evaluateExpression(expression, params);
} else {
console.error('ag-Grid: value should be either a string or a function', expressionOrFunc);
}
}
private evaluateExpression(expression: string, params: any): any {
try {
let javaScriptFunction = this.createExpressionFunction(expression);
// the params don't have all these values, rather we add every possible
// value a params can have, which makes whatever is in the params available.
let result = javaScriptFunction(params.value, params.context,
params.oldValue, params.newValue, params.value, params.node,
params.data, params.colDef, params.rowIndex, params.api, params.columnApi,
params.getValue, params.column, params.columnGroup);
return result;
} catch (e) {
// the expression failed, which can happen, as it's the client that
// provides the expression. so print a nice message
console.log('Processing of the expression failed');
console.log('Expression = ' + expression);
console.log('Exception = ' + e);
return null;
}
}
private createExpressionFunction(expression: any) {
// check cache first
if (this.expressionToFunctionCache[expression]) {
return this.expressionToFunctionCache[expression];
}
// if not found in cache, return the function
let functionBody = this.createFunctionBody(expression);
let theFunction = new Function('x, ctx, oldValue, newValue, value, node, data, colDef, rowIndex, api, columnApi, getValue, column, columnGroup', functionBody);
// store in cache
this.expressionToFunctionCache[expression] = theFunction;
return theFunction;
}
private createFunctionBody(expression: any) {
// if the expression has the 'return' word in it, then use as is,
// if not, then wrap it with return and ';' to make a function
if (expression.indexOf('return') >= 0) {
return expression;
} else {
return 'return ' + expression + ';';
}
}
}