net.java.truecommons.shed.ExceptionHandler Maven / Gradle / Ivy
/*
* Copyright (C) 2005-2012 Schlichtherle IT Services.
* All rights reserved. Use is subject to license terms.
*/
package net.java.truecommons.shed;
import javax.annotation.concurrent.NotThreadSafe;
/**
* A generic callback interface designed to be implemented by client
* applications in order to inject an exception handling strategy into a
* cooperative algorithm as its dependency.
* In the event of an exception, the cooperative algorithm would then call this
* interface with an input exception in order to let the implementation decide
* how to proceed.
* The implementation can then make the following decisions:
*
* - If possible, shall the control be returned to the cooperative algorithm
* in order to proceed its task?
*
- If not, shall the input exception get mapped to or composed into an
* output exception of the same or another type before throwing it?
*
*
* Optionally, the implementation may perform additional operations such as
* logging the input exception or storing it for later use.
* This implies that the implementation may be stateful and mutable, which
* in turn implies that the cooperative algorithm should not bypass this
* interface, i.e. it should never simply create and throw an exception without
* calling this exception handler.
* Otherwise some information, such as previous cause exceptions for example,
* could get lost.
*
* In general, the type parameter for the input exception is determined by the
* cooperative algorithm, whereas the type parameter for the output exception
* is determined by the client application.
* Where possible, the cooperative algorithm should declare generic method
* signatures in order to enable the client application to select the type of
* the thrown exception as desired (see below).
*
* As an example for a cooperative algorithm which may benefit from using
* this interface, consider the recursive copying of a directory tree:
* Among many others, the copy algorithm may encounter the following
* exceptional conditions:
*
* - A source file cannot get opened because of insufficient access
* privileges.
*
- A destination file cannot get written because the file system is full.
*
*
* Now the implementation may decide whether the copy algorithm shall proceed
* with the remaining files and directories in the tree or if not, if the cause
* exception should get wrapped in another exception in order to enable
* diagnosing the situation by its client application.
*
* The copy algorithm could use two different exception handlers:
* One for any exception when reading from a source file and another one for
* any exception when writing to a destination file.
* If these exception handlers would map any cause to a different exception
* type, then this would enable the client application to analyze the situation
* and take appropriate action.
*
* However, if the client application doesn't care, it could simply provide the
* same exception handler for both input and output exceptions to the copy
* algorithm.
*
* Here's how a generic method declaration for a copy algorithm could look like:
*
{@code
* public
* copy( File src, ExceptionHandler inputHandler,
* File dst, ExceptionHandler outputHandler)
* throws I, O {
* // ...
* }
* }
*
* Note that the first type parameter for both handlers is an
* {@link java.io.IOException} for the input exceptions whereas the the second
* type parameter determines the type of the output exceptions which may get
* thrown by the exception handlers themselves.
*
* @param the type of the input exceptions.
* @param the type of the output exceptions.
* @author Christian Schlichtherle
*/
@NotThreadSafe
public interface ExceptionHandler {
/**
* Called to handle an exception which doesn't allow the caller
* to proceed with its task.
* The implementation must return an appropriate exception to be thrown
* by the cooperative algorithm.
* Finally, if the implementation maintains a state, it must get updated
* so that this instance can get reused to handle more exceptions!
*
* @param input the input exception to handle.
* @return The output exception to throw.
*/
O fail(I input);
/**
* Called to handle an exception which may allow the caller to
* proceed with its task.
* The implementation may return from the call or throw an exception of the
* parameter type {@code O}.
* If the implementation maintains a state, it must get updated
* so that this instance can get reused to handle more exceptions.
*
* @param input the input exception to handle.
* @throws O the output exception if the client application
* wants the cooperative algorithm to abort its task.
*/
void warn(I input) throws O;
}