package hirondelle.web4j.model;

import java.io.Serializable;
import java.util.List;

/**
 Base class for most exceptions defined by WEB4J.  

 <P>Differs from most exception classes in that multiple error 
 messages may be used, instead of just one. Used in JSPs to inform the user of 
 error conditions, usually related to user input validations.
 
 <P>This class is {@link Serializable}, since all {@link Throwable}s are serializable.
*/
public class AppException extends Exception implements MessageList { 
  
  /** No-argument constructor. */
  public AppException(){
    super();
  }
  
  /**
   Constructor.
    
   @param aMessage text describing the problem. Must have content.
   @param aThrowable root cause underlying the problem.
  */
  public AppException(String aMessage, Throwable aThrowable){
    super(aMessage, aThrowable);
    add(aMessage);
    //using instanceof is distasteful, but overloading constructors,
    //that is, defining a second ctor(String, AppException), does not work
    if ( aThrowable instanceof AppException ) {
      add( (AppException)aThrowable );
    }
  }

  public final void add(String aErrorMessage){
    fErrorMessages.add(aErrorMessage);
  }

  public final void add(String aErrorMessage, Object... aParams){
    fErrorMessages.add(aErrorMessage, aParams);
  }
  
  public final void add(AppException ex){
    fErrorMessages.add(ex);
  }
  
  public boolean isEmpty(){
    return fErrorMessages.isEmpty();
  }
  
  public final boolean isNotEmpty(){
    return !fErrorMessages.isEmpty();
  }
  
  public final List<AppResponseMessage> getMessages(){
    return fErrorMessages.getMessages();
  }
  
  /** Intended for debugging only.  */
  @Override public String toString(){
    return fErrorMessages.toString();
  }
  
  // PRIVATE 
  
  /**
   List of error messages attached to this exception.
   <P>Implementation Note :
   This class is a wrapper of MessageListImpl, and simply forwards
   related method calls to this field. This avoids code repetition.
  */
  private MessageList fErrorMessages = new MessageListImpl();
}
