001/* 002 * jDTAUS Banking SPI 003 * Copyright (C) 2005 Christian Schulte 004 * <cs@schulte.it> 005 * 006 * This library is free software; you can redistribute it and/or 007 * modify it under the terms of the GNU Lesser General Public 008 * License as published by the Free Software Foundation; either 009 * version 2.1 of the License, or any later version. 010 * 011 * This library is distributed in the hope that it will be useful, 012 * but WITHOUT ANY WARRANTY; without even the implied warranty of 013 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 014 * Lesser General Public License for more details. 015 * 016 * You should have received a copy of the GNU Lesser General Public 017 * License along with this library; if not, write to the Free Software 018 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 019 * 020 */ 021package org.jdtaus.banking.dtaus.spi; 022 023import java.util.ArrayList; 024import java.util.HashMap; 025import java.util.Iterator; 026import java.util.LinkedList; 027import java.util.List; 028import java.util.Locale; 029import java.util.Map; 030import org.jdtaus.banking.dtaus.Transaction; 031import org.jdtaus.core.text.Message; 032import org.jdtaus.core.text.Messages; 033 034/** 035 * Gets thrown whenever an illegal transaction is passed to a method expecting a legal transaction. 036 * <p>Example: Throwing an {@code IllegalTransactionException}<br/><blockquote> 037 * <pre> 038 * IllegalTransactionException e = new IllegalTransactionException(); 039 * e.addMessage(message); 040 * e.addMessage(Transaction.PROP_<i>XYZ</i>, message); 041 * throw e;</pre></blockquote></p> 042 * 043 * @author <a href="mailto:cs@schulte.it">Christian Schulte</a> 044 * @version $JDTAUS: IllegalTransactionException.java 8661 2012-09-27 11:29:58Z schulte $ 045 */ 046public class IllegalTransactionException 047 extends org.jdtaus.banking.dtaus.IllegalTransactionException 048{ 049 050 /** Serial version UID for backwards compatibility with 1.0.x classes. */ 051 private static final long serialVersionUID = -81649021330912822L; 052 053 /** Creates a new {@code IllegalTransactionException} instance. */ 054 public IllegalTransactionException() 055 { 056 super(); 057 } 058 059 /** Key to the list of messages not bound to any particular property. */ 060 private static final String PROP_UNSPECIFIED = "org.jdtaus.banking.dtaus.Transaction"; 061 062 /** 063 * The messages describing the exception. 064 * @serial 065 */ 066 private Map messages = new HashMap(); 067 068 /** 069 * Adds a message to the instance. 070 * 071 * @param message The message to add to the instance. 072 * 073 * @throws NullPointerException if {@code message} is {@code null}. 074 */ 075 public void addMessage( final Message message ) 076 { 077 this.addMessage( PROP_UNSPECIFIED, message ); 078 } 079 080 /** 081 * Adds messages to the instance. 082 * 083 * @param messages The messages to add to the instance. 084 * 085 * @throws NullPointerException if {@code messages} is {@code null}. 086 */ 087 public final void addMessages( final Messages messages ) 088 { 089 if ( messages == null ) 090 { 091 throw new NullPointerException( "messages" ); 092 } 093 094 for ( int i = messages.size() - 1; i >= 0; i-- ) 095 { 096 this.addMessage( messages.getMessage( i ) ); 097 } 098 } 099 100 /** 101 * Adds a message for a property to the instance. 102 * 103 * @param propertyName The name of a property {@code message} is bound to. 104 * @param message The message to add to the instance. 105 * 106 * @throws NullPointerException if either {@code message} or {@code propertyName} is {@code null}. 107 */ 108 public void addMessage( final String propertyName, final Message message ) 109 { 110 if ( propertyName == null ) 111 { 112 throw new NullPointerException( "propertyName" ); 113 } 114 if ( message == null ) 115 { 116 throw new NullPointerException( "message" ); 117 } 118 119 List msgs = (List) this.messages.get( propertyName ); 120 if ( msgs == null ) 121 { 122 msgs = new LinkedList(); 123 this.messages.put( propertyName, msgs ); 124 } 125 126 msgs.add( message ); 127 } 128 129 /** 130 * Adds messages bound to a property to the instance. 131 * 132 * @param propertyName The name of a property {@code messages} are bound to. 133 * @param messages The messages to add to the instance. 134 * 135 * @throws NullPointerException if either {@code messages} or {@code propertyName} is {@code null}. 136 */ 137 public final void addMessages( final String propertyName, final Messages messages ) 138 { 139 if ( propertyName == null ) 140 { 141 throw new NullPointerException( "propertyName" ); 142 } 143 if ( messages == null ) 144 { 145 throw new NullPointerException( "messages" ); 146 } 147 148 for ( int i = messages.size() - 1; i >= 0; i-- ) 149 { 150 this.addMessage( propertyName, messages.getMessage( i ) ); 151 } 152 } 153 154 /** 155 * Gets all messages describing the exception. 156 * 157 * @return An array of messages describing the exception or an empty array if the instance does not hold any 158 * messages. 159 */ 160 public Message[] getMessages() 161 { 162 final List col = new LinkedList(); 163 for ( Iterator it = this.messages.keySet().iterator(); it.hasNext(); ) 164 { 165 final String propertyName = (String) it.next(); 166 col.addAll( (List) this.messages.get( propertyName ) ); 167 } 168 169 return (Message[]) col.toArray( new Message[ col.size() ] ); 170 } 171 172 /** 173 * Gets messages bound to a property removing these messages from the instance. 174 * 175 * @param propertyName the name of a property to return any messages for. 176 * 177 * @return All messages bound to a property with name {@code propertyName} or an empty array if the instance does 178 * not hold messages for a property with name {@code propertyName}. 179 * 180 * @throws NullPointerException if {@code propertyName} is {@code null}. 181 */ 182 public Message[] getMessages( final String propertyName ) 183 { 184 if ( propertyName == null ) 185 { 186 throw new NullPointerException( "propertyName" ); 187 } 188 189 final List msgs = (List) this.messages.remove( propertyName ); 190 return msgs == null ? new Message[ 0 ] : (Message[]) msgs.toArray( new Message[ msgs.size() ] ); 191 } 192 193 /** 194 * Gets the names of all properties for which the exception holds messages. 195 * 196 * @return An array of the names of all properties for which the exception holds messages or an empty array if the 197 * exception does not hold any message bound to a property. 198 */ 199 public String[] getPropertyNames() 200 { 201 final List names = new ArrayList( this.messages.size() ); 202 for ( Iterator it = this.messages.keySet().iterator(); it.hasNext(); ) 203 { 204 final String name = (String) it.next(); 205 if ( !PROP_UNSPECIFIED.equals( name ) ) 206 { 207 names.add( name ); 208 } 209 } 210 211 return (String[]) names.toArray( new String[ names.size() ] ); 212 } 213 214 /** 215 * Creates a string representing the messages of the instance. 216 * 217 * @return A string representing the messages of the instance. 218 */ 219 private String internalString() 220 { 221 final StringBuffer buf = new StringBuffer( 200 ).append( '{' ); 222 final String[] propertyNames = this.getPropertyNames(); 223 final List unspecifiedMsgs = (List) this.messages.get( PROP_UNSPECIFIED ); 224 225 for ( int i = 0; i < propertyNames.length; i++ ) 226 { 227 buf.append( propertyNames[i] ).append( "={" ); 228 229 int j = 0; 230 final List msgs = (List) this.messages.get( propertyNames[i] ); 231 for ( Iterator it = msgs.iterator(); it.hasNext(); j++ ) 232 { 233 final Message msg = (Message) it.next(); 234 buf.append( "[" ).append( j ).append( "]=" ).append( msg.getText( Locale.getDefault() ) ); 235 if ( it.hasNext() ) 236 { 237 buf.append( ", " ); 238 } 239 } 240 241 buf.append( '}' ); 242 243 if ( i + i < propertyNames.length ) 244 { 245 buf.append( ", " ); 246 } 247 } 248 249 if ( unspecifiedMsgs != null && !unspecifiedMsgs.isEmpty() ) 250 { 251 if ( propertyNames.length > 0 ) 252 { 253 buf.append( ", " ); 254 } 255 256 buf.append( PROP_UNSPECIFIED ).append( "={" ); 257 258 int i = 0; 259 for ( Iterator it = unspecifiedMsgs.iterator(); it.hasNext(); i++ ) 260 { 261 final Message msg = (Message) it.next(); 262 buf.append( "[" ).append( i ).append( "]=" ).append( msg.getText( Locale.getDefault() ) ); 263 if ( it.hasNext() ) 264 { 265 buf.append( ", " ); 266 } 267 } 268 269 buf.append( '}' ); 270 } 271 272 buf.append( '}' ); 273 return buf.toString(); 274 } 275 276 /** 277 * Returns a string representation of the object. 278 * 279 * @return A string representation of the object. 280 */ 281 public String toString() 282 { 283 return super.toString() + '\n' + this.internalString(); 284 } 285 286}