org.eclipse.emf.compare.ide.ui.internal.structuremergeviewer.actions.SaveComparisonModelAction.java Source code

Java tutorial

Introduction

Here is the source code for org.eclipse.emf.compare.ide.ui.internal.structuremergeviewer.actions.SaveComparisonModelAction.java

Source

/*******************************************************************************
 * Copyright (c) 2013, 2016 Obeo and others.
 * 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:
 *     Obeo - initial API and implementation
 *     Stefan Dirix - bug 473985
 *******************************************************************************/
package org.eclipse.emf.compare.ide.ui.internal.structuremergeviewer.actions;

import static com.google.common.collect.Maps.newHashMap;

import com.google.common.collect.ImmutableList;

import java.io.File;
import java.io.IOException;
import java.io.NotSerializableException;

import org.eclipse.core.resources.IFile;
import org.eclipse.core.resources.IResource;
import org.eclipse.core.resources.ResourcesPlugin;
import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IStatus;
import org.eclipse.core.runtime.NullProgressMonitor;
import org.eclipse.core.runtime.Path;
import org.eclipse.core.runtime.Status;
import org.eclipse.emf.common.util.URI;
import org.eclipse.emf.compare.Comparison;
import org.eclipse.emf.compare.ide.ui.internal.EMFCompareIDEUIMessages;
import org.eclipse.emf.compare.ide.ui.internal.EMFCompareIDEUIPlugin;
import org.eclipse.emf.compare.rcp.ui.internal.configuration.IEMFCompareConfiguration;
import org.eclipse.emf.ecore.EObject;
import org.eclipse.emf.ecore.resource.Resource;
import org.eclipse.emf.ecore.util.EcoreUtil.Copier;
import org.eclipse.emf.ecore.xmi.impl.XMIResourceImpl;
import org.eclipse.jface.action.Action;
import org.eclipse.jface.dialogs.MessageDialog;
import org.eclipse.swt.SWT;
import org.eclipse.swt.widgets.Display;
import org.eclipse.swt.widgets.FileDialog;
import org.eclipse.swt.widgets.Shell;
import org.eclipse.ui.PlatformUI;
import org.eclipse.ui.plugin.AbstractUIPlugin;
import org.eclipse.ui.statushandlers.StatusAdapter;
import org.eclipse.ui.statushandlers.StatusManager;

/**
 * Action that manages the save of the comparison model.
 * 
 * @author <a href="mailto:axel.richard@obeo.fr">Axel Richard</a>
 * @since 3.0
 */
public class SaveComparisonModelAction extends Action {

    /** The dialog buttons. */
    private static final ImmutableList<String> DIALOG_BUTTON_LABELS = ImmutableList.of("Replace", "Cancel");

    /** The compare configuration object used to get the compare model. */
    private IEMFCompareConfiguration configuration;

    /**
     * Constructor.
     * 
     * @param configuration
     *            The compare configuration object.
     */
    public SaveComparisonModelAction(IEMFCompareConfiguration configuration) {
        this.configuration = configuration;
        setToolTipText(EMFCompareIDEUIMessages.getString("save.model.tooltip")); //$NON-NLS-1$
        setImageDescriptor(AbstractUIPlugin.imageDescriptorFromPlugin(EMFCompareIDEUIPlugin.PLUGIN_ID,
                "icons/full/toolb16/saveas_edit.gif")); //$NON-NLS-1$
    }

    /**
     * {@inheritDoc}
     * 
     * @see org.eclipse.jface.action.Action#run()
     */
    @Override
    public void run() {
        Shell parent = getShell();

        FileDialog fileDialog = new FileDialog(parent, SWT.SAVE);
        String filePath = fileDialog.open();
        if (filePath != null) {
            File file = new File(filePath);
            if (file.exists()) {
                MessageDialog messageDialog = new MessageDialog(parent, "File already exists", null,
                        "File \"" + file.toString() + "\" already exists. Do you want to replace the existing one?",
                        MessageDialog.WARNING,
                        DIALOG_BUTTON_LABELS.toArray(new String[DIALOG_BUTTON_LABELS.size()]), 1);
                int open = messageDialog.open();
                if (open == DIALOG_BUTTON_LABELS.indexOf("Replace")) {
                    saveComparison(file);
                    refreshLocation(filePath);
                } // else do nothing
            } else {
                saveComparison(file);
                refreshLocation(filePath);
            }
        }

        super.run();
    }

    /**
     * Returns the active shell from the workbench (if running) or the default display.
     * 
     * @return The active shell.
     */
    private Shell getShell() {
        if (PlatformUI.isWorkbenchRunning()) {
            return PlatformUI.getWorkbench().getDisplay().getActiveShell();
        }
        return Display.getDefault().getActiveShell();
    }

    /**
     * {@inheritDoc}
     * 
     * @see org.eclipse.jface.action.Action#isEnabled()
     */
    @Override
    public boolean isEnabled() {
        return configuration.isLeftEditable() && configuration.isRightEditable();
    }

    /**
     * Save the compare model in the given result {@link File}.
     * 
     * @param file
     *            the result {@link File}.
     */
    private void saveComparison(File file) {
        Comparison comparison = configuration.getComparison();
        Resource resource = new XMIResourceImpl(URI.createFileURI(file.getAbsolutePath()));
        Copier copier = new Copier(false);
        EObject comparisonCopy = copier.copy(comparison);
        copier.copyReferences();

        resource.getContents().add(comparisonCopy);
        try {
            resource.save(newHashMap());
        } catch (RuntimeException e) {
            if (e.getCause() instanceof NotSerializableException) {
                final Status status = new Status(IStatus.ERROR, EMFCompareIDEUIPlugin.PLUGIN_ID,
                        EMFCompareIDEUIMessages.getString("resource.not.serializable"), e); //$NON-NLS-1$
                StatusManager.getManager().handle(new StatusAdapter(status), StatusManager.SHOW);
            } else {
                EMFCompareIDEUIPlugin.getDefault().log(e);
            }
        } catch (IOException e) {
            EMFCompareIDEUIPlugin.getDefault().log(e);
        }
    }

    /**
     * Refresh the folder containing the given path.
     * 
     * @param path
     *            the given path.
     */
    private void refreshLocation(String path) {
        try {
            IFile fileForLocation = ResourcesPlugin.getWorkspace().getRoot().getFileForLocation(new Path(path));
            if (fileForLocation != null) {
                fileForLocation.getParent().refreshLocal(IResource.DEPTH_INFINITE, new NullProgressMonitor());
            }
        } catch (CoreException e) {
            EMFCompareIDEUIPlugin.getDefault().log(e);
        }
    }
}