001/* 002 * Licensed to the Apache Software Foundation (ASF) under one 003 * or more contributor license agreements. See the NOTICE file 004 * distributed with this work for additional information 005 * regarding copyright ownership. The ASF licenses this file 006 * to you under the Apache License, Version 2.0 (the 007 * "License"); you may not use this file except in compliance 008 * with the License. You may obtain a copy of the License at 009 * 010 * http://www.apache.org/licenses/LICENSE-2.0 011 * 012 * Unless required by applicable law or agreed to in writing, 013 * software distributed under the License is distributed on an 014 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 015 * KIND, either express or implied. See the License for the 016 * specific language governing permissions and limitations 017 * under the License. 018 * 019 */ 020package org.apache.directory.api.util.exception; 021 022 023import java.io.PrintStream; 024import java.io.PrintWriter; 025 026import java.util.ArrayList; 027import java.util.Collection; 028import java.util.Iterator; 029 030 031/** 032 * This exception is thrown when Base class for nested exceptions. 033 * 034 * @author <a href="mailto:dev@directory.apache.org">Apache Directory Project</a> 035 */ 036public class MultiException extends Exception 037{ 038 /** The serialVersionUID. */ 039 static final long serialVersionUID = 2889747406899775761L; 040 041 /** Collection of nested exceptions. */ 042 private final Collection<Throwable> nestedExceptions = new ArrayList<>(); 043 044 045 /** 046 * Constructs an Exception without a message. 047 */ 048 public MultiException() 049 { 050 super(); 051 } 052 053 054 /** 055 * Constructs an Exception with a detailed message. 056 * 057 * @param message The message associated with the exception. 058 */ 059 public MultiException( String message ) 060 { 061 super( message ); 062 } 063 064 065 /** 066 * Lists the nested exceptions that this Exception encapsulates. 067 * 068 * @return an Iterator over the nested exceptions. 069 */ 070 public Iterator<Throwable> listNestedExceptions() 071 { 072 return nestedExceptions.iterator(); 073 } 074 075 076 /** 077 * Gets the size of this nested exception which equals the number of 078 * exception nested within. 079 * 080 * @return the size of this nested exception. 081 */ 082 public int size() 083 { 084 return nestedExceptions.size(); 085 } 086 087 088 /** 089 * Tests to see if there are any nested exceptions within this 090 * MultiException. 091 * 092 * @return true if no exceptions are nested, false otherwise. 093 */ 094 public boolean isEmpty() 095 { 096 return nestedExceptions.isEmpty(); 097 } 098 099 100 /** 101 * Add an exception to this multiexception. 102 * 103 * @param nested exception to add to this MultiException. 104 */ 105 public void addThrowable( Throwable nested ) 106 { 107 nestedExceptions.add( nested ); 108 } 109 110 111 // /////////////////////////////////////////// 112 // Overriden Throwable Stack Trace Methods // 113 // /////////////////////////////////////////// 114 115 /** 116 * Beside printing out the standard stack trace this method prints out the 117 * stack traces of all the nested exceptions. 118 * 119 * @param out PrintWriter to write the nested stack trace to. 120 */ 121 @Override 122 public void printStackTrace( PrintWriter out ) 123 { 124 super.printStackTrace( out ); 125 126 out.println( "Nested exceptions to follow:\n" ); 127 boolean isFirst = true; 128 129 for ( Throwable throwable : nestedExceptions ) 130 { 131 if ( isFirst ) 132 { 133 isFirst = false; 134 } 135 else 136 { 137 out.println( "\n\t<<========= Next Nested Exception" + " ========>>\n" ); 138 } 139 140 throwable.printStackTrace( out ); 141 } 142 143 out.println( "\n\t<<========= Last Nested Exception" + " ========>>\n" ); 144 } 145 146 147 /** 148 * Beside printing out the standard stack trace this method prints out the 149 * stack traces of all the nested exceptions. 150 * 151 * @param out PrintStream to write the nested stack trace to. 152 */ 153 @Override 154 public void printStackTrace( PrintStream out ) 155 { 156 super.printStackTrace( out ); 157 158 out.println( "Nested exceptions to follow:\n" ); 159 boolean isFirst = true; 160 161 for ( Throwable throwable : nestedExceptions ) 162 { 163 if ( isFirst ) 164 { 165 isFirst = false; 166 } 167 else 168 { 169 out.println( "\n\t<<========= Next Nested Exception" + " ========>>\n" ); 170 } 171 172 throwable.printStackTrace( out ); 173 } 174 175 out.println( "\n\t<<========= Last Nested Exception" + " ========>>\n" ); 176 } 177 178 179 /** 180 * Beside printing out the standard stack trace this method prints out the 181 * stack traces of all the nested exceptions using standard error. 182 */ 183 @Override 184 public void printStackTrace() 185 { 186 this.printStackTrace( System.err ); 187 } 188}