/*! ****************************************************************************** * * Pentaho Data Integration * * Copyright (C) 2002-2015 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.ui.spoon.delegates; import java.util.ArrayList; import java.util.List; import org.eclipse.swt.dnd.DND; import org.eclipse.swt.dnd.DragSource; import org.eclipse.swt.dnd.DragSourceEvent; import org.eclipse.swt.dnd.DragSourceListener; import org.eclipse.swt.dnd.Transfer; import org.eclipse.swt.widgets.Tree; import org.eclipse.swt.widgets.TreeItem; import org.pentaho.di.cluster.ClusterSchema; import org.pentaho.di.cluster.SlaveServer; import org.pentaho.di.core.Const; import org.pentaho.di.core.database.DatabaseMeta; import org.pentaho.di.core.dnd.DragAndDropContainer; import org.pentaho.di.core.dnd.XMLTransfer; import org.pentaho.di.core.extension.ExtensionPointHandler; import org.pentaho.di.core.extension.KettleExtensionPoint; import org.pentaho.di.core.plugins.JobEntryPluginType; import org.pentaho.di.core.plugins.PluginInterface; import org.pentaho.di.core.plugins.PluginRegistry; import org.pentaho.di.core.plugins.PluginTypeInterface; import org.pentaho.di.core.plugins.StepPluginType; import org.pentaho.di.job.JobMeta; import org.pentaho.di.job.entry.JobEntryCopy; import org.pentaho.di.partition.PartitionSchema; import org.pentaho.di.trans.TransHopMeta; import org.pentaho.di.trans.TransMeta; import org.pentaho.di.trans.step.StepMeta; import org.pentaho.di.ui.core.ConstUI; import org.pentaho.di.ui.spoon.Spoon; import org.pentaho.di.ui.spoon.TreeSelection; public class SpoonTreeDelegate extends SpoonDelegate { public SpoonTreeDelegate( Spoon spoon ) { super( spoon ); } /** * @return The object that is selected in the tree or null if we couldn't figure it out. (titles etc. == null) */ public TreeSelection[] getTreeObjects( final Tree tree, Tree selectionTree, Tree coreObjectsTree ) { List<TreeSelection> objects = new ArrayList<TreeSelection>(); if ( selectionTree != null && !selectionTree.isDisposed() && tree.equals( selectionTree ) ) { TreeItem[] selection = selectionTree.getSelection(); for ( int s = 0; s < selection.length; s++ ) { TreeItem treeItem = selection[s]; String[] path = ConstUI.getTreeStrings( treeItem ); TreeSelection object = null; switch ( path.length ) { case 0: break; case 1: // ------complete----- if ( path[0].equals( Spoon.STRING_TRANSFORMATIONS ) ) { // the top level Transformations entry object = new TreeSelection( path[0], TransMeta.class ); } if ( path[0].equals( Spoon.STRING_JOBS ) ) { // the top level Jobs entry object = new TreeSelection( path[0], JobMeta.class ); } break; case 2: // ------complete----- if ( path[0].equals( Spoon.STRING_BUILDING_BLOCKS ) ) { // the top level Transformations entry if ( path[1].equals( Spoon.STRING_TRANS_BASE ) ) { object = new TreeSelection( path[1], PluginInterface.class ); } } if ( path[0].equals( Spoon.STRING_TRANSFORMATIONS ) ) { // Transformation title object = new TreeSelection( path[1], spoon.delegates.trans.getTransformation( path[1] ) ); } if ( path[0].equals( Spoon.STRING_JOBS ) ) { // Jobs title object = new TreeSelection( path[1], spoon.delegates.jobs.getJob( path[1] ) ); } break; case 3: // ------complete----- if ( path[0].equals( Spoon.STRING_TRANSFORMATIONS ) ) { // Transformations title TransMeta transMeta = spoon.delegates.trans.getTransformation( path[1] ); if ( path[2].equals( Spoon.STRING_CONNECTIONS ) ) { object = new TreeSelection( path[2], DatabaseMeta.class, transMeta ); } if ( path[2].equals( Spoon.STRING_STEPS ) ) { object = new TreeSelection( path[2], StepMeta.class, transMeta ); } if ( path[2].equals( Spoon.STRING_HOPS ) ) { object = new TreeSelection( path[2], TransHopMeta.class, transMeta ); } if ( path[2].equals( Spoon.STRING_PARTITIONS ) ) { object = new TreeSelection( path[2], PartitionSchema.class, transMeta ); } if ( path[2].equals( Spoon.STRING_SLAVES ) ) { object = new TreeSelection( path[2], SlaveServer.class, transMeta ); } if ( path[2].equals( Spoon.STRING_CLUSTERS ) ) { object = new TreeSelection( path[2], ClusterSchema.class, transMeta ); } executeExtensionPoint( new SpoonTreeDelegateExtension( transMeta, path, 3, objects ) ); } if ( path[0].equals( Spoon.STRING_JOBS ) ) { // Jobs title JobMeta jobMeta = spoon.delegates.jobs.getJob( path[1] ); if ( path[2].equals( Spoon.STRING_CONNECTIONS ) ) { object = new TreeSelection( path[2], DatabaseMeta.class, jobMeta ); } if ( path[2].equals( Spoon.STRING_JOB_ENTRIES ) ) { object = new TreeSelection( path[2], JobEntryCopy.class, jobMeta ); } if ( path[2].equals( Spoon.STRING_SLAVES ) ) { object = new TreeSelection( path[2], SlaveServer.class, jobMeta ); } executeExtensionPoint( new SpoonTreeDelegateExtension( jobMeta, path, 3, objects ) ); } break; case 4: // ------complete----- if ( path[0].equals( Spoon.STRING_TRANSFORMATIONS ) ) { // The name of a transformation final TransMeta transMeta = spoon.delegates.trans.getTransformation( path[1] ); if ( transMeta != null ) { if ( path[2].equals( Spoon.STRING_CONNECTIONS ) ) { String dbName = path[3]; DatabaseMeta databaseMeta = transMeta.findDatabase( dbName ); if ( databaseMeta != null ) { dbName = databaseMeta.getName(); } object = new TreeSelection( dbName, databaseMeta, transMeta ); } if ( path[2].equals( Spoon.STRING_STEPS ) ) { object = new TreeSelection( path[3], transMeta.findStep( path[3] ), transMeta ); } if ( path[2].equals( Spoon.STRING_HOPS ) ) { object = new TreeSelection( path[3], transMeta.findTransHop( path[3] ), transMeta ); } if ( path[2].equals( Spoon.STRING_PARTITIONS ) ) { object = new TreeSelection( path[3], transMeta.findPartitionSchema( path[3] ), transMeta ); } if ( path[2].equals( Spoon.STRING_SLAVES ) ) { object = new TreeSelection( path[3], transMeta.findSlaveServer( path[3] ), transMeta ); } if ( path[2].equals( Spoon.STRING_CLUSTERS ) ) { object = new TreeSelection( path[3], transMeta.findClusterSchema( path[3] ), transMeta ); } executeExtensionPoint( new SpoonTreeDelegateExtension( transMeta, path, 4, objects ) ); } } if ( path[0].equals( Spoon.STRING_JOBS ) ) { // The name of a job JobMeta jobMeta = spoon.delegates.jobs.getJob( path[1] ); if ( jobMeta != null && path[2].equals( Spoon.STRING_CONNECTIONS ) ) { String dbName = path[3]; DatabaseMeta databaseMeta = jobMeta.findDatabase( dbName ); if ( databaseMeta != null ) { dbName = databaseMeta.getName(); } object = new TreeSelection( dbName, databaseMeta, jobMeta ); } if ( jobMeta != null && path[2].equals( Spoon.STRING_JOB_ENTRIES ) ) { object = new TreeSelection( path[3], jobMeta.findJobEntry( path[3] ), jobMeta ); } if ( jobMeta != null && path[2].equals( Spoon.STRING_SLAVES ) ) { object = new TreeSelection( path[3], jobMeta.findSlaveServer( path[3] ), jobMeta ); } executeExtensionPoint( new SpoonTreeDelegateExtension( jobMeta, path, 4, objects ) ); } break; case 5: if ( path[0].equals( Spoon.STRING_TRANSFORMATIONS ) ) { // The name of a transformation TransMeta transMeta = spoon.delegates.trans.getTransformation( path[1] ); if ( transMeta != null && path[2].equals( Spoon.STRING_CLUSTERS ) ) { ClusterSchema clusterSchema = transMeta.findClusterSchema( path[3] ); object = new TreeSelection( path[4], clusterSchema.findSlaveServer( path[4] ), clusterSchema, transMeta ); } } break; default: break; } if ( object != null ) { objects.add( object ); } } } if ( tree != null && coreObjectsTree != null && tree.equals( coreObjectsTree ) ) { TreeItem[] selection = coreObjectsTree.getSelection(); for ( int s = 0; s < selection.length; s++ ) { TreeItem treeItem = selection[s]; String[] path = ConstUI.getTreeStrings( treeItem ); TreeSelection object = null; switch ( path.length ) { case 0: break; case 2: // Job entries if ( spoon.showJob ) { PluginRegistry registry = PluginRegistry.getInstance(); Class<? extends PluginTypeInterface> pluginType = JobEntryPluginType.class; PluginInterface plugin = registry.findPluginWithName( pluginType, path[1] ); // Retry for Start // if ( plugin == null ) { if ( path[1].equals( JobMeta.STRING_SPECIAL_START ) ) { plugin = registry.findPluginWithId( pluginType, JobMeta.STRING_SPECIAL ); } } // Retry for Dummy // if ( plugin == null ) { if ( path[1].equals( JobMeta.STRING_SPECIAL_DUMMY ) ) { plugin = registry.findPluginWithId( pluginType, JobMeta.STRING_SPECIAL ); } } if ( plugin != null ) { object = new TreeSelection( path[1], plugin ); } } if ( spoon.showTrans ) { // Steps object = new TreeSelection( path[1], PluginRegistry.getInstance().findPluginWithName( StepPluginType.class, path[1] ) ); } break; default: break; } if ( object != null ) { objects.add( object ); } } } return objects.toArray( new TreeSelection[objects.size()] ); } public void addDragSourceToTree( final Tree tree, final Tree selectionTree, final Tree coreObjectsTree ) { // Drag & Drop for steps Transfer[] ttypes = new Transfer[] { XMLTransfer.getInstance() }; DragSource ddSource = new DragSource( tree, DND.DROP_MOVE ); ddSource.setTransfer( ttypes ); ddSource.addDragListener( new DragSourceListener() { public void dragStart( DragSourceEvent event ) { TreeSelection[] treeObjects = getTreeObjects( tree, selectionTree, coreObjectsTree ); if ( treeObjects.length == 0 ) { event.doit = false; return; } spoon.hideToolTips(); TreeSelection treeObject = treeObjects[0]; Object object = treeObject.getSelection(); TransMeta transMeta = spoon.getActiveTransformation(); // JobMeta jobMeta = spoon.getActiveJob(); if ( object instanceof StepMeta || object instanceof PluginInterface || ( object instanceof DatabaseMeta && transMeta != null ) || object instanceof TransHopMeta || object instanceof JobEntryCopy ) { event.doit = true; } else { event.doit = false; } } public void dragSetData( DragSourceEvent event ) { TreeSelection[] treeObjects = getTreeObjects( tree, selectionTree, coreObjectsTree ); if ( treeObjects.length == 0 ) { event.doit = false; return; } int type = 0; String data = null; TreeSelection treeObject = treeObjects[0]; Object object = treeObject.getSelection(); if ( object instanceof StepMeta ) { StepMeta stepMeta = (StepMeta) object; type = DragAndDropContainer.TYPE_STEP; data = stepMeta.getName(); // name of the step. } else if ( object instanceof PluginInterface ) { PluginInterface plugin = (PluginInterface) object; Class<? extends PluginTypeInterface> pluginType = plugin.getPluginType(); if ( Const.classIsOrExtends( pluginType, StepPluginType.class ) ) { type = DragAndDropContainer.TYPE_BASE_STEP_TYPE; data = plugin.getName(); // Step type name } else { type = DragAndDropContainer.TYPE_BASE_JOB_ENTRY; data = plugin.getName(); // job entry type name if ( treeObject.getItemText().equals( JobMeta.createStartEntry().getName() ) ) { data = treeObject.getItemText(); } else if ( treeObject.getItemText().equals( JobMeta.createDummyEntry().getName() ) ) { data = treeObject.getItemText(); } } } else if ( object instanceof DatabaseMeta ) { DatabaseMeta databaseMeta = (DatabaseMeta) object; type = DragAndDropContainer.TYPE_DATABASE_CONNECTION; data = databaseMeta.getName(); } else if ( object instanceof TransHopMeta ) { TransHopMeta hop = (TransHopMeta) object; type = DragAndDropContainer.TYPE_TRANS_HOP; data = hop.toString(); // nothing for really ;-) } else if ( object instanceof JobEntryCopy ) { JobEntryCopy jobEntryCopy = (JobEntryCopy) object; type = DragAndDropContainer.TYPE_JOB_ENTRY; data = jobEntryCopy.getName(); // name of the job entry. } else { event.doit = false; return; // ignore anything else you drag. } event.data = new DragAndDropContainer( type, data ); } public void dragFinished( DragSourceEvent event ) { } } ); } private void executeExtensionPoint( SpoonTreeDelegateExtension extension ) { try { ExtensionPointHandler .callExtensionPoint( log, KettleExtensionPoint.SpoonTreeDelegateExtension.id, extension ); } catch ( Exception e ) { log.logError( "Error handling SpoonTreeDelegate through extension point", e ); } } }