1 // 2 // ======================================================================== 3 // Copyright (c) 1995-2016 Mort Bay Consulting Pty. Ltd. 4 // ------------------------------------------------------------------------ 5 // All rights reserved. This program and the accompanying materials 6 // are made available under the terms of the Eclipse Public License v1.0 7 // and Apache License v2.0 which accompanies this distribution. 8 // 9 // The Eclipse Public License is available at 10 // http://www.eclipse.org/legal/epl-v10.html 11 // 12 // The Apache License v2.0 is available at 13 // http://www.opensource.org/licenses/apache2.0.php 14 // 15 // You may elect to redistribute this code under either of these licenses. 16 // ======================================================================== 17 // 18 19 module hunt.http.codec.http.model.MultiException; 20 21 import hunt.container; 22 23 import hunt.lang.exception; 24 import hunt.string; 25 26 /** 27 * Wraps multiple exceptions. 28 * 29 * Allows multiple exceptions to be thrown as a single exception. 30 */ 31 // 32 class MultiException :Exception 33 { 34 private List!Exception nested; 35 36 /* ------------------------------------------------------------ */ 37 this() 38 { 39 super("Multiple exceptions"); 40 } 41 42 /* ------------------------------------------------------------ */ 43 void add(Exception e) 44 { 45 if (e is null) 46 throw new IllegalArgumentException(""); 47 48 if(nested is null) 49 { 50 // initCause(e); 51 nested = new ArrayList!Exception(); 52 } 53 // else 54 // addSuppressed(e); 55 56 if (typeid(e) == typeid(MultiException)) 57 { 58 MultiException me = cast(MultiException)e; 59 // nested.addAll(me.nested); 60 } 61 else 62 nested.add(e); 63 } 64 65 /* ------------------------------------------------------------ */ 66 int size() 67 { 68 return (nested is null)?0:nested.size(); 69 } 70 71 /* ------------------------------------------------------------ */ 72 List!Exception getThrowables() 73 { 74 if(nested is null) 75 return new EmptyList!Exception(); // Collections.emptyList(); 76 return nested; 77 } 78 79 /* ------------------------------------------------------------ */ 80 Exception getThrowable(int i) 81 { 82 return nested.get(i); 83 } 84 85 /* ------------------------------------------------------------ */ 86 /** Throw a multiexception. 87 * If this multi exception is empty then no action is taken. If it 88 * contains a single exception that is thrown, otherwise the this 89 * multi exception is thrown. 90 * @exception Exception the Error or Exception if nested is 1, or the MultiException itself if nested is more than 1. 91 */ 92 void ifExceptionThrow() 93 { 94 if(nested is null) 95 return; 96 97 switch (nested.size()) 98 { 99 case 0: 100 break; 101 case 1: 102 Exception th=nested.get(0); 103 if (typeid(th) == typeid(Error)) 104 throw cast(Error)th; 105 if (typeid(th) == typeid(Exception)) 106 throw cast(Exception)th; 107 break; 108 109 default: 110 throw this; 111 } 112 } 113 114 /* ------------------------------------------------------------ */ 115 /** Throw a Runtime exception. 116 * If this multi exception is empty then no action is taken. If it 117 * contains a single error or runtime exception that is thrown, otherwise the this 118 * multi exception is thrown, wrapped in a runtime onException. 119 * @exception Error If this exception contains exactly 1 {@link Error} 120 * @exception RuntimeException If this exception contains 1 {@link Exception} but it is not an error, 121 * or it contains more than 1 {@link Exception} of any type. 122 */ 123 void ifExceptionThrowRuntime() 124 { 125 if(nested is null) 126 return; 127 128 switch (nested.size()) 129 { 130 case 0: 131 break; 132 case 1: 133 Exception th=nested.get(0); 134 if (typeid(th) == typeid(Error)) 135 throw cast(Error)th; 136 else if (typeid(th) == typeid(RuntimeException)) 137 throw cast(RuntimeException)th; 138 else 139 throw new RuntimeException(th); 140 default: 141 throw new RuntimeException(this); 142 } 143 } 144 145 /* ------------------------------------------------------------ */ 146 /** Throw a multiexception. 147 * If this multi exception is empty then no action is taken. If it 148 * contains a any exceptions then this 149 * multi exception is thrown. 150 * @throws MultiException the multiexception if there are nested exception 151 */ 152 void ifExceptionThrowMulti() 153 { 154 if(nested is null) 155 return; 156 157 if (nested.size()>0) 158 throw this; 159 } 160 161 /* ------------------------------------------------------------ */ 162 override 163 string toString() 164 { 165 StringBuilder str = new StringBuilder(); 166 str.append(MultiException.stringof); 167 if((nested is null) || (nested.size()<=0)) { 168 str.append("[]"); 169 } else { 170 str.append(nested.toString()); 171 } 172 return str.toString(); 173 } 174 175 }