// ============================================================================ // // Copyright (C) 2006-2016 Talend Inc. - www.talend.com // // This source code is available under agreement available at // %InstallDIR%\features\org.talend.rcp.branding.%PRODUCTNAME%\%PRODUCTNAME%license.txt // // You should have received a copy of the agreement // along with this program; if not, write to Talend SA // 9 rue Pages 92150 Suresnes, France // // ============================================================================ package org.talend.dataprofiler.core.ui.action.actions; import java.lang.reflect.InvocationTargetException; import java.util.List; import java.util.Map; import org.apache.log4j.Logger; import org.eclipse.core.runtime.IProgressMonitor; import org.eclipse.emf.common.util.EList; import org.eclipse.jface.action.Action; import org.eclipse.jface.dialogs.MessageDialog; import org.eclipse.jface.operation.IRunnableWithProgress; import org.eclipse.jface.window.Window; import org.eclipse.swt.widgets.Shell; import org.eclipse.ui.PlatformUI; import org.eclipse.ui.cheatsheets.ICheatSheetAction; import org.eclipse.ui.cheatsheets.ICheatSheetManager; import org.talend.core.model.metadata.builder.connection.Connection; import org.talend.core.model.metadata.builder.connection.DelimitedFileConnection; import org.talend.core.model.properties.ConnectionItem; import org.talend.cwm.compare.exception.ReloadCompareException; import org.talend.cwm.compare.factory.ComparisonLevelFactory; import org.talend.cwm.compare.factory.IComparisonLevel; import org.talend.cwm.dependencies.DependenciesHandler; import org.talend.cwm.helper.ColumnHelper; import org.talend.cwm.relational.TdColumn; import org.talend.dataprofiler.core.CorePlugin; import org.talend.dataprofiler.core.helper.FolderNodeHelper; import org.talend.dataprofiler.core.i18n.internal.DefaultMessagesImpl; import org.talend.dataprofiler.core.ui.action.CheatSheetActionHelper; import org.talend.dataprofiler.core.ui.dialog.AnalyzedColumnSetsSynDialog; import org.talend.dataprofiler.core.ui.dialog.AnalyzedColumnsSynDialog; import org.talend.dataprofiler.core.ui.dialog.AnalyzedElementSynDialog; import org.talend.dataprofiler.core.ui.dialog.AnalyzedElementSynDialog.SynTreeModel; import org.talend.dataprofiler.core.ui.dialog.AnalyzedPackageSynDialog; import org.talend.dataprofiler.core.ui.editor.analysis.AbstractAnalysisMetadataPage; import org.talend.dataprofiler.core.ui.progress.ProgressUI; import org.talend.dataquality.PluginConstant; import org.talend.dataquality.analysis.Analysis; import org.talend.dataquality.analysis.AnalysisType; import org.talend.dataquality.helpers.MetadataHelper; import org.talend.dataquality.indicators.DataminingType; import org.talend.dataquality.indicators.Indicator; import org.talend.dataquality.indicators.columnset.ColumnDependencyIndicator; import org.talend.dataquality.indicators.columnset.ColumnSetMultiValueIndicator; import org.talend.dataquality.indicators.columnset.ColumnsCompareIndicator; import org.talend.dataquality.properties.TDQAnalysisItem; import org.talend.dq.analysis.AnalysisBuilder; import org.talend.dq.helper.RepositoryNodeHelper; import org.talend.dq.nodes.DBConnectionRepNode; import org.talend.dq.nodes.DFConnectionRepNode; import org.talend.dq.nodes.foldernode.IFolderNode; import org.talend.dq.writer.impl.ElementWriterFactory; import org.talend.repository.model.RepositoryNode; import org.talend.resource.EResourceConstant; import org.talend.utils.sugars.ReturnCode; import orgomg.cwm.objectmodel.core.ModelElement; import orgomg.cwm.objectmodel.core.Package; import orgomg.cwm.resource.relational.ColumnSet; /** * DOC mzhao class global comment. Detailled comment */ public class ChangeConnectionAction extends Action implements ICheatSheetAction { private static Logger log = Logger.getLogger(ChangeConnectionAction.class); private Connection oldDataProvider; private Connection newDataProvider; private TDQAnalysisItem analysisItem = null; private AnalyzedElementSynDialog anaEleSynDialog = null; private ReturnCode changeActionStatus; public ChangeConnectionAction(AbstractAnalysisMetadataPage masterPage, Connection tdProvider) { Object connectionObj = masterPage.getConnCombo().getData( masterPage.getConnCombo().getSelectionIndex() + PluginConstant.EMPTY_STRING); if (connectionObj instanceof DBConnectionRepNode || connectionObj instanceof DFConnectionRepNode) { this.newDataProvider = ((ConnectionItem) (((RepositoryNode) connectionObj).getObject().getProperty().getItem())) .getConnection(); } else { this.newDataProvider = (Connection) connectionObj; } this.oldDataProvider = tdProvider; this.analysisItem = (TDQAnalysisItem) masterPage.getCurrentRepNode().getObject().getProperty().getItem(); this.changeActionStatus = new ReturnCode(Boolean.FALSE); } public void run(String[] params, ICheatSheetManager manager) { // ADD xqliu TDQ-4285 2011-12-27 if (!CheatSheetActionHelper.canRun()) { return; } // ~ TDQ-4285 run(); } @Override public void run() { try { changeActionStatus = changedDatabaseConnection(); } catch (ReloadCompareException e) { log.error(e, e); } } private ReturnCode changedDatabaseConnection() throws ReloadCompareException { Shell shell = PlatformUI.getWorkbench().getActiveWorkbenchWindow().getShell(); final EList<ModelElement> analyzedElements = analysisItem.getAnalysis().getContext() == null ? null : analysisItem .getAnalysis().getContext().getAnalysedElements(); if (analyzedElements == null || analyzedElements.size() == 0) { analysisItem.getAnalysis().getContext().setConnection(newDataProvider); return new ReturnCode(Boolean.TRUE); } // MOD qiongli 2011-1-10,feature 16796. if (oldDataProvider instanceof DelimitedFileConnection) { // MessageDialog.openInformation(shell, // DefaultMessagesImpl.getString("ChangeConnectionAction.ChangeConnection"), // "Can't change this connection!"); if (!MessageDialog.openConfirm(shell, DefaultMessagesImpl.getString("ChangeConnectionAction.ChangeConnection"), //$NON-NLS-1$ DefaultMessagesImpl.getString("ChangeConnectionAction.ChangeConnectionTips"))) { //$NON-NLS-1$ return new ReturnCode(Boolean.FALSE); } } // Open synchronized dialog. boolean retCode = MessageDialog.openQuestion(shell, DefaultMessagesImpl.getString("ChangeConnectionAction.ChangeConnection"), //$NON-NLS-1$ DefaultMessagesImpl.getString("ChangeConnectionAction.MayCauseAsynProblem")); //$NON-NLS-1$ if (retCode) { if (analyzedElements.get(0) instanceof TdColumn) { anaEleSynDialog = new AnalyzedColumnsSynDialog(shell, analysisItem.getAnalysis(), newDataProvider, analyzedElements); } else if (analyzedElements.get(0) instanceof ColumnSet) { anaEleSynDialog = new AnalyzedColumnSetsSynDialog(shell, analysisItem.getAnalysis(), newDataProvider, analyzedElements); } else if (analyzedElements.get(0) instanceof Package) { anaEleSynDialog = new AnalyzedPackageSynDialog(shell, analysisItem.getAnalysis(), newDataProvider, analyzedElements); } final List<SynTreeModel> treeModelLs = anaEleSynDialog == null ? null : anaEleSynDialog.getSynInputModel(); if (treeModelLs != null && treeModelLs.size() > 0) { // Make attempt to reload from db before showing asyned // message. boolean isReload = MessageDialog.openQuestion(shell, DefaultMessagesImpl.getString("ChangeConnectionAction.ReloadFromDatabase"), //$NON-NLS-1$ DefaultMessagesImpl.getString("ChangeConnectionAction.ExistElementAsynchronuos")); //$NON-NLS-1$ if (isReload) { ModelElement newDataProviderModel = treeModelLs.get(0).getNewDataProvElement(); if (newDataProviderModel != null && (newDataProviderModel instanceof ColumnSet || newDataProviderModel instanceof Package)) { if (newDataProviderModel instanceof Package) { IRunnableWithProgress op = new IRunnableWithProgress() { public void run(IProgressMonitor monitor) throws InvocationTargetException, InterruptedException { try { reloadByColumnSetFolderLevel(treeModelLs, anaEleSynDialog, newDataProvider); if (analyzedElements.get(0) instanceof TdColumn) { // Reload column folder reloadByColumnFolderLevel(treeModelLs, anaEleSynDialog, newDataProvider); } } catch (ReloadCompareException e) { log.error(e, e); } } }; try { ProgressUI.popProgressDialog(op); } catch (InvocationTargetException e) { log.error(e, e); } catch (InterruptedException e) { log.error(e, e); } } else if (newDataProviderModel instanceof ColumnSet) { IRunnableWithProgress op = new IRunnableWithProgress() { public void run(IProgressMonitor monitor) throws InvocationTargetException, InterruptedException { try { reloadByColumnFolderLevel(treeModelLs, anaEleSynDialog, newDataProvider); } catch (ReloadCompareException e) { log.error(e, e); } } }; try { ProgressUI.popProgressDialog(op); } catch (InvocationTargetException e) { log.error(e, e); } catch (InterruptedException e) { log.error(e, e); } } } } } // Open asyned dialog. if (treeModelLs != null && treeModelLs.size() > 0) { // Open confirmation dialog to see whether user want to // continue or not. int returnCode = anaEleSynDialog.open(); if (returnCode != Window.OK) { return new ReturnCode(Boolean.FALSE); } } // Synchronize analyzed elements. boolean isExistSynedElement = synAnalyzedElements(anaEleSynDialog, analysisItem.getAnalysis(), oldDataProvider, newDataProvider); // Add new dependencies. if (isExistSynedElement) { DependenciesHandler.getInstance().setDependencyOn(analysisItem.getAnalysis(), newDataProvider); ElementWriterFactory.getInstance().createDataProviderWriter().save(newDataProvider); } // Refresh analysis editor viewer. ElementWriterFactory.getInstance().createAnalysisWrite().save(analysisItem, false); // Refresh the repository tree view to adapt for the new analysis CorePlugin.getDefault().refreshDQView(RepositoryNodeHelper.getDataProfilingFolderNode(EResourceConstant.ANALYSIS)); } else { return new ReturnCode(Boolean.FALSE); } return new ReturnCode(Boolean.TRUE); } private void reloadByColumnSetFolderLevel(List<SynTreeModel> treeModelLs, AnalyzedElementSynDialog anaEleSynDialog, Connection newDataProv) throws ReloadCompareException { ModelElement oldDataProviderModel = treeModelLs.get(0).getOldDataProvElement(); // Reload columnSet folder ColumnSet columnset = null; if (oldDataProviderModel instanceof ColumnSet) { columnset = (ColumnSet) oldDataProviderModel; } else if (oldDataProviderModel instanceof TdColumn) { columnset = ColumnHelper.getColumnOwnerAsColumnSet(oldDataProviderModel); } else { return; } // MOD mzhao bug 8567 2010-03-29 IFolderNode reloadFolder = FolderNodeHelper .getFolderNode((Package) treeModelLs.get(0).getNewDataProvElement(), columnset); if (reloadFolder != null) { IComparisonLevel creatComparisonLevel = ComparisonLevelFactory.creatComparisonLevel(reloadFolder); if (creatComparisonLevel != null) { // FIXME newDataProv is never used in the following codes. newDataProv = creatComparisonLevel.reloadCurrentLevelElement(); } // Recompute after reload // FIXME treeModelLs is never used in the following codes. treeModelLs = anaEleSynDialog.getSynInputModel(); } } private void reloadByColumnFolderLevel(List<SynTreeModel> treeModelLs, AnalyzedElementSynDialog anaEleSynDialog, Connection newDataProv) throws ReloadCompareException { ModelElement newDataProviderModel = treeModelLs.get(0).getNewDataProvElement(); // If schema or catalog changed, we did not load anymore. // Reload column folder ColumnSet columnset = null; if (newDataProviderModel instanceof ColumnSet) { columnset = (ColumnSet) newDataProviderModel; } else if (newDataProviderModel instanceof TdColumn) { columnset = ColumnHelper.getColumnOwnerAsColumnSet(newDataProviderModel); } else { return; } // MOD mzhao bug 8567 2010-03-29 IFolderNode reloadFolder = FolderNodeHelper.getFolderNodes(columnset)[0]; if (reloadFolder != null) { IComparisonLevel creatComparisonLevel = ComparisonLevelFactory.creatComparisonLevel(reloadFolder); if (creatComparisonLevel != null) { // FIXME newDataProv is never used in the following codes. newDataProv = creatComparisonLevel.reloadCurrentLevelElement(); } // Recompute after reload // FIXME treeModelLs is never used in the following codes. treeModelLs = anaEleSynDialog.getSynInputModel(); } } private boolean synAnalyzedElements(AnalyzedElementSynDialog anaEleSynDialog, Analysis synAnalysis, Connection oldDataProvider, Connection newDataProv) { // Change connection uuid. Map<ModelElement, ModelElement> synEleMap = anaEleSynDialog == null ? null : anaEleSynDialog.getSynedEleMap(); AnalysisBuilder anaBuilder = new AnalysisBuilder(); anaBuilder.setAnalysis(synAnalysis); // Remove old dependencies. boolean isRemovedDependency = DependenciesHandler.getInstance().removeConnDependencyAndSave(analysisItem); if (!isRemovedDependency) { return false; } synAnalysis.getContext().setConnection(newDataProv); // Synchronize analysis result. EList<Indicator> indcList = synAnalysis.getResults().getIndicators(); Indicator[] copiedIndArray = new Indicator[indcList.size()]; System.arraycopy(indcList.toArray(), 0, copiedIndArray, 0, indcList.size()); // MOD qiongli 2010-6-13,bug 12766:To column analysis, which has same // construct connection with before and maybe have not indicator boolean isExistSynedElement = false; AnalysisType analysisType = synAnalysis.getParameters().getAnalysisType(); if (analysisType == AnalysisType.MULTIPLE_COLUMN) { EList<ModelElement> meLs = synAnalysis.getContext().getAnalysedElements(); ModelElement[] mes = new ModelElement[meLs.size()]; System.arraycopy(meLs.toArray(), 0, mes, 0, meLs.size()); synAnalysis.getContext().getAnalysedElements().clear(); for (ModelElement me : mes) { if (synEleMap != null && synEleMap.get(me) != null) { TdColumn newColumn = (TdColumn) synEleMap.get(me); synAnalysis.getContext().getAnalysedElements().add(newColumn); isExistSynedElement = true; } } } if (!isExistSynedElement) { synAnalysis.getContext().getAnalysedElements().clear(); } // ~ synAnalysis.getResults().getIndicators().clear(); for (Indicator indicator : copiedIndArray) { // Add new analyzed element contained in new // connection. if (indicator instanceof ColumnSetMultiValueIndicator) { ColumnSetMultiValueIndicator compositeInd = (ColumnSetMultiValueIndicator) indicator; ModelElement[] mes = new ModelElement[compositeInd.getAnalyzedColumns().size()]; ((ColumnSetMultiValueIndicator) indicator).getAnalyzedColumns().toArray(mes); compositeInd.getAnalyzedColumns().clear(); for (ModelElement me : mes) { if (synEleMap != null && synEleMap.get(me) != null) { TdColumn newColumn = (TdColumn) synEleMap.get(me); DataminingType dataminingType = MetadataHelper.getDataminingType((TdColumn) me); if (dataminingType == null) { dataminingType = MetadataHelper.getDefaultDataminingType(((TdColumn) me).getSqlDataType() .getJavaDataType()); } MetadataHelper.setDataminingType(dataminingType, newColumn); compositeInd.getAnalyzedColumns().add(newColumn); anaBuilder.addElementToAnalyze(newColumn, indicator); isExistSynedElement = true; } } } else if (indicator instanceof ColumnsCompareIndicator) { // Correlation compare ColumnsCompareIndicator compInd = (ColumnsCompareIndicator) indicator; if ((compInd.getColumnSetA() == null || compInd.getColumnSetA().size() == 0) || (compInd.getColumnSetB() == null || compInd.getColumnSetB().size() == 0)) { return false; } // Column set(Columns) ModelElement[] mesA = new ModelElement[compInd.getColumnSetA().size()]; compInd.getColumnSetA().toArray(mesA); compInd.getColumnSetA().clear(); for (ModelElement me : mesA) { if (synEleMap != null && synEleMap.get(me) != null) { TdColumn newColumn = (TdColumn) synEleMap.get(me); compInd.getColumnSetA().add(newColumn); anaBuilder.addElementToAnalyze(newColumn, indicator); isExistSynedElement = true; } } ModelElement[] mesB = new ModelElement[compInd.getColumnSetB().size()]; compInd.getColumnSetB().toArray(mesB); compInd.getColumnSetB().clear(); for (ModelElement me : mesB) { if (synEleMap != null && synEleMap.get(me) != null) { TdColumn newColumn = (TdColumn) synEleMap.get(me); compInd.getColumnSetB().add(newColumn); anaBuilder.addElementToAnalyze(newColumn, indicator); isExistSynedElement = true; } } // Analyzed element(Table) ModelElement oldAnaEle = compInd.getAnalyzedElement(); compInd.setAnalyzedElement(null); ColumnSet oldColSetA = ColumnHelper.getColumnOwnerAsColumnSet(mesA[0]); ColumnSet oldColSetB = ColumnHelper.getColumnOwnerAsColumnSet(mesB[0]); if (oldColSetA == oldAnaEle) { if (synEleMap != null && synEleMap.get(mesA[0]) != null) { compInd.setAnalyzedElement(ColumnHelper.getColumnOwnerAsColumnSet(synEleMap.get(mesA[0]))); } } if (oldColSetB == oldAnaEle) { if (synEleMap != null && synEleMap.get(mesB[0]) != null) { compInd.setAnalyzedElement(ColumnHelper.getColumnOwnerAsColumnSet(synEleMap.get(mesB[0]))); } } } else if (indicator instanceof ColumnDependencyIndicator) { // ADD qiongli bug 0012766 // Functional Dependency indicator ColumnDependencyIndicator funDepInd = (ColumnDependencyIndicator) indicator; if (funDepInd.getColumnA() == null || funDepInd.getColumnB() == null) { return false; } // Column A if (synEleMap != null && synEleMap.get(funDepInd.getColumnA()) != null) { TdColumn newColumn = (TdColumn) synEleMap.get(funDepInd.getColumnA()); funDepInd.setColumnA(newColumn); anaBuilder.addElementToAnalyze(newColumn, indicator); isExistSynedElement = true; } // Column B if (synEleMap != null && synEleMap.get(funDepInd.getColumnB()) != null) { TdColumn newColumn = (TdColumn) synEleMap.get(funDepInd.getColumnB()); funDepInd.setColumnB(newColumn); anaBuilder.addElementToAnalyze(newColumn, indicator); isExistSynedElement = true; } // Analyzed element(Table) ModelElement oldAnaEle = funDepInd.getAnalyzedElement(); funDepInd.setAnalyzedElement(null); ColumnSet oldColSetA = ColumnHelper.getColumnOwnerAsColumnSet(funDepInd.getColumnA()); ColumnSet oldColSetB = ColumnHelper.getColumnOwnerAsColumnSet(funDepInd.getColumnB()); if (oldColSetA == oldAnaEle) { if (synEleMap != null && synEleMap.get(funDepInd.getColumnA()) != null) { funDepInd .setAnalyzedElement(ColumnHelper.getColumnOwnerAsColumnSet(synEleMap.get(funDepInd.getColumnA()))); } } if (oldColSetB == oldAnaEle) { if (synEleMap != null && synEleMap.get(funDepInd.getColumnB()) != null) { funDepInd .setAnalyzedElement(ColumnHelper.getColumnOwnerAsColumnSet(synEleMap.get(funDepInd.getColumnB()))); } } } else { ModelElement me = indicator.getAnalyzedElement(); if (synEleMap != null && synEleMap.get(me) != null) { indicator.setAnalyzedElement(synEleMap.get(me)); if (analysisType == AnalysisType.MULTIPLE_COLUMN) { synAnalysis.getResults().getIndicators().add(indicator); } else { anaBuilder.addElementToAnalyze(synEleMap.get(me), indicator); } isExistSynedElement = true; } } } return isExistSynedElement; } public ReturnCode getStatus() { return changeActionStatus; } }