/******************************************************************************* * Copyright (c) 2013, 2015 Red Hat, Inc. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html * * Contributors: * Red Hat Inc. - initial API and implementation and/or initial documentation *******************************************************************************/ package org.eclipse.thym.ui.plugins.internal; import static org.eclipse.thym.ui.plugins.internal.CordovaPluginSelectionPage.PLUGIN_SOURCE_DIRECTORY; import static org.eclipse.thym.ui.plugins.internal.CordovaPluginSelectionPage.PLUGIN_SOURCE_GIT; import static org.eclipse.thym.ui.plugins.internal.CordovaPluginSelectionPage.PLUGIN_SOURCE_REGISTRY; import java.io.File; import java.lang.reflect.InvocationTargetException; import java.net.URI; import java.util.List; import org.eclipse.core.runtime.Assert; import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.IProgressMonitor; import org.eclipse.core.runtime.IStatus; import org.eclipse.core.runtime.Status; import org.eclipse.jface.dialogs.ErrorDialog; import org.eclipse.jface.dialogs.IDialogConstants; import org.eclipse.jface.dialogs.IDialogSettings; import org.eclipse.jface.dialogs.MessageDialog; import org.eclipse.jface.viewers.IStructuredSelection; import org.eclipse.jface.wizard.Wizard; import org.eclipse.jface.wizard.WizardPage; import org.eclipse.swt.SWT; import org.eclipse.swt.widgets.Composite; import org.eclipse.swt.widgets.Control; import org.eclipse.swt.widgets.Shell; import org.eclipse.thym.core.HybridProject; import org.eclipse.thym.core.plugin.CordovaPluginManager; import org.eclipse.thym.core.plugin.FileOverwriteCallback; import org.eclipse.thym.core.plugin.registry.CordovaRegistryPlugin.RegistryPluginVersion; import org.eclipse.thym.ui.HybridUI; import org.eclipse.thym.ui.internal.status.StatusManager; import org.eclipse.ui.IWorkbench; import org.eclipse.ui.IWorkbenchWizard; import org.eclipse.ui.actions.WorkspaceModifyOperation; public class CordovaPluginWizard extends Wizard implements IWorkbenchWizard, FileOverwriteCallback, ICordovaPluginWizard{ static final String IMAGE_WIZBAN = "/icons/wizban/cordova_plugin_wiz.png"; private static final String DIALOG_SETTINGS_KEY = "CordovaPluginWizard"; private static class OverwriteDialog extends MessageDialog{ public static final int YES_TO_ALL_INDEX = 0; private String[] paths; public OverwriteDialog(Shell parentShell, String[] paths) { super(parentShell, "Overwrite Files", null, "Listed files will be overwritten, would you like to proceed with the installation?", MessageDialog.QUESTION, new String[]{IDialogConstants.YES_TO_ALL_LABEL, IDialogConstants.CANCEL_LABEL}, 1); this.paths = paths; } @Override protected Control createCustomArea(Composite parent) { org.eclipse.swt.widgets.List list = new org.eclipse.swt.widgets.List(parent, SWT.SINGLE); for (int i = 0; i < paths.length; i++) { list.add(paths[i]); } return list; } } private CordovaPluginSelectionPage pageOne; private RegistryConfirmPage pageTwo; private IStructuredSelection initialSelection; private HybridProject fixedProject; private int initialSource; private class PluginInstallOperation extends WorkspaceModifyOperation{ private CordovaPluginManager pm; private int opType; private File dir; private URI gitRepo; private List<RegistryPluginVersion> plugins; private FileOverwriteCallback fileOverwriteCallback; private PluginInstallOperation(CordovaPluginManager pm, FileOverwriteCallback overwrite){ this.pm = pm; this.fileOverwriteCallback = overwrite; } public PluginInstallOperation(File directory, CordovaPluginManager pm, FileOverwriteCallback overwite ){ this(pm,overwite); this.dir = directory; opType = PLUGIN_SOURCE_DIRECTORY; } public PluginInstallOperation(URI gitRepo, CordovaPluginManager pm, FileOverwriteCallback overwite){ this(pm, overwite); this.gitRepo = gitRepo; opType = PLUGIN_SOURCE_GIT; } public PluginInstallOperation(List<RegistryPluginVersion> plugins, CordovaPluginManager pm, FileOverwriteCallback overwite ){ this(pm,overwite); this.plugins = plugins; opType = PLUGIN_SOURCE_REGISTRY; } @Override protected void execute(IProgressMonitor monitor) throws CoreException, InvocationTargetException, InterruptedException { switch (opType){ case PLUGIN_SOURCE_DIRECTORY: pm.installPlugin(this.dir,fileOverwriteCallback, monitor); break; case PLUGIN_SOURCE_GIT: pm.installPlugin(this.gitRepo,fileOverwriteCallback,false, monitor ); break; case PLUGIN_SOURCE_REGISTRY: for (RegistryPluginVersion cordovaRegistryPluginVersion : plugins) { pm.installPlugin(cordovaRegistryPluginVersion,fileOverwriteCallback,false, monitor); } break; default: Assert.isTrue(false, "No valid plugin source can be determined"); break; } } } public CordovaPluginWizard() { setWindowTitle("Cordova Plug-in Discovery"); setNeedsProgressMonitor(true); IDialogSettings workbenchSettings= HybridUI.getDefault().getDialogSettings(); IDialogSettings section= workbenchSettings.getSection(DIALOG_SETTINGS_KEY); setDialogSettings(section); } @Override public void init(IWorkbench workbench, IStructuredSelection selection) { initialSelection = selection; } /** * Causes the wizard to work with a fixed project, and does not enable * users to select a different project to operate on. * @param project */ public void init(HybridProject project, int initialSourceTab){ this.fixedProject = project; this.initialSource = initialSourceTab; } @Override public boolean performFinish() { HybridProject project = HybridProject.getHybridProject(pageOne.getProjectName()); if(project == null ) return false; CordovaPluginManager pm = new CordovaPluginManager(project); PluginInstallOperation op = null; switch (pageOne.getPluginSourceType()) { case PLUGIN_SOURCE_DIRECTORY: File directory = new File(pageOne.getSelectedDirectory()); op=new PluginInstallOperation(directory, pm,this); break; case PLUGIN_SOURCE_GIT: URI uri = URI.create(pageOne.getSpecifiedGitURL()); op = new PluginInstallOperation(uri, pm, this); break; case PLUGIN_SOURCE_REGISTRY: List<RegistryPluginVersion> plugins = pageTwo.getSelectedPluginVersions(); op = new PluginInstallOperation(plugins, pm, this); break; default: Assert.isTrue(false, "No valid plugin source can be determined"); } try { getContainer().run(true, true, op); } catch (InvocationTargetException e) { if (e.getTargetException() != null) { if(e.getTargetException() instanceof CoreException ){ StatusManager.handle((CoreException) e.getTargetException()); }else{ ErrorDialog.openError(getShell(), "Plug-in installation problem", null, new Status(IStatus.ERROR, HybridUI.PLUGIN_ID, "Errors occured during plug-in installation", e.getTargetException() )); return false; } } return false; } catch (InterruptedException e) { return false; } savePageSettings(); return true; } @Override public void addPages() { if(fixedProject == null ){ pageOne = new CordovaPluginSelectionPage(this.initialSelection); }else{ pageOne = new CordovaPluginSelectionPage(fixedProject,initialSource); } addPage(pageOne); pageTwo = new RegistryConfirmPage(); addPage(pageTwo); } public WizardPage getRegistryConfirmPage(){ return pageTwo; } HybridProject getFixedProject(){ return fixedProject; } private void savePageSettings() { IDialogSettings workbenchSettings = HybridUI.getDefault() .getDialogSettings(); IDialogSettings section = workbenchSettings .getSection(DIALOG_SETTINGS_KEY); if (section == null) { section = workbenchSettings.addNewSection(DIALOG_SETTINGS_KEY); } setDialogSettings(section); pageOne.saveWidgetValues(); } @Override public boolean isOverwiteAllowed(String[] files) { final OverwriteDialog dialog = new OverwriteDialog(this.getShell(), files); getShell().getDisplay().syncExec(new Runnable() { @Override public void run() { dialog.open(); } }); return dialog.getReturnCode() == OverwriteDialog.YES_TO_ALL_INDEX; } @Override public boolean isPluginSelectionOptional() { return false; } }