org.pentaho.reporting.libraries.formula.lvalues.FormulaFunction Java Examples

The following examples show how to use org.pentaho.reporting.libraries.formula.lvalues.FormulaFunction. You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example #1
Source File: FormulaUtil.java    From pentaho-reporting with GNU Lesser General Public License v2.1 6 votes vote down vote up
private static void collectReferences( final LValue lval, final LinkedHashMap<String, Boolean> map ) {
  if ( lval instanceof Term ) {
    final Term t = (Term) lval;
    final LValue[] childValues = t.getChildValues();
    for ( int i = 0; i < childValues.length; i++ ) {
      final LValue childValue = childValues[ i ];
      collectReferences( childValue, map );
    }
  } else if ( lval instanceof ContextLookup ) {
    final ContextLookup cl = (ContextLookup) lval;
    map.put( cl.getName(), Boolean.TRUE );
  } else if ( lval instanceof FormulaFunction ){
    FormulaFunction ff = FormulaFunction.class.cast(lval);
    LValue[] lvals = ff.getChildValues();
    for (int i = 0; i < lvals.length; i++) {
      collectReferences( lvals[i], map );
    }
  }
}
 
Example #2
Source File: PMSFormula.java    From pentaho-metadata with GNU Lesser General Public License v2.1 6 votes vote down vote up
/**
 * Determines whether or not child val needs to be wrapped with parens. The determining factor is if both the current
 * object and the parent are sql infix operators
 * 
 * @param parent
 *          object
 * @param val
 *          current object
 * @return true if parens are required
 */
public boolean requiresParens( Object parent, Object val ) {
  // first see if parent may required children parens
  boolean parentMatch = false;
  if ( parent instanceof Term ) {
    parentMatch = true;
  } else if ( parent instanceof FormulaFunction ) {
    FormulaFunction parentFunction = (FormulaFunction) parent;
    SQLFunctionGeneratorInterface parentGen = sqlDialect.getFunctionSQLGenerator( parentFunction.getFunctionName() );
    parentMatch = ( parentGen.getType() == SQLFunctionGeneratorInterface.INLINE_FUNCTION );
  }
  if ( !parentMatch ) {
    return false;
  }
  // second see if child needs parens
  if ( val instanceof InfixOperator ) {
    return true;
  } else if ( val instanceof FormulaFunction ) {
    FormulaFunction f = (FormulaFunction) val;
    SQLFunctionGeneratorInterface gen = sqlDialect.getFunctionSQLGenerator( f.getFunctionName() );
    return ( gen.getType() == SQLFunctionGeneratorInterface.INLINE_FUNCTION );
  } else {
    return false;
  }
}
 
Example #3
Source File: DefaultSQLFunctionGenerator.java    From pentaho-metadata with GNU Lesser General Public License v2.1 6 votes vote down vote up
/**
 * This method may be used by child classes to verify all params are static numbers.
 * 
 * @param f
 *          function to verify
 * @throws PentahoMetadataException
 *           if params are not numbers
 */
protected void verifyAllStaticStrings( FormulaFunction f ) throws PentahoMetadataException {

  for ( int i = 0; i < f.getChildValues().length; i++ ) {
    // this checks to see if the strings are static or if they are available as parameters
    if ( ( !( f.getChildValues()[i] instanceof StaticValue ) || !( ( (StaticValue) f.getChildValues()[i] )
        .getValueType() instanceof TextType ) )
        && ( !( f.getChildValues()[i] instanceof ContextLookup ) || !( ( (ContextLookup) f.getChildValues()[i] )
            .getName().startsWith( "param:" ) ) ) ) {
      throw new PentahoMetadataException(
          Messages
              .getErrorString(
                  "PMSFormulaContext.ERROR_0004_INVALID_PARAM_TYPE_NOT_STRING", Integer.toString( i + 1 ), f.getFunctionName() ) ); //$NON-NLS-1$
    }
  }
}
 
Example #4
Source File: SqlOpenFormula.java    From pentaho-metadata with GNU Lesser General Public License v2.1 6 votes vote down vote up
/**
 * Determines whether or not child val needs to be wrapped with parens. The determining factor is if both the current
 * object and the parent are sql infix operators
 * 
 * @param parent
 *          object
 * @param val
 *          current object
 * @return true if parens are required
 */
public boolean requiresParens( Object parent, Object val ) {
  // first see if parent may required children parens
  boolean parentMatch = false;
  if ( parent instanceof Term ) {
    parentMatch = true;
  } else if ( parent instanceof FormulaFunction ) {
    FormulaFunction parentFunction = (FormulaFunction) parent;
    SQLFunctionGeneratorInterface parentGen = sqlDialect.getFunctionSQLGenerator( parentFunction.getFunctionName() );
    parentMatch = ( parentGen.getType() == SQLFunctionGeneratorInterface.INLINE_FUNCTION );
  }
  if ( !parentMatch ) {
    return false;
  }
  // second see if child needs parens
  if ( val instanceof InfixOperator ) {
    return true;
  } else if ( val instanceof FormulaFunction ) {
    FormulaFunction f = (FormulaFunction) val;
    SQLFunctionGeneratorInterface gen = sqlDialect.getFunctionSQLGenerator( f.getFunctionName() );
    return ( gen.getType() == SQLFunctionGeneratorInterface.INLINE_FUNCTION );
  } else {
    return false;
  }
}
 
Example #5
Source File: DefaultSQLDialectIT.java    From pentaho-metadata with GNU Lesser General Public License v2.1 6 votes vote down vote up
@Test
public void testTimestampType() throws PentahoMetadataException {
  Timestamp timestamp = new Timestamp( 0 );
  Calendar calendar = Calendar.getInstance( Locale.getDefault() );
  calendar.setTime( timestamp );
  SimpleDateFormat sdf = new SimpleDateFormat( "yyyy-MM-dd HH:mm:ss", Locale.getDefault() );
  String expected = '\'' + sdf.format( calendar.getTime() ) + '.' + calendar.get( Calendar.MILLISECOND ) + '\'';
  FormulaTraversalInterface formula = mock( FormulaTraversalInterface.class );
  LValue[] values = new LValue[] { new StaticValue( timestamp ) };
  FormulaFunction formulaFunction = mock( FormulaFunction.class );
  when( formulaFunction.getChildValues() ).thenReturn( values );
  StringBuffer sb = new StringBuffer();
  SQLDialectInterface dialect = new DefaultSQLDialect();
  SQLFunctionGeneratorInterface generator = dialect.getFunctionSQLGenerator( "DATEVALUE" );
  generator.generateFunctionSQL( formula, sb, Locale.getDefault().toString(), formulaFunction );
  assertEquals( expected, sb.toString() );
}
 
Example #6
Source File: DrillDownModel.java    From pentaho-reporting with GNU Lesser General Public License v2.1 5 votes vote down vote up
public boolean initializeFromFormula( final String formulaWithPrefix,
                                      final boolean formulaFragment ) {
  clear();
  if ( StringUtils.isEmpty( formulaWithPrefix, true ) == false ) {
    final String formula;
    if ( formulaFragment ) {
      formula = formulaWithPrefix;
    } else {
      formula = FormulaUtil.extractFormula( formulaWithPrefix );
    }
    try {
      final FormulaParser parser = new FormulaParser();
      final LValue value = parser.parse( formula );
      if ( value instanceof FormulaFunction ) {
        final FormulaFunction function = (FormulaFunction) value;
        if ( "DRILLDOWN".equals( function.getFunctionName() ) ) { // NON-NLS
          updateModelFromFunction( function );
          return true;
        }
      }
      DebugLog.log( "Fall through on formula " + formula ); //NON-NLS
    } catch ( Exception e ) {
      // plain value ..
      DebugLog.log( "Failed with formula " + formulaWithPrefix, e ); //NON-NLS
    }
  } else {
    DebugLog.log( "formula is empty " + formulaWithPrefix ); //NON-NLS
  }
  return false;
}
 
Example #7
Source File: DefaultSQLFunctionGenerator.java    From pentaho-metadata with GNU Lesser General Public License v2.1 5 votes vote down vote up
/**
 * default validation function verifies parameter count if necessary
 */
public void validateFunction( FormulaFunction f ) throws PentahoMetadataException {
  if ( paramCount != -1 ) {
    if ( f.getChildValues() == null || f.getChildValues().length != paramCount ) {
      throw new PentahoMetadataException( Messages.getErrorString(
          "PMSFormulaContext.ERROR_0002_INVALID_NUMBER_PARAMS", f.getFunctionName(), "" + paramCount ) ); //$NON-NLS-1$ //$NON-NLS-2$
    }
  }
}
 
Example #8
Source File: DefaultSQLFunctionGenerator.java    From pentaho-metadata with GNU Lesser General Public License v2.1 5 votes vote down vote up
/**
 * This is a utility function that may be used by child classes to verify all params are static numbers.
 * 
 * @param f
 *          function to verify
 * @throws PentahoMetadataException
 *           if params are not numbers
 */
protected void verifyAllStaticNumbers( FormulaFunction f ) throws PentahoMetadataException {

  for ( int i = 0; i < f.getChildValues().length; i++ ) {
    if ( !( f.getChildValues()[i] instanceof StaticValue )
        || !( ( (StaticValue) f.getChildValues()[i] ).getValueType() == NumberType.GENERIC_NUMBER ) ) {
      throw new PentahoMetadataException(
          Messages
              .getErrorString(
                  "PMSFormulaContext.ERROR_0003_INVALID_PARAM_TYPE_NOT_STATIC_NUMBER", Integer.toString( i + 1 ), f.getFunctionName() ) ); //$NON-NLS-1$
    }
  }
}
 
Example #9
Source File: DefaultSQLFunctionGenerator.java    From pentaho-metadata with GNU Lesser General Public License v2.1 5 votes vote down vote up
/**
 * this is the default implementation of generateFunctionSQL.
 * 
 * Note that this function is part of the formula traversal process, which is executed in PMSFormula
 * 
 * @see PMSFormula
 * 
 * @param formula
 *          the traversal instance
 * @param sb
 *          the string to append sql to
 * @param f
 *          libformula function object
 */
public void
  generateFunctionSQL( FormulaTraversalInterface formula, StringBuffer sb, String locale, FormulaFunction f )
    throws PentahoMetadataException {
  if ( type == INLINE_FUNCTION ) {
    if ( f.getChildValues() != null && f.getChildValues().length > 0 ) {
      formula.generateSQL( f, f.getChildValues()[0], sb, locale );
      if ( paramCount == 1 ) {
        sb.append( " " + getSQL() ); //$NON-NLS-1$ //$NON-NLS-2$
      } else {
        for ( int i = 1; i < f.getChildValues().length; i++ ) {
          sb.append( " " + getSQL() + " " ); //$NON-NLS-1$ //$NON-NLS-2$
          formula.generateSQL( f, f.getChildValues()[i], sb, locale );
        }
      }
    }
  } else if ( type == PARAM_FUNCTION || type == PARAM_AGG_FUNCTION ) {
    sb.append( " " + getSQL() ); //$NON-NLS-1$
    if ( parens ) {
      sb.append( "(" ); //$NON-NLS-1$
    }

    if ( f.getChildValues() != null && f.getChildValues().length > 0 ) {
      formula.generateSQL( f, f.getChildValues()[0], sb, locale );
      for ( int i = 1; i < f.getChildValues().length; i++ ) {
        sb.append( " , " ); //$NON-NLS-1$
        formula.generateSQL( f, f.getChildValues()[i], sb, locale );
      }
    }
    if ( parens ) {
      sb.append( ")" ); //$NON-NLS-1$
    }
  }
}
 
Example #10
Source File: LucidDbDialect.java    From pentaho-metadata with GNU Lesser General Public License v2.1 5 votes vote down vote up
public LucidDbDialect() {
  super( "LucidDB" ); //$NON-NLS-1$

  // Luciddb specific date functions
  supportedFunctions.put(
      "NOW", new DefaultSQLFunctionGenerator( SQLFunctionGeneratorInterface.PARAM_FUNCTION, "CURRENT_TIMESTAMP", 0 ) { //$NON-NLS-1$ //$NON-NLS-2$
        public void generateFunctionSQL( FormulaTraversalInterface formula, StringBuffer sb, String locale,
            FormulaFunction f ) throws PentahoMetadataException {
          sb.append( sql );
        }
      } );
}
 
Example #11
Source File: PostgreSQLDialect.java    From pentaho-metadata with GNU Lesser General Public License v2.1 5 votes vote down vote up
public PostgreSQLDialect( String dialectName ) {
  super( dialectName );
  // oracle specific date functions
  supportedFunctions.put(
    "NOW", new DefaultSQLFunctionGenerator( SQLFunctionGeneratorInterface.PARAM_FUNCTION, "now",
      0 ) { //$NON-NLS-1$ //$NON-NLS-2$
      public void generateFunctionSQL( FormulaTraversalInterface formula, StringBuffer sb, String locale,
                                       FormulaFunction f ) throws PentahoMetadataException {
        sb.append( sql );
      }
    } );

}
 
Example #12
Source File: DrillDownModel.java    From pentaho-reporting with GNU Lesser General Public License v2.1 4 votes vote down vote up
private void updateModelFromFunction( final FormulaFunction function ) {
  final LValue[] lValues = function.getChildValues();
  if ( lValues.length == 0 ) {
    return;
  }

  final LValue configValue = lValues[ 0 ];
  final String configText = extractStringValue( configValue );
  final String pathText;
  if ( lValues.length > 1 ) {
    final LValue pathValue = lValues[ 1 ];
    pathText = extractStringValue( pathValue );
  } else {
    pathText = null;
  }

  final DrillDownParameter[] parameters;
  if ( lValues.length == 3 ) {
    final LValue dataValue = lValues[ 2 ];
    if ( dataValue instanceof DataTable ) {
      final ArrayList<DrillDownParameter> values = new ArrayList<DrillDownParameter>();
      final DataTable paramsStaticValue = (DataTable) dataValue;
      final int colCount = paramsStaticValue.getColumnCount();
      final int rowCount = paramsStaticValue.getRowCount();
      for ( int row = 0; row < rowCount; row++ ) {
        if ( colCount == 0 ) {
          continue;
        }
        final LValue parameterNameValue = paramsStaticValue.getValueAt( row, 0 );
        final String parameterName = extractStringValue( parameterNameValue );
        final String parameterText;
        if ( colCount > 1 ) {
          final LValue parameterTextValue = paramsStaticValue.getValueAt( row, 1 );
          if ( parameterTextValue != null ) {
            parameterText = parameterTextValue.toString();
          } else {
            parameterText = null;
          }
        } else {
          parameterText = null;
        }

        if ( parameterName != null ) {
          values.add( new DrillDownParameter( parameterName, parameterText ) );
        }
      }
      parameters = values.toArray( new DrillDownParameter[ values.size() ] );
    } else {
      parameters = EMPTY_PARAMS;
    }
  } else {
    parameters = EMPTY_PARAMS;
  }

  setDrillDownConfig( configText );
  setDrillDownPath( pathText );
  setDrillDownParameter( parameters );
}
 
Example #13
Source File: PMSFormula.java    From pentaho-metadata with GNU Lesser General Public License v2.1 4 votes vote down vote up
/**
 * Recursive function that traverses the formula object model, resolves the business columns, and validates the
 * functions and operators specified.
 * 
 * 
 * 
 * @param val
 *          the root of the formula object model
 */
private void validateAndResolveObjectModel( Object val ) throws PentahoMetadataException {
  if ( val instanceof Term ) {
    Term t = (Term) val;
    validateAndResolveObjectModel( t.getHeadValue() );
    for ( int i = 0; i < t.getOperators().length; i++ ) {
      validateAndResolveObjectModel( t.getOperators()[i] );
      validateAndResolveObjectModel( t.getOperands()[i] );
    }
  } else if ( val instanceof ContextLookup ) {
    ContextLookup lookup = (ContextLookup) val;
    addField( lookup.getName() );
    // no exception, let's add the ref
    addFieldLookup( lookup );
  } else if ( val instanceof StaticValue ) {
    // everything is fine
    return;
  } else if ( val instanceof FormulaFunction ) {

    FormulaFunction f = (FormulaFunction) val;
    if ( sqlDialect.isSupportedFunction( f.getFunctionName() ) ) {
      SQLFunctionGeneratorInterface gen = sqlDialect.getFunctionSQLGenerator( f.getFunctionName() );
      gen.validateFunction( f );
      // note, if aggregator function, we should make sure it is part of the table formula vs. conditional formula
      if ( !allowAggregateFunctions && tables == null && sqlDialect.isAggregateFunction( f.getFunctionName() ) ) {
        throw new PentahoMetadataException( Messages.getErrorString(
            "PMSFormula.ERROR_0013_AGGREGATE_USAGE_ERROR", f.getFunctionName(), formulaString ) ); //$NON-NLS-1$
      }

      if ( sqlDialect.isAggregateFunction( f.getFunctionName() ) ) {
        hasAggregateFunction = true;
      }

      // validate functions parameters
      if ( f.getChildValues() != null && f.getChildValues().length > 0 ) {
        validateAndResolveObjectModel( f.getChildValues()[0] );
        for ( int i = 1; i < f.getChildValues().length; i++ ) {
          validateAndResolveObjectModel( f.getChildValues()[i] );
        }
      }
    } else {
      throw new PentahoMetadataException( Messages.getErrorString(
          "PMSFormula.ERROR_0014_FUNCTION_NOT_SUPPORTED", f.getFunctionName() ) ); //$NON-NLS-1$
    }
  } else if ( val instanceof InfixOperator ) {
    if ( sqlDialect.isSupportedInfixOperator( val.toString() ) ) {
      // everything is fine
      return;
    } else {
      throw new PentahoMetadataException( Messages.getErrorString(
          "PMSFormula.ERROR_0021_OPERATOR_NOT_SUPPORTED", val.toString() ) ); //$NON-NLS-1$
    }
  } else if ( val instanceof PrefixTerm ) {
    return;
  } else {
    throw new PentahoMetadataException( Messages.getErrorString(
        "PMSFormula.ERROR_0016_CLASS_TYPE_NOT_SUPPORTED", val.getClass().toString() ) ); //$NON-NLS-1$
  }
}
 
Example #14
Source File: SqlOpenFormula.java    From pentaho-metadata with GNU Lesser General Public License v2.1 4 votes vote down vote up
/**
 * Recursive function that traverses the formula object model, resolves the business columns, and validates the
 * functions and operators specified.
 * 
 * 
 * 
 * @param val
 *          the root of the formula object model
 */
private void validateAndResolveObjectModel( Object val ) throws PentahoMetadataException {
  if ( val instanceof Term ) {
    Term t = (Term) val;
    validateAndResolveObjectModel( t.getHeadValue() );
    for ( int i = 0; i < t.getOperators().length; i++ ) {
      validateAndResolveObjectModel( t.getOperators()[i] );

      if ( t.getOperands()[i] instanceof ContextLookup ) {
        if ( paramContainsMultipleValues( (ContextLookup) t.getOperands()[i] ) ) {
          // no infix operators support multi-valued parameters
          throw new PentahoMetadataException( Messages.getErrorString(
              "SqlOpenFormula.ERROR_0024_MULTIPLE_VALUES_NOT_SUPPORTED", t.getOperators()[i].toString() ) ); //$NON-NLS-1$
        }
      }
      validateAndResolveObjectModel( t.getOperands()[i] );
    }
  } else if ( val instanceof ContextLookup ) {
    ContextLookup l = (ContextLookup) val;
    addField( l.getName() );
  } else if ( val instanceof StaticValue ) {
    // everything is fine
    return;
  } else if ( val instanceof FormulaFunction ) {

    FormulaFunction f = (FormulaFunction) val;
    if ( sqlDialect.isSupportedFunction( f.getFunctionName() ) ) {
      SQLFunctionGeneratorInterface gen = sqlDialect.getFunctionSQLGenerator( f.getFunctionName() );
      gen.validateFunction( f );

      // note, if aggregator function, we should make sure it is part of the table formula vs. conditional formula
      if ( !allowAggregateFunctions && tables == null && sqlDialect.isAggregateFunction( f.getFunctionName() ) ) {
        throw new PentahoMetadataException( Messages.getErrorString(
            "SqlOpenFormula.ERROR_0013_AGGREGATE_USAGE_ERROR", f.getFunctionName(), formulaString ) ); //$NON-NLS-1$
      }

      if ( sqlDialect.isAggregateFunction( f.getFunctionName() ) ) {
        hasAggregateFunction = true;
      }

      // validate functions parameters
      if ( f.getChildValues() != null && f.getChildValues().length > 0 ) {
        validateAndResolveObjectModel( f.getChildValues()[0] );

        for ( int i = 1; i < f.getChildValues().length; i++ ) {
          if ( f.getChildValues()[i] instanceof ContextLookup ) {
            if ( paramContainsMultipleValues( (ContextLookup) f.getChildValues()[i] )
                && !gen.isMultiValuedParamAware() ) {
              throw new PentahoMetadataException( Messages.getErrorString(
                  "SqlOpenFormula.ERROR_0024_MULTIPLE_VALUES_NOT_SUPPORTED", f.getFunctionName() ) ); //$NON-NLS-1$
            }
          }
          validateAndResolveObjectModel( f.getChildValues()[i] );
        }
      }
    } else {
      throw new PentahoMetadataException( Messages.getErrorString(
          "SqlOpenFormula.ERROR_0014_FUNCTION_NOT_SUPPORTED", f.getFunctionName() ) ); //$NON-NLS-1$
    }
  } else if ( val instanceof InfixOperator ) {
    if ( sqlDialect.isSupportedInfixOperator( val.toString() ) ) {
      // everything is fine
      return;
    } else {
      throw new PentahoMetadataException( Messages.getErrorString(
          "SqlOpenFormula.ERROR_0021_OPERATOR_NOT_SUPPORTED", val.toString() ) ); //$NON-NLS-1$
    }
  } else if ( val instanceof PrefixTerm ) {
    return;
  } else {
    throw new PentahoMetadataException( Messages.getErrorString(
        "SqlOpenFormula.ERROR_0016_CLASS_TYPE_NOT_SUPPORTED", val.getClass().toString() ) ); //$NON-NLS-1$
  }
}
 
Example #15
Source File: SQLFunctionGeneratorInterface.java    From pentaho-metadata with GNU Lesser General Public License v2.1 2 votes vote down vote up
/**
 * this is called during the validation phase of the PMSFormula throws a formula exception if there is a validation
 * problem.
 */
public void validateFunction( FormulaFunction f ) throws PentahoMetadataException;
 
Example #16
Source File: SQLFunctionGeneratorInterface.java    From pentaho-metadata with GNU Lesser General Public License v2.1 2 votes vote down vote up
/**
 * This method manages the generation of the SQL for a specific function.
 * 
 * @param formula
 * @param sb
 * @param locale
 * @param f
 */
public void
  generateFunctionSQL( FormulaTraversalInterface formula, StringBuffer sb, String locale, FormulaFunction f )
    throws PentahoMetadataException;