org.eclipse.emf.workspace
Class AbstractEMFOperation

java.lang.Object
  extended by org.eclipse.core.commands.operations.AbstractOperation
      extended by org.eclipse.emf.workspace.AbstractEMFOperation
All Implemented Interfaces:
IUndoableOperation
Direct Known Subclasses:
CompositeEMFOperation, EMFCommandOperation

public abstract class AbstractEMFOperation
extends AbstractOperation

An abstract superclass for IUndoableOperations that modify EMF models. The EMF operation provides a read/write transaction context for the subclass implementation of the execution logic, with undo/redo support "for free" (via recording of undo information).

The assumption is that an EMF operation will perform only changes to EMF models that can be recorded. If concomitant changes to non-EMF models are also required, then they should be combined with the EMF operation via a CompositeEMFOperation, unless ordering of EMF and non-EMF changes is unimportant. In such cases, it is sufficient to extend the doUndo(IProgressMonitor, IAdaptable) and doRedo(IProgressMonitor, IAdaptable) methods.

This class is meant to be extended by clients.

See Also:
CompositeEMFOperation

Constructor Summary
AbstractEMFOperation(TransactionalEditingDomain domain, String label)
          Initializes me with the editing domain in which I am making model changes and a label.
AbstractEMFOperation(TransactionalEditingDomain domain, String label, Map<?,?> options)
          Initializes me with the editing domain, a label, and transaction options.
 
Method Summary
protected  IStatus aggregateStatuses(List<? extends IStatus> statuses)
          Creates a suitable aggregate from these statuses.
 boolean canRedo()
          Queries whether I can be redone.
 boolean canUndo()
          Queries whether I can be undone.
protected  void didCommit(Transaction transaction)
           Hook for subclasses to learn that the specified transaction has been successfully committed and, if necessary, to extract information from it.
protected  void didRedo(Transaction tx)
          Hook for subclasses to learn that the specified transaction has been successfully redone and, if necessary, to extract information from it.
protected  void didUndo(Transaction tx)
          Hook for subclasses to learn that the specified transaction has been successfully undone and, if necessary, to extract information from it.
 void dispose()
          Forgets my transaction and its change description.
protected abstract  IStatus doExecute(IProgressMonitor monitor, IAdaptable info)
          Implemented by subclasses to perform the model changes.
protected  IStatus doRedo(IProgressMonitor monitor, IAdaptable info)
          Implements the redo behaviour by replaying my recorded changes.
protected  IStatus doUndo(IProgressMonitor monitor, IAdaptable info)
          Implements the undo behaviour by inverting my recorded changes.
 IStatus execute(IProgressMonitor monitor, IAdaptable info)
          Implements the execution by delegating to the doExecute(IProgressMonitor, IAdaptable) method within a read/write transaction.
protected  TransactionChangeDescription getChange()
          Obtains the change description that I recorded during execution of my transaction.
 TransactionalEditingDomain getEditingDomain()
          Obtains my editing domain.
 Map<?,?> getOptions()
          Obtains the transaction options that I use to create my transaction.
 IStatus redo(IProgressMonitor monitor, IAdaptable info)
          Redoes me by replaying my recorded changes in a transaction.
 IStatus undo(IProgressMonitor monitor, IAdaptable info)
          Undoes me by inverting my recorded changes in a transaction.
 
Methods inherited from class org.eclipse.core.commands.operations.AbstractOperation
addContext, canExecute, getContexts, getLabel, hasContext, removeContext, setLabel, toString
 
Methods inherited from class java.lang.Object
clone, equals, finalize, getClass, hashCode, notify, notifyAll, wait, wait, wait
 

Constructor Detail

AbstractEMFOperation

public AbstractEMFOperation(TransactionalEditingDomain domain,
                            String label)
Initializes me with the editing domain in which I am making model changes and a label.

Parameters:
domain - my editing domain
label - my user-readable label

AbstractEMFOperation

public AbstractEMFOperation(TransactionalEditingDomain domain,
                            String label,
                            Map<?,?> options)
Initializes me with the editing domain, a label, and transaction options.

Parameters:
domain - my editing domain
label - my user-readable label
options - for the transaction in which I execute myself, or null for the default options
Method Detail

execute

public final IStatus execute(IProgressMonitor monitor,
                             IAdaptable info)
                      throws ExecutionException
Implements the execution by delegating to the doExecute(IProgressMonitor, IAdaptable) method within a read/write transaction.

Specified by:
execute in interface IUndoableOperation
Specified by:
execute in class AbstractOperation
Throws:
ExecutionException
See Also:
doExecute(IProgressMonitor, IAdaptable)

aggregateStatuses

protected IStatus aggregateStatuses(List<? extends IStatus> statuses)
Creates a suitable aggregate from these statuses. If there are no statuses to aggregate, then an OK status is returned. If there is a single status to aggregate, then it is returned. Otherwise, a multi-status is returned with the provided statuses as children.

Parameters:
statuses - the statuses to aggregate. May have zero, one, or more elements (all must be IStatuses)
Returns:
the multi-status

getChange

protected final TransactionChangeDescription getChange()
Obtains the change description that I recorded during execution of my transaction.

Returns:
my change description, if I executed successfully; null, otherwise

didCommit

protected void didCommit(Transaction transaction)

Hook for subclasses to learn that the specified transaction has been successfully committed and, if necessary, to extract information from it.

Note: subclasses should call this super implementation to get some default behaviours.

Parameters:
transaction - a transaction that has committed, which has recorded our changes

canUndo

public boolean canUndo()
Queries whether I can be undone. I can generally be undone if I was successfully executed. Subclasses would not usually need to override this method.

Specified by:
canUndo in interface IUndoableOperation
Overrides:
canUndo in class AbstractOperation

undo

public final IStatus undo(IProgressMonitor monitor,
                          IAdaptable info)
                   throws ExecutionException
Undoes me by inverting my recorded changes in a transaction.

Specified by:
undo in interface IUndoableOperation
Specified by:
undo in class AbstractOperation
Throws:
ExecutionException

didUndo

protected void didUndo(Transaction tx)
Hook for subclasses to learn that the specified transaction has been successfully undone and, if necessary, to extract information from it.

Parameters:
tx - a transaction that has been undone.

canRedo

public boolean canRedo()
Queries whether I can be redone. I can generally be redone if I was successfully executed. Subclasses would not usually need to override this method.

Specified by:
canRedo in interface IUndoableOperation
Overrides:
canRedo in class AbstractOperation

redo

public final IStatus redo(IProgressMonitor monitor,
                          IAdaptable info)
                   throws ExecutionException
Redoes me by replaying my recorded changes in a transaction.

Specified by:
redo in interface IUndoableOperation
Specified by:
redo in class AbstractOperation
Throws:
ExecutionException

didRedo

protected void didRedo(Transaction tx)
Hook for subclasses to learn that the specified transaction has been successfully redone and, if necessary, to extract information from it.

Parameters:
tx - a transaction that has been redone.

getEditingDomain

public final TransactionalEditingDomain getEditingDomain()
Obtains my editing domain.

Returns:
my editing domain

getOptions

public final Map<?,?> getOptions()
Obtains the transaction options that I use to create my transaction.

Returns:
my options, or an empty map if none

doExecute

protected abstract IStatus doExecute(IProgressMonitor monitor,
                                     IAdaptable info)
                              throws ExecutionException
Implemented by subclasses to perform the model changes. These changes are applied by manipulation of the EMF metamodel's API, not by executing commands on the editing domain's command stack.

Parameters:
monitor - the progress monitor provided by the operation history. Will never be null because the execute(IProgressMonitor, IAdaptable) method would substitute a NullProgressMonitor in that case
info - the adaptable provided by the operation history
Returns:
the status of the execution
Throws:
ExecutionException - if, for some reason, I fail to complete the operation

doUndo

protected IStatus doUndo(IProgressMonitor monitor,
                         IAdaptable info)
                  throws ExecutionException
Implements the undo behaviour by inverting my recorded changes.

Note that subclasses overriding this method must invoke the super implementation as well.

Parameters:
monitor - the progress monitor provided by the operation history Will never be null because the undo(IProgressMonitor, IAdaptable) method would substitute a NullProgressMonitor in that case
info - the adaptable provided by the operation history
Returns:
the status of the undo operation
Throws:
ExecutionException - on failure to undo

doRedo

protected IStatus doRedo(IProgressMonitor monitor,
                         IAdaptable info)
                  throws ExecutionException
Implements the redo behaviour by replaying my recorded changes.

Note that subclasses overriding this method must invoke the super implementation as well.

Parameters:
monitor - the progress monitor provided by the operation history Will never be null because the redo(IProgressMonitor, IAdaptable) method would substitute a NullProgressMonitor in that case
info - the adaptable provided by the operation history
Returns:
the status of the redo operation
Throws:
ExecutionException - on failure to redo

dispose

public void dispose()
Forgets my transaction and its change description.

Specified by:
dispose in interface IUndoableOperation
Overrides:
dispose in class AbstractOperation

Copyright 2002, 2007 IBM Corporation and others.
All Rights Reserved.