/*! ****************************************************************************** * * Pentaho Data Integration * * Copyright (C) 2002-2013 by Pentaho : http://www.pentaho.com * ******************************************************************************* * * 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 org.pentaho.di.trans.steps.terafast; import java.util.List; import org.apache.commons.lang.StringUtils; import org.pentaho.di.core.CheckResult; import org.pentaho.di.core.CheckResultInterface; import org.pentaho.di.core.database.Database; import org.pentaho.di.core.exception.KettleDatabaseException; import org.pentaho.di.core.exception.KettleException; import org.pentaho.di.core.exception.KettleStepException; import org.pentaho.di.core.row.RowMetaInterface; import org.pentaho.di.core.util.AbstractStepMeta; import org.pentaho.di.core.util.BooleanPluginProperty; import org.pentaho.di.core.util.GenericStepData; import org.pentaho.di.core.util.IntegerPluginProperty; import org.pentaho.di.core.util.PluginMessages; import org.pentaho.di.core.util.StringListPluginProperty; import org.pentaho.di.core.util.StringPluginProperty; import org.pentaho.di.core.variables.VariableSpace; import org.pentaho.di.repository.Repository; import org.pentaho.di.trans.Trans; import org.pentaho.di.trans.TransMeta; import org.pentaho.di.trans.step.StepDataInterface; import org.pentaho.di.trans.step.StepInterface; import org.pentaho.di.trans.step.StepMeta; import org.pentaho.metastore.api.IMetaStore; /** * @author <a href="mailto:michael.gugerell@aschauer-edv.at">Michael Gugerell(asc145)</a> * */ public class TeraFastMeta extends AbstractStepMeta { public static final PluginMessages MESSAGES = PluginMessages.getMessages( TeraFastMeta.class ); /** * Default fast load path. */ public static final String DEFAULT_FASTLOAD_PATH = "/usr/bin/fastload"; /** * Default data file. */ public static final String DEFAULT_DATA_FILE = "${Internal.Step.CopyNr}.dat"; public static final String DEFAULT_TARGET_TABLE = "${TARGET_TABLE}_${RUN_ID}"; /** * Default session. */ public static final int DEFAULT_SESSIONS = 2; public static final boolean DEFAULT_TRUNCATETABLE = true; public static final boolean DEFAULT_VARIABLE_SUBSTITUTION = true; /** * Default error limit. */ public static final int DEFAULT_ERROR_LIMIT = 25; /* custom xml values */ private static final String FASTLOADPATH = "fastload_path"; private static final String CONTROLFILE = "controlfile_path"; private static final String DATAFILE = "datafile_path"; private static final String LOGFILE = "logfile_path"; private static final String SESSIONS = "sessions"; private static final String ERRORLIMIT = "error_limit"; private static final String USECONTROLFILE = "use_control_file"; private static final String TARGETTABLE = "target_table"; private static final String TRUNCATETABLE = "truncate_table"; private static final String TABLE_FIELD_LIST = "table_field_list"; private static final String STREAM_FIELD_LIST = "stream_field_list"; private static final String VARIABLE_SUBSTITUTION = "variable_substitution"; /** available options. **/ private StringPluginProperty fastloadPath; private StringPluginProperty controlFile; private StringPluginProperty dataFile; private StringPluginProperty logFile; private IntegerPluginProperty sessions; private IntegerPluginProperty errorLimit; private BooleanPluginProperty useControlFile; private BooleanPluginProperty variableSubstitution; private BooleanPluginProperty truncateTable; private StringPluginProperty targetTable; private StringListPluginProperty tableFieldList; private StringListPluginProperty streamFieldList; /** * */ public TeraFastMeta() { super(); this.fastloadPath = this.getPropertyFactory().createString( FASTLOADPATH ); this.controlFile = this.getPropertyFactory().createString( CONTROLFILE ); this.dataFile = this.getPropertyFactory().createString( DATAFILE ); this.logFile = this.getPropertyFactory().createString( LOGFILE ); this.sessions = this.getPropertyFactory().createInteger( SESSIONS ); this.errorLimit = this.getPropertyFactory().createInteger( ERRORLIMIT ); this.targetTable = this.getPropertyFactory().createString( TARGETTABLE ); this.useControlFile = this.getPropertyFactory().createBoolean( USECONTROLFILE ); this.truncateTable = this.getPropertyFactory().createBoolean( TRUNCATETABLE ); this.tableFieldList = this.getPropertyFactory().createStringList( TABLE_FIELD_LIST ); this.streamFieldList = this.getPropertyFactory().createStringList( STREAM_FIELD_LIST ); this.variableSubstitution = this.getPropertyFactory().createBoolean( VARIABLE_SUBSTITUTION ); } /** * {@inheritDoc} * * @see org.pentaho.di.trans.step.StepMetaInterface#check(java.util.List, org.pentaho.di.trans.TransMeta, * org.pentaho.di.trans.step.StepMeta, org.pentaho.di.core.row.RowMetaInterface, java.lang.String[], * java.lang.String[], org.pentaho.di.core.row.RowMetaInterface) */ public void check( final List<CheckResultInterface> remarks, final TransMeta transmeta, final StepMeta stepMeta, final RowMetaInterface prev, final String[] input, final String[] output, final RowMetaInterface info, VariableSpace space, Repository repository, IMetaStore metaStore ) { CheckResult checkResult; try { RowMetaInterface tableFields = getRequiredFields( transmeta ); checkResult = new CheckResult( CheckResultInterface.TYPE_RESULT_OK, MESSAGES .getString( "TeraFastMeta.Message.ConnectionEstablished" ), stepMeta ); remarks.add( checkResult ); checkResult = new CheckResult( CheckResultInterface.TYPE_RESULT_OK, MESSAGES .getString( "TeraFastMeta.Message.TableExists" ), stepMeta ); remarks.add( checkResult ); boolean error = false; for ( String field : this.tableFieldList.getValue() ) { if ( tableFields.searchValueMeta( field ) == null ) { error = true; checkResult = new CheckResult( CheckResultInterface.TYPE_RESULT_ERROR, MESSAGES .getString( "TeraFastMeta.Exception.TableFieldNotFound" ), stepMeta ); remarks.add( checkResult ); } } if ( !error ) { checkResult = new CheckResult( CheckResultInterface.TYPE_RESULT_OK, MESSAGES .getString( "TeraFastMeta.Message.AllTableFieldsFound" ), stepMeta ); remarks.add( checkResult ); } if ( prev != null && prev.size() > 0 ) { // step mode. step receiving input checkResult = new CheckResult( CheckResultInterface.TYPE_RESULT_OK, MESSAGES .getString( "TeraFastMeta.Message.StepInputDataFound" ), stepMeta ); remarks.add( checkResult ); error = false; for ( String field : this.streamFieldList.getValue() ) { if ( prev.searchValueMeta( field ) == null ) { error = true; checkResult = new CheckResult( CheckResultInterface.TYPE_RESULT_ERROR, MESSAGES .getString( "TeraFastMeta.Exception.StreamFieldNotFound" ), stepMeta ); remarks.add( checkResult ); } } if ( !error ) { checkResult = new CheckResult( CheckResultInterface.TYPE_RESULT_OK, MESSAGES .getString( "TeraFastMeta.Message.AllStreamFieldsFound" ), stepMeta ); remarks.add( checkResult ); } } // else { job mode. no input rows. pentaho doesn't seem to allow to check jobs. Default Warning: Step is not // in transformation. } catch ( KettleDatabaseException e ) { checkResult = new CheckResult( CheckResultInterface.TYPE_RESULT_ERROR, MESSAGES .getString( "TeraFastMeta.Exception.ConnectionFailed" ), stepMeta ); remarks.add( checkResult ); } catch ( KettleException e ) { checkResult = new CheckResult( CheckResultInterface.TYPE_RESULT_ERROR, e.getMessage(), stepMeta ); remarks.add( checkResult ); } } /** * @param space * the variableSpace to be used. * @return the quoted and resolved schema table name. * @throws KettleException * if no table specified. */ public String getQuotedSchemaTableName( final VariableSpace space ) throws KettleException { final String realTableName = space.environmentSubstitute( this.targetTable.getValue() ); if ( StringUtils.isEmpty( realTableName ) ) { throw new KettleException( MESSAGES.getString( "TeraFastMeta.Exception.TableNotSpecified" ) ); } return this.getDbMeta().getQuotedSchemaTableCombination( StringUtils.EMPTY, realTableName ); } /** * @return the database. * @throws KettleException * if an error occurs. */ public Database connectToDatabase() throws KettleException { if ( this.getDbMeta() != null ) { Database db = new Database( loggingObject, this.getDbMeta() ); db.connect(); return db; } throw new KettleException( MESSAGES.getString( "TeraFastMeta.Exception.ConnectionNotDefined" ) ); } /** * {@inheritDoc} * * @see org.pentaho.di.trans.step.StepMetaInterface#getStep(org.pentaho.di.trans.step.StepMeta, * org.pentaho.di.trans.step.StepDataInterface, int, org.pentaho.di.trans.TransMeta, org.pentaho.di.trans.Trans) */ public StepInterface getStep( final StepMeta stepMeta, final StepDataInterface stepDataInterface, final int cnr, final TransMeta transMeta, final Trans disp ) { return new TeraFast( stepMeta, stepDataInterface, cnr, transMeta, disp ); } /** * {@inheritDoc} * * @see org.pentaho.di.trans.step.StepMetaInterface#getStepData() */ @Override public StepDataInterface getStepData() { return new GenericStepData(); } /** * {@inheritDoc} * * @see org.pentaho.di.trans.step.StepMetaInterface#setDefault() */ public void setDefault() { this.fastloadPath.setValue( DEFAULT_FASTLOAD_PATH ); this.dataFile.setValue( DEFAULT_DATA_FILE ); this.sessions.setValue( DEFAULT_SESSIONS ); this.errorLimit.setValue( DEFAULT_ERROR_LIMIT ); this.truncateTable.setValue( DEFAULT_TRUNCATETABLE ); this.variableSubstitution.setValue( DEFAULT_VARIABLE_SUBSTITUTION ); this.targetTable.setValue( DEFAULT_TARGET_TABLE ); this.useControlFile.setValue( true ); } /** * {@inheritDoc} * * @see org.pentaho.di.trans.step.BaseStepMeta#getFields(org.pentaho.di.core.row.RowMetaInterface, java.lang.String, * org.pentaho.di.core.row.RowMetaInterface[], org.pentaho.di.trans.step.StepMeta, * org.pentaho.di.core.variables.VariableSpace) */ @Override public void getFields( final RowMetaInterface inputRowMeta, final String name, final RowMetaInterface[] info, final StepMeta nextStep, final VariableSpace space, Repository repository, IMetaStore metaStore ) throws KettleStepException { // Default: nothing changes to rowMeta } /** * {@inheritDoc} * * @see org.pentaho.di.trans.step.BaseStepMeta#getRequiredFields(org.pentaho.di.core.variables.VariableSpace) */ @Override public RowMetaInterface getRequiredFields( final VariableSpace space ) throws KettleException { if ( !this.useControlFile.getValue() ) { final Database database = connectToDatabase(); database.shareVariablesWith( space ); final String schemaTable = getQuotedSchemaTableName( space ); RowMetaInterface fields = database.getTableFields( schemaTable ); database.disconnect(); if ( fields == null ) { throw new KettleException( MESSAGES.getString( "TeraFastMeta.Exception.TableNotFound" ) ); } return fields; } return null; } /** * {@inheritDoc} * * @see org.pentaho.di.trans.step.BaseStepMeta#clone() */ @Override public Object clone() { return super.clone(); } /** * @return the fastloadPath */ public StringPluginProperty getFastloadPath() { return this.fastloadPath; } /** * @param fastloadPath * the fastloadPath to set */ public void setFastloadPath( final StringPluginProperty fastloadPath ) { this.fastloadPath = fastloadPath; } /** * @return the controlFile */ public StringPluginProperty getControlFile() { return this.controlFile; } /** * @param controlFile * the controlFile to set */ public void setControlFile( final StringPluginProperty controlFile ) { this.controlFile = controlFile; } /** * @return the dataFile */ public StringPluginProperty getDataFile() { return this.dataFile; } /** * @param dataFile * the dataFile to set */ public void setDataFile( final StringPluginProperty dataFile ) { this.dataFile = dataFile; } /** * @return the logFile */ public StringPluginProperty getLogFile() { return this.logFile; } /** * @param logFile * the logFile to set */ public void setLogFile( final StringPluginProperty logFile ) { this.logFile = logFile; } /** * @return the sessions */ public IntegerPluginProperty getSessions() { return this.sessions; } /** * @param sessions * the sessions to set */ public void setSessions( final IntegerPluginProperty sessions ) { this.sessions = sessions; } /** * @return the errorLimit */ public IntegerPluginProperty getErrorLimit() { return this.errorLimit; } /** * @param errorLimit * the errorLimit to set */ public void setErrorLimit( final IntegerPluginProperty errorLimit ) { this.errorLimit = errorLimit; } /** * @return the useControlFile */ public BooleanPluginProperty getUseControlFile() { return this.useControlFile; } /** * @param useControlFile * the useControlFile to set */ public void setUseControlFile( final BooleanPluginProperty useControlFile ) { this.useControlFile = useControlFile; } /** * @return the targetTable */ public StringPluginProperty getTargetTable() { return this.targetTable; } /** * @param targetTable * the targetTable to set */ public void setTargetTable( final StringPluginProperty targetTable ) { this.targetTable = targetTable; } /** * @return the truncateTable */ public BooleanPluginProperty getTruncateTable() { return this.truncateTable; } /** * @param truncateTable * the truncateTable to set */ public void setTruncateTable( final BooleanPluginProperty truncateTable ) { this.truncateTable = truncateTable; } /** * @return the tableFieldList */ public StringListPluginProperty getTableFieldList() { return this.tableFieldList; } /** * @param tableFieldList * the tableFieldList to set */ public void setTableFieldList( final StringListPluginProperty tableFieldList ) { this.tableFieldList = tableFieldList; } /** * @return the streamFieldList */ public StringListPluginProperty getStreamFieldList() { return this.streamFieldList; } /** * @param streamFieldList * the streamFieldList to set */ public void setStreamFieldList( final StringListPluginProperty streamFieldList ) { this.streamFieldList = streamFieldList; } /** * @return the variableSubstitution */ public BooleanPluginProperty getVariableSubstitution() { return this.variableSubstitution; } /** * @param variableSubstitution * the variableSubstitution to set */ public void setVariableSubstitution( BooleanPluginProperty variableSubstitution ) { this.variableSubstitution = variableSubstitution; } }