blob: 41be97c7081f609c8a5b767e1e701c838ebb3123 [file] [log] [blame]
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*
*/
package org.apache.directory.shared.ldap.util;
import java.io.Serializable;
import java.lang.reflect.Array;
import java.util.Collection;
import java.util.Map;
/**
* <p>
* Controls <code>String</code> formatting for {@link ToStringBuilder}. The
* main public interface is always via <code>ToStringBuilder</code>.
* </p>
* <p>
* These classes are intended to be used as <code>Singletons</code>. There is
* no need to instantiate a new style each time. A program will generally use
* one of the predefined constants on this class. Alternatively, the
* class can be used to set the individual settings. Thus most styles can be
* achieved without subclassing.
* </p>
* <p>
* If required, a subclass can override as many or as few of the methods as it
* requires. Each object type (from <code>boolean</code> to <code>long</code>
* to <code>Object</code> to <code>int[]</code>) has its own methods to
* output it. Most have two versions, detail and summary.
* <p>
* For example, the detail version of the array based methods will output the
* whole array, whereas the summary method will just output the array length.
* </p>
*
* @author <a href="mailto:dev@directory.apache.org">Apache Directory Project</a>
*/
public abstract class ToStringStyle implements Serializable
{
static final long serialVersionUID = -3594451267200535036L;
/**
* The default toString style.
*/
public static final ToStringStyle DEFAULT_STYLE = new DefaultToStringStyle();
/**
* The multi line toString style.
*/
public static final ToStringStyle MULTI_LINE_STYLE = new MultiLineToStringStyle();
/**
* The no field names toString style.
*/
public static final ToStringStyle NO_FIELD_NAMES_STYLE = new NoFieldNameToStringStyle();
/**
* The short prefix toString style.
*/
public static final ToStringStyle SHORT_PREFIX_STYLE = new ShortPrefixToStringStyle();
/**
* The simple toString style.
*/
public static final ToStringStyle SIMPLE_STYLE = new SimpleToStringStyle();
/**
* Whether to use the field names, the default is <code>true</code>.
*/
private boolean useFieldNames = true;
/**
* Whether to use the class name, the default is <code>true</code>.
*/
private boolean useClassName = true;
/**
* Whether to use short class names, the default is <code>false</code>.
*/
private boolean useShortClassName = false;
/**
* Whether to use the identity hash code, the default is <code>true</code>.
*/
private boolean useIdentityHashCode = true;
/**
* The content start <code>'['</code>.
*/
private String contentStart = "[";
/**
* The content end <code>']'</code>.
*/
private String contentEnd = "]";
/**
* The field name value separator <code>'='</code>.
*/
private String fieldNameValueSeparator = "=";
/**
* Whether the field separator should be added before any other fields.
*/
private boolean fieldSeparatorAtStart = false;
/**
* Whether the field separator should be added after any other fields.
*/
private boolean fieldSeparatorAtEnd = false;
/**
* The field separator <code>','</code>.
*/
private String fieldSeparator = ",";
/**
* The array start <code>'{'</code>.
*/
private String arrayStart = "{";
/**
* The array separator <code>','</code>.
*/
private String arraySeparator = ",";
/**
* The detail for array content.
*/
private boolean arrayContentDetail = true;
/**
* The array end <code>'}'</code>.
*/
private String arrayEnd = "}";
/**
* The value to use when fullDetail is <code>null</code>, the default
* value is <code>true</code>.
*/
private boolean defaultFullDetail = true;
/**
* The <code>null</code> text <code>'&lt;null&gt;'</code>.
*/
private String nullText = "<null>";
/**
* The summary size text start <code>'<size'</code>.
*/
private String sizeStartText = "<size=";
/**
* The summary size text start <code>'&gt;'</code>.
*/
private String sizeEndText = ">";
/**
* The summary object text start <code>'&lt;'</code>.
*/
private String summaryObjectStartText = "<";
/**
* The summary object text start <code>'&gt;'</code>.
*/
private String summaryObjectEndText = ">";
// ----------------------------------------------------------------------------
/**
* <p>
* Constructor.
* </p>
*/
protected ToStringStyle()
{
super();
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> the superclass toString.
* </p>
* <p>
* A <code>null</code> <code>superToString</code> is ignored.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param superToString
* the <code>super.toString()</code>
* @since 2.0
*/
public void appendSuper( StringBuffer buffer, String superToString )
{
appendToString( buffer, superToString );
}
/**
* <p>
* Append to the <code>toString</code> another toString.
* </p>
* <p>
* A <code>null</code> <code>toString</code> is ignored.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param toString
* the additional <code>toString</code>
* @since 2.0
*/
public void appendToString( StringBuffer buffer, String toString )
{
if ( toString != null )
{
int pos1 = toString.indexOf( contentStart ) + contentStart.length();
int pos2 = toString.lastIndexOf( contentEnd );
if ( pos1 != pos2 && pos1 >= 0 && pos2 >= 0 )
{
String data = toString.substring( pos1, pos2 );
if ( fieldSeparatorAtStart )
{
removeLastFieldSeparator( buffer );
}
buffer.append( data );
appendFieldSeparator( buffer );
}
}
}
/**
* <p>
* Append to the <code>toString</code> the start of data indicator.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param object
* the <code>Object</code> to build a <code>toString</code>
* for
*/
public void appendStart( StringBuffer buffer, Object object )
{
if ( object != null )
{
appendClassName( buffer, object );
appendIdentityHashCode( buffer, object );
appendContentStart( buffer );
if ( fieldSeparatorAtStart )
{
appendFieldSeparator( buffer );
}
}
}
/**
* <p>
* Append to the <code>toString</code> the end of data indicator.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param object
* the <code>Object</code> to build a <code>toString</code>
* for.
*/
public void appendEnd( StringBuffer buffer, Object object )
{
if ( this.fieldSeparatorAtEnd == false )
{
removeLastFieldSeparator( buffer );
}
appendContentEnd( buffer );
}
/**
* <p>
* Remove the last field separator from the buffer.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @since 2.0
*/
protected void removeLastFieldSeparator( StringBuffer buffer )
{
int len = buffer.length();
int sepLen = fieldSeparator.length();
if ( len > 0 && sepLen > 0 && len >= sepLen )
{
boolean match = true;
for ( int i = 0; i < sepLen; i++ )
{
if ( buffer.charAt( len - 1 - i ) != fieldSeparator.charAt( sepLen - 1 - i ) )
{
match = false;
break;
}
}
if ( match )
{
buffer.setLength( len - sepLen );
}
}
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> an <code>Object</code> value,
* printing the full <code>toString</code> of the <code>Object</code>
* passed in.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param value
* the value to add to the <code>toString</code>
* @param fullDetail
* <code>true</code> for detail, <code>false</code> for
* summary info, <code>null</code> for style decides
*/
public void append( StringBuffer buffer, String fieldName, Object value, Boolean fullDetail )
{
appendFieldStart( buffer, fieldName );
if ( value == null )
{
appendNullText( buffer, fieldName );
}
else
{
appendInternal( buffer, fieldName, value, isFullDetail( fullDetail ) );
}
appendFieldEnd( buffer, fieldName );
}
/**
* <p>
* Append to the <code>toString</code> an <code>Object</code>,
* correctly interpreting its type.
* </p>
* <p>
* This method performs the main lookup by Class type to correctly route
* arrays, <code>Collections</code>, <code>Maps</code> and
* <code>Objects</code> to the appropriate method.
* </p>
* <p>
* Either detail or summary views can be specified.
* </p>
* <p>
* If a cycle is detected, an object will be appended with the
* <code>Object.toString()</code> format.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param value
* the value to add to the <code>toString</code>, not
* <code>null</code>
* @param detail
* output detail or not
*/
protected void appendInternal( StringBuffer buffer, String fieldName, Object value, boolean detail )
{
if ( ReflectionToStringBuilder.isRegistered( value )
&& !( value instanceof Number || value instanceof Boolean || value instanceof Character ) )
{
ObjectUtils.appendIdentityToString( buffer, value );
}
else if ( value instanceof Collection )
{
if ( detail )
{
appendDetail( buffer, fieldName, ( Collection ) value );
}
else
{
appendSummarySize( buffer, fieldName, ( ( Collection ) value ).size() );
}
}
else if ( value instanceof Map )
{
if ( detail )
{
appendDetail( buffer, fieldName, ( Map ) value );
}
else
{
appendSummarySize( buffer, fieldName, ( ( Map ) value ).size() );
}
}
else if ( value instanceof long[] )
{
if ( detail )
{
appendDetail( buffer, fieldName, ( long[] ) value );
}
else
{
appendSummary( buffer, fieldName, ( long[] ) value );
}
}
else if ( value instanceof int[] )
{
if ( detail )
{
appendDetail( buffer, fieldName, ( int[] ) value );
}
else
{
appendSummary( buffer, fieldName, ( int[] ) value );
}
}
else if ( value instanceof short[] )
{
if ( detail )
{
appendDetail( buffer, fieldName, ( short[] ) value );
}
else
{
appendSummary( buffer, fieldName, ( short[] ) value );
}
}
else if ( value instanceof byte[] )
{
if ( detail )
{
appendDetail( buffer, fieldName, ( byte[] ) value );
}
else
{
appendSummary( buffer, fieldName, ( byte[] ) value );
}
}
else if ( value instanceof char[] )
{
if ( detail )
{
appendDetail( buffer, fieldName, ( char[] ) value );
}
else
{
appendSummary( buffer, fieldName, ( char[] ) value );
}
}
else if ( value instanceof double[] )
{
if ( detail )
{
appendDetail( buffer, fieldName, ( double[] ) value );
}
else
{
appendSummary( buffer, fieldName, ( double[] ) value );
}
}
else if ( value instanceof float[] )
{
if ( detail )
{
appendDetail( buffer, fieldName, ( float[] ) value );
}
else
{
appendSummary( buffer, fieldName, ( float[] ) value );
}
}
else if ( value instanceof boolean[] )
{
if ( detail )
{
appendDetail( buffer, fieldName, ( boolean[] ) value );
}
else
{
appendSummary( buffer, fieldName, ( boolean[] ) value );
}
}
else if ( value.getClass().isArray() )
{
if ( detail )
{
appendDetail( buffer, fieldName, ( Object[] ) value );
}
else
{
appendSummary( buffer, fieldName, ( Object[] ) value );
}
}
else
{
if ( detail )
{
appendDetail( buffer, fieldName, value );
}
else
{
appendSummary( buffer, fieldName, value );
}
}
}
/**
* <p>
* Append to the <code>toString</code> an <code>Object</code> value,
* printing the full detail of the <code>Object</code>.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param value
* the value to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, Object value )
{
buffer.append( value );
}
/**
* <p>
* Append to the <code>toString</code> a <code>Collection</code>.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param coll
* the <code>Collection</code> to add to the
* <code>toString</code>, not <code>null</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, Collection coll )
{
buffer.append( coll );
}
/**
* <p>
* Append to the <code>toString</code> a <code>Map<code>.</p>
*
* @param buffer the <code>StringBuffer</code> to populate
* @param fieldName the field name, typically not used as already appended
* @param map the <code>Map</code> to add to the <code>toString</code>,
* not <code>null</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, Map map )
{
buffer.append( map );
}
/**
* <p>
* Append to the <code>toString</code> an <code>Object</code> value,
* printing a summary of the <code>Object</code>.
* </P>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param value
* the value to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendSummary( StringBuffer buffer, String fieldName, Object value )
{
buffer.append( summaryObjectStartText );
buffer.append( getShortClassName( value.getClass() ) );
buffer.append( summaryObjectEndText );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> a <code>long</code> value.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param value
* the value to add to the <code>toString</code>
*/
public void append( StringBuffer buffer, String fieldName, long value )
{
appendFieldStart( buffer, fieldName );
appendDetail( buffer, fieldName, value );
appendFieldEnd( buffer, fieldName );
}
/**
* <p>
* Append to the <code>toString</code> a <code>long</code> value.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param value
* the value to add to the <code>toString</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, long value )
{
buffer.append( value );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> an <code>int</code> value.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param value
* the value to add to the <code>toString</code>
*/
public void append( StringBuffer buffer, String fieldName, int value )
{
appendFieldStart( buffer, fieldName );
appendDetail( buffer, fieldName, value );
appendFieldEnd( buffer, fieldName );
}
/**
* <p>
* Append to the <code>toString</code> an <code>int</code> value.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param value
* the value to add to the <code>toString</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, int value )
{
buffer.append( value );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> a <code>short</code> value.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param value
* the value to add to the <code>toString</code>
*/
public void append( StringBuffer buffer, String fieldName, short value )
{
appendFieldStart( buffer, fieldName );
appendDetail( buffer, fieldName, value );
appendFieldEnd( buffer, fieldName );
}
/**
* <p>
* Append to the <code>toString</code> a <code>short</code> value.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param value
* the value to add to the <code>toString</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, short value )
{
buffer.append( value );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> a <code>byte</code> value.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param value
* the value to add to the <code>toString</code>
*/
public void append( StringBuffer buffer, String fieldName, byte value )
{
appendFieldStart( buffer, fieldName );
appendDetail( buffer, fieldName, value );
appendFieldEnd( buffer, fieldName );
}
/**
* <p>
* Append to the <code>toString</code> a <code>byte</code> value.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param value
* the value to add to the <code>toString</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, byte value )
{
buffer.append( value );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> a <code>char</code> value.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param value
* the value to add to the <code>toString</code>
*/
public void append( StringBuffer buffer, String fieldName, char value )
{
appendFieldStart( buffer, fieldName );
appendDetail( buffer, fieldName, value );
appendFieldEnd( buffer, fieldName );
}
/**
* <p>
* Append to the <code>toString</code> a <code>char</code> value.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param value
* the value to add to the <code>toString</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, char value )
{
buffer.append( value );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> a <code>double</code> value.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param value
* the value to add to the <code>toString</code>
*/
public void append( StringBuffer buffer, String fieldName, double value )
{
appendFieldStart( buffer, fieldName );
appendDetail( buffer, fieldName, value );
appendFieldEnd( buffer, fieldName );
}
/**
* <p>
* Append to the <code>toString</code> a <code>double</code> value.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param value
* the value to add to the <code>toString</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, double value )
{
buffer.append( value );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> a <code>float</code> value.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param value
* the value to add to the <code>toString</code>
*/
public void append( StringBuffer buffer, String fieldName, float value )
{
appendFieldStart( buffer, fieldName );
appendDetail( buffer, fieldName, value );
appendFieldEnd( buffer, fieldName );
}
/**
* <p>
* Append to the <code>toString</code> a <code>float</code> value.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param value
* the value to add to the <code>toString</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, float value )
{
buffer.append( value );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> a <code>boolean</code> value.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param value
* the value to add to the <code>toString</code>
*/
public void append( StringBuffer buffer, String fieldName, boolean value )
{
appendFieldStart( buffer, fieldName );
appendDetail( buffer, fieldName, value );
appendFieldEnd( buffer, fieldName );
}
/**
* <p>
* Append to the <code>toString</code> a <code>boolean</code> value.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param value
* the value to add to the <code>toString</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, boolean value )
{
buffer.append( value );
}
/**
* <p>
* Append to the <code>toString</code> an <code>Object</code> array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param array
* the array to add to the toString
* @param fullDetail
* <code>true</code> for detail, <code>false</code> for
* summary info, <code>null</code> for style decides
*/
public void append( StringBuffer buffer, String fieldName, Object[] array, Boolean fullDetail )
{
appendFieldStart( buffer, fieldName );
if ( array == null )
{
appendNullText( buffer, fieldName );
}
else if ( isFullDetail( fullDetail ) )
{
appendDetail( buffer, fieldName, array );
}
else
{
appendSummary( buffer, fieldName, array );
}
appendFieldEnd( buffer, fieldName );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> the detail of an
* <code>Object</code> array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, Object[] array )
{
buffer.append( arrayStart );
for ( int i = 0; i < array.length; i++ )
{
Object item = array[i];
if ( i > 0 )
{
buffer.append( arraySeparator );
}
if ( item == null )
{
appendNullText( buffer, fieldName );
}
else
{
appendInternal( buffer, fieldName, item, arrayContentDetail );
}
}
buffer.append( arrayEnd );
}
/**
* <p>
* Append to the <code>toString</code> the detail of an array type.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
* @since 2.0
*/
protected void reflectionAppendArrayDetail( StringBuffer buffer, String fieldName, Object array )
{
buffer.append( arrayStart );
int length = Array.getLength( array );
for ( int i = 0; i < length; i++ )
{
Object item = Array.get( array, i );
if ( i > 0 )
{
buffer.append( arraySeparator );
}
if ( item == null )
{
appendNullText( buffer, fieldName );
}
else
{
appendInternal( buffer, fieldName, item, arrayContentDetail );
}
}
buffer.append( arrayEnd );
}
/**
* <p>
* Append to the <code>toString</code> a summary of an <code>Object</code>
* array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendSummary( StringBuffer buffer, String fieldName, Object[] array )
{
appendSummarySize( buffer, fieldName, array.length );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> a <code>long</code> array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param array
* the array to add to the <code>toString</code>
* @param fullDetail
* <code>true</code> for detail, <code>false</code> for
* summary info, <code>null</code> for style decides
*/
public void append( StringBuffer buffer, String fieldName, long[] array, Boolean fullDetail )
{
appendFieldStart( buffer, fieldName );
if ( array == null )
{
appendNullText( buffer, fieldName );
}
else if ( isFullDetail( fullDetail ) )
{
appendDetail( buffer, fieldName, array );
}
else
{
appendSummary( buffer, fieldName, array );
}
appendFieldEnd( buffer, fieldName );
}
/**
* <p>
* Append to the <code>toString</code> the detail of a <code>long</code>
* array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, long[] array )
{
buffer.append( arrayStart );
for ( int i = 0; i < array.length; i++ )
{
if ( i > 0 )
{
buffer.append( arraySeparator );
}
appendDetail( buffer, fieldName, array[i] );
}
buffer.append( arrayEnd );
}
/**
* <p>
* Append to the <code>toString</code> a summary of a <code>long</code>
* array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendSummary( StringBuffer buffer, String fieldName, long[] array )
{
appendSummarySize( buffer, fieldName, array.length );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> an <code>int</code> array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param array
* the array to add to the <code>toString</code>
* @param fullDetail
* <code>true</code> for detail, <code>false</code> for
* summary info, <code>null</code> for style decides
*/
public void append( StringBuffer buffer, String fieldName, int[] array, Boolean fullDetail )
{
appendFieldStart( buffer, fieldName );
if ( array == null )
{
appendNullText( buffer, fieldName );
}
else if ( isFullDetail( fullDetail ) )
{
appendDetail( buffer, fieldName, array );
}
else
{
appendSummary( buffer, fieldName, array );
}
appendFieldEnd( buffer, fieldName );
}
/**
* <p>
* Append to the <code>toString</code> the detail of an <code>int</code>
* array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, int[] array )
{
buffer.append( arrayStart );
for ( int i = 0; i < array.length; i++ )
{
if ( i > 0 )
{
buffer.append( arraySeparator );
}
appendDetail( buffer, fieldName, array[i] );
}
buffer.append( arrayEnd );
}
/**
* <p>
* Append to the <code>toString</code> a summary of an <code>int</code>
* array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendSummary( StringBuffer buffer, String fieldName, int[] array )
{
appendSummarySize( buffer, fieldName, array.length );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> a <code>short</code> array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param array
* the array to add to the <code>toString</code>
* @param fullDetail
* <code>true</code> for detail, <code>false</code> for
* summary info, <code>null</code> for style decides
*/
public void append( StringBuffer buffer, String fieldName, short[] array, Boolean fullDetail )
{
appendFieldStart( buffer, fieldName );
if ( array == null )
{
appendNullText( buffer, fieldName );
}
else if ( isFullDetail( fullDetail ) )
{
appendDetail( buffer, fieldName, array );
}
else
{
appendSummary( buffer, fieldName, array );
}
appendFieldEnd( buffer, fieldName );
}
/**
* <p>
* Append to the <code>toString</code> the detail of a <code>short</code>
* array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, short[] array )
{
buffer.append( arrayStart );
for ( int i = 0; i < array.length; i++ )
{
if ( i > 0 )
{
buffer.append( arraySeparator );
}
appendDetail( buffer, fieldName, array[i] );
}
buffer.append( arrayEnd );
}
/**
* <p>
* Append to the <code>toString</code> a summary of a <code>short</code>
* array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendSummary( StringBuffer buffer, String fieldName, short[] array )
{
appendSummarySize( buffer, fieldName, array.length );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> a <code>byte</code> array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param array
* the array to add to the <code>toString</code>
* @param fullDetail
* <code>true</code> for detail, <code>false</code> for
* summary info, <code>null</code> for style decides
*/
public void append( StringBuffer buffer, String fieldName, byte[] array, Boolean fullDetail )
{
appendFieldStart( buffer, fieldName );
if ( array == null )
{
appendNullText( buffer, fieldName );
}
else if ( isFullDetail( fullDetail ) )
{
appendDetail( buffer, fieldName, array );
}
else
{
appendSummary( buffer, fieldName, array );
}
appendFieldEnd( buffer, fieldName );
}
/**
* <p>
* Append to the <code>toString</code> the detail of a <code>byte</code>
* array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, byte[] array )
{
buffer.append( arrayStart );
for ( int i = 0; i < array.length; i++ )
{
if ( i > 0 )
{
buffer.append( arraySeparator );
}
appendDetail( buffer, fieldName, array[i] );
}
buffer.append( arrayEnd );
}
/**
* <p>
* Append to the <code>toString</code> a summary of a <code>byte</code>
* array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendSummary( StringBuffer buffer, String fieldName, byte[] array )
{
appendSummarySize( buffer, fieldName, array.length );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> a <code>char</code> array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param array
* the array to add to the <code>toString</code>
* @param fullDetail
* <code>true</code> for detail, <code>false</code> for
* summary info, <code>null</code> for style decides
*/
public void append( StringBuffer buffer, String fieldName, char[] array, Boolean fullDetail )
{
appendFieldStart( buffer, fieldName );
if ( array == null )
{
appendNullText( buffer, fieldName );
}
else if ( isFullDetail( fullDetail ) )
{
appendDetail( buffer, fieldName, array );
}
else
{
appendSummary( buffer, fieldName, array );
}
appendFieldEnd( buffer, fieldName );
}
/**
* <p>
* Append to the <code>toString</code> the detail of a <code>char</code>
* array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, char[] array )
{
buffer.append( arrayStart );
for ( int i = 0; i < array.length; i++ )
{
if ( i > 0 )
{
buffer.append( arraySeparator );
}
appendDetail( buffer, fieldName, array[i] );
}
buffer.append( arrayEnd );
}
/**
* <p>
* Append to the <code>toString</code> a summary of a <code>char</code>
* array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendSummary( StringBuffer buffer, String fieldName, char[] array )
{
appendSummarySize( buffer, fieldName, array.length );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> a <code>double</code> array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param array
* the array to add to the toString
* @param fullDetail
* <code>true</code> for detail, <code>false</code> for
* summary info, <code>null</code> for style decides
*/
public void append( StringBuffer buffer, String fieldName, double[] array, Boolean fullDetail )
{
appendFieldStart( buffer, fieldName );
if ( array == null )
{
appendNullText( buffer, fieldName );
}
else if ( isFullDetail( fullDetail ) )
{
appendDetail( buffer, fieldName, array );
}
else
{
appendSummary( buffer, fieldName, array );
}
appendFieldEnd( buffer, fieldName );
}
/**
* <p>
* Append to the <code>toString</code> the detail of a <code>double</code>
* array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, double[] array )
{
buffer.append( arrayStart );
for ( int i = 0; i < array.length; i++ )
{
if ( i > 0 )
{
buffer.append( arraySeparator );
}
appendDetail( buffer, fieldName, array[i] );
}
buffer.append( arrayEnd );
}
/**
* <p>
* Append to the <code>toString</code> a summary of a <code>double</code>
* array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendSummary( StringBuffer buffer, String fieldName, double[] array )
{
appendSummarySize( buffer, fieldName, array.length );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> a <code>float</code> array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param array
* the array to add to the toString
* @param fullDetail
* <code>true</code> for detail, <code>false</code> for
* summary info, <code>null</code> for style decides
*/
public void append( StringBuffer buffer, String fieldName, float[] array, Boolean fullDetail )
{
appendFieldStart( buffer, fieldName );
if ( array == null )
{
appendNullText( buffer, fieldName );
}
else if ( isFullDetail( fullDetail ) )
{
appendDetail( buffer, fieldName, array );
}
else
{
appendSummary( buffer, fieldName, array );
}
appendFieldEnd( buffer, fieldName );
}
/**
* <p>
* Append to the <code>toString</code> the detail of a <code>float</code>
* array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, float[] array )
{
buffer.append( arrayStart );
for ( int i = 0; i < array.length; i++ )
{
if ( i > 0 )
{
buffer.append( arraySeparator );
}
appendDetail( buffer, fieldName, array[i] );
}
buffer.append( arrayEnd );
}
/**
* <p>
* Append to the <code>toString</code> a summary of a <code>float</code>
* array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendSummary( StringBuffer buffer, String fieldName, float[] array )
{
appendSummarySize( buffer, fieldName, array.length );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> a <code>boolean</code> array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
* @param array
* the array to add to the toString
* @param fullDetail
* <code>true</code> for detail, <code>false</code> for
* summary info, <code>null</code> for style decides
*/
public void append( StringBuffer buffer, String fieldName, boolean[] array, Boolean fullDetail )
{
appendFieldStart( buffer, fieldName );
if ( array == null )
{
appendNullText( buffer, fieldName );
}
else if ( isFullDetail( fullDetail ) )
{
appendDetail( buffer, fieldName, array );
}
else
{
appendSummary( buffer, fieldName, array );
}
appendFieldEnd( buffer, fieldName );
}
/**
* <p>
* Append to the <code>toString</code> the detail of a
* <code>boolean</code> array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendDetail( StringBuffer buffer, String fieldName, boolean[] array )
{
buffer.append( arrayStart );
for ( int i = 0; i < array.length; i++ )
{
if ( i > 0 )
{
buffer.append( arraySeparator );
}
appendDetail( buffer, fieldName, array[i] );
}
buffer.append( arrayEnd );
}
/**
* <p>
* Append to the <code>toString</code> a summary of a <code>boolean</code>
* array.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
* @param array
* the array to add to the <code>toString</code>, not
* <code>null</code>
*/
protected void appendSummary( StringBuffer buffer, String fieldName, boolean[] array )
{
appendSummarySize( buffer, fieldName, array.length );
}
// ----------------------------------------------------------------------------
/**
* <p>
* Append to the <code>toString</code> the class name.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param object
* the <code>Object</code> whose name to output
*/
protected void appendClassName( StringBuffer buffer, Object object )
{
if ( useClassName && object != null )
{
if ( useShortClassName )
{
buffer.append( getShortClassName( object.getClass() ) );
}
else
{
buffer.append( object.getClass().getName() );
}
}
}
/**
* <p>
* Append the {@link System#identityHashCode(java.lang.Object)}.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param object
* the <code>Object</code> whose id to output
*/
protected void appendIdentityHashCode( StringBuffer buffer, Object object )
{
if ( this.isUseIdentityHashCode() && object != null )
{
buffer.append( '@' );
buffer.append( Integer.toHexString( System.identityHashCode( object ) ) );
}
}
/**
* <p>
* Append to the <code>toString</code> the content start.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
*/
protected void appendContentStart( StringBuffer buffer )
{
buffer.append( contentStart );
}
/**
* <p>
* Append to the <code>toString</code> the content end.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
*/
protected void appendContentEnd( StringBuffer buffer )
{
buffer.append( contentEnd );
}
/**
* <p>
* Append to the <code>toString</code> an indicator for <code>null</code>.
* </p>
* <p>
* The default indicator is <code>'&lt;null&gt;'</code>.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name, typically not used as already appended
*/
protected void appendNullText( StringBuffer buffer, String fieldName )
{
buffer.append( nullText );
}
/**
* <p>
* Append to the <code>toString</code> the field separator.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
*/
protected void appendFieldSeparator( StringBuffer buffer )
{
buffer.append( fieldSeparator );
}
/**
* <p>
* Append to the <code>toString</code> the field start.
* </p>
*
* @param buffer
* the <code>StringBuffer</code> to populate
* @param fieldName
* the field name
*/
protected void appendFieldStart( StringBuffer buffer, String fieldName )
{
if ( useFieldNames && fieldName != null )
{
buffer.append( fieldName );
buffer.append( fieldNameValueSeparator );
}
}
/**
* <p>
* Append to the <code>toString<code> the field end.</p>
*
* @param buffer the <code>StringBuffer</code> to populate
* @param fieldName the field name, typically not used as already appended
*/
protected void appendFieldEnd( StringBuffer buffer, String fieldName )
{
appendFieldSeparator( buffer );
}
/**
* <p>
* Append to the <code>toString</code> a size summary.
* </p>
* <p>
* The size summary is used to summarize the contents of
* <code>Collections</code>, <code>Maps</code> and arrays.
* </p>
* <p>
* The output consists of a prefix, the passed in size and a suffix.
* </p>
* <p>
* The default format is <code>'&lt;size=n&gt;'<code>.</p>
*
* @param buffer the <code>StringBuffer</code> to populate
* @param fieldName the field name, typically not used as already appended
* @param size the size to append
*/
protected void appendSummarySize( StringBuffer buffer, String fieldName, int size )
{
buffer.append( sizeStartText );
buffer.append( size );
buffer.append( sizeEndText );
}
/**
* <p>
* Is this field to be output in full detail.
* </p>
* <p>
* This method converts a detail request into a detail level. The calling
* code may request full detail (<code>true</code>), but a subclass
* might ignore that and always return <code>false</code>. The calling
* code may pass in <code>null</code> indicating that it doesn't care
* about the detail level. In this case the default detail level is used.
* </p>
*
* @param fullDetailRequest
* the detail level requested
* @return whether full detail is to be shown
*/
protected boolean isFullDetail( Boolean fullDetailRequest )
{
if ( fullDetailRequest == null )
{
return defaultFullDetail;
}
return fullDetailRequest.booleanValue();
}
/**
* <p>
* Gets the short class name for a class.
* </p>
* <p>
* The short class name is the classname excluding the package name.
* </p>
*
* @param cls
* the <code>Class</code> to get the short name of
* @return the short name
*/
protected String getShortClassName( Class cls )
{
return ClassUtils.getShortClassName( cls );
}
// Setters and getters for the customizable parts of the style
// These methods are not expected to be overridden, except to make public
// (They are not public so that immutable subclasses can be written)
// ---------------------------------------------------------------------
/**
* <p>
* Gets whether to use the class name.
* </p>
*
* @return the current useClassName flag
*/
protected boolean isUseClassName()
{
return useClassName;
}
/**
* <p>
* Sets whether to use the class name.
* </p>
*
* @param useClassName
* the new useClassName flag
*/
protected void setUseClassName( boolean useClassName )
{
this.useClassName = useClassName;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets whether to output short or long class names.
* </p>
*
* @return the current useShortClassName flag
* @since 2.0
*/
protected boolean isUseShortClassName()
{
return useShortClassName;
}
/**
* <p>
* Gets whether to output short or long class names.
* </p>
*
* @return the current shortClassName flag
* @deprecated Use {@link #isUseShortClassName()} Method will be removed in
* Commons Lang 3.0.
*/
protected boolean isShortClassName()
{
return useShortClassName;
}
/**
* <p>
* Sets whether to output short or long class names.
* </p>
*
* @param useShortClassName
* the new useShortClassName flag
* @since 2.0
*/
protected void setUseShortClassName( boolean useShortClassName )
{
this.useShortClassName = useShortClassName;
}
/**
* <p>
* Sets whether to output short or long class names.
* </p>
*
* @param shortClassName
* the new shortClassName flag
* @deprecated Use {@link #setUseShortClassName(boolean)} Method will be
* removed in Commons Lang 3.0.
*/
protected void setShortClassName( boolean shortClassName )
{
this.useShortClassName = shortClassName;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets whether to use the identity hash code.
* </p>
*
* @return the current useIdentityHashCode flag
*/
protected boolean isUseIdentityHashCode()
{
return useIdentityHashCode;
}
/**
* <p>
* Sets whether to use the identity hash code.
* </p>
*
* @param useIdentityHashCode
* the new useIdentityHashCode flag
*/
protected void setUseIdentityHashCode( boolean useIdentityHashCode )
{
this.useIdentityHashCode = useIdentityHashCode;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets whether to use the field names passed in.
* </p>
*
* @return the current useFieldNames flag
*/
protected boolean isUseFieldNames()
{
return useFieldNames;
}
/**
* <p>
* Sets whether to use the field names passed in.
* </p>
*
* @param useFieldNames
* the new useFieldNames flag
*/
protected void setUseFieldNames( boolean useFieldNames )
{
this.useFieldNames = useFieldNames;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets whether to use full detail when the caller doesn't specify.
* </p>
*
* @return the current defaultFullDetail flag
*/
protected boolean isDefaultFullDetail()
{
return defaultFullDetail;
}
/**
* <p>
* Sets whether to use full detail when the caller doesn't specify.
* </p>
*
* @param defaultFullDetail
* the new defaultFullDetail flag
*/
protected void setDefaultFullDetail( boolean defaultFullDetail )
{
this.defaultFullDetail = defaultFullDetail;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets whether to output array content detail.
* </p>
*
* @return the current array content detail setting
*/
protected boolean isArrayContentDetail()
{
return arrayContentDetail;
}
/**
* <p>
* Sets whether to output array content detail.
* </p>
*
* @param arrayContentDetail
* the new arrayContentDetail flag
*/
protected void setArrayContentDetail( boolean arrayContentDetail )
{
this.arrayContentDetail = arrayContentDetail;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets the array start text.
* </p>
*
* @return the current array start text
*/
protected String getArrayStart()
{
return arrayStart;
}
/**
* <p>
* Sets the array start text.
* </p>
* <p>
* <code>null</code> is accepted, but will be converted to an empty
* String.
* </p>
*
* @param arrayStart
* the new array start text
*/
protected void setArrayStart( String arrayStart )
{
if ( arrayStart == null )
{
arrayStart = "";
}
this.arrayStart = arrayStart;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets the array end text.
* </p>
*
* @return the current array end text
*/
protected String getArrayEnd()
{
return arrayEnd;
}
/**
* <p>
* Sets the array end text.
* </p>
* <p>
* <code>null</code> is accepted, but will be converted to an empty
* String.
* </p>
*
* @param arrayEnd
* the new array end text
*/
protected void setArrayEnd( String arrayEnd )
{
if ( arrayStart == null )
{
arrayStart = "";
}
this.arrayEnd = arrayEnd;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets the array separator text.
* </p>
*
* @return the current array separator text
*/
protected String getArraySeparator()
{
return arraySeparator;
}
/**
* <p>
* Sets the array separator text.
* </p>
* <p>
* <code>null</code> is accepted, but will be converted to an empty
* String.
* </p>
*
* @param arraySeparator
* the new array separator text
*/
protected void setArraySeparator( String arraySeparator )
{
if ( arraySeparator == null )
{
arraySeparator = "";
}
this.arraySeparator = arraySeparator;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets the content start text.
* </p>
*
* @return the current content start text
*/
protected String getContentStart()
{
return contentStart;
}
/**
* <p>
* Sets the content start text.
* </p>
* <p>
* <code>null</code> is accepted, but will be converted to an empty
* String.
* </p>
*
* @param contentStart
* the new content start text
*/
protected void setContentStart( String contentStart )
{
if ( contentStart == null )
{
contentStart = "";
}
this.contentStart = contentStart;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets the content end text.
* </p>
*
* @return the current content end text
*/
protected String getContentEnd()
{
return contentEnd;
}
/**
* <p>
* Sets the content end text.
* </p>
* <p>
* <code>null</code> is accepted, but will be converted to an empty
* String.
* </p>
*
* @param contentEnd
* the new content end text
*/
protected void setContentEnd( String contentEnd )
{
if ( contentEnd == null )
{
contentEnd = "";
}
this.contentEnd = contentEnd;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets the field name value separator text.
* </p>
*
* @return the current field name value separator text
*/
protected String getFieldNameValueSeparator()
{
return fieldNameValueSeparator;
}
/**
* <p>
* Sets the field name value separator text.
* </p>
* <p>
* <code>null</code> is accepted, but will be converted to an empty
* String.
* </p>
*
* @param fieldNameValueSeparator
* the new field name value separator text
*/
protected void setFieldNameValueSeparator( String fieldNameValueSeparator )
{
if ( fieldNameValueSeparator == null )
{
fieldNameValueSeparator = "";
}
this.fieldNameValueSeparator = fieldNameValueSeparator;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets the field separator text.
* </p>
*
* @return the current field separator text
*/
protected String getFieldSeparator()
{
return fieldSeparator;
}
/**
* <p>
* Sets the field separator text.
* </p>
* <p>
* <code>null</code> is accepted, but will be converted to an empty
* String.
* </p>
*
* @param fieldSeparator
* the new field separator text
*/
protected void setFieldSeparator( String fieldSeparator )
{
if ( fieldSeparator == null )
{
fieldSeparator = "";
}
this.fieldSeparator = fieldSeparator;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets whether the field separator should be added at the start of each
* buffer.
* </p>
*
* @return the fieldSeparatorAtStart flag
* @since 2.0
*/
protected boolean isFieldSeparatorAtStart()
{
return fieldSeparatorAtStart;
}
/**
* <p>
* Sets whether the field separator should be added at the start of each
* buffer.
* </p>
*
* @param fieldSeparatorAtStart
* the fieldSeparatorAtStart flag
* @since 2.0
*/
protected void setFieldSeparatorAtStart( boolean fieldSeparatorAtStart )
{
this.fieldSeparatorAtStart = fieldSeparatorAtStart;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets whether the field separator should be added at the end of each
* buffer.
* </p>
*
* @return fieldSeparatorAtEnd flag
* @since 2.0
*/
protected boolean isFieldSeparatorAtEnd()
{
return fieldSeparatorAtEnd;
}
/**
* <p>
* Sets whether the field separator should be added at the end of each
* buffer.
* </p>
*
* @param fieldSeparatorAtEnd
* the fieldSeparatorAtEnd flag
* @since 2.0
*/
protected void setFieldSeparatorAtEnd( boolean fieldSeparatorAtEnd )
{
this.fieldSeparatorAtEnd = fieldSeparatorAtEnd;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets the text to output when <code>null</code> found.
* </p>
*
* @return the current text to output when null found
*/
protected String getNullText()
{
return nullText;
}
/**
* <p>
* Sets the text to output when <code>null</code> found.
* </p>
* <p>
* <code>null</code> is accepted, but will be converted to an empty
* String.
* </p>
*
* @param nullText
* the new text to output when null found
*/
protected void setNullText( String nullText )
{
if ( nullText == null )
{
nullText = "";
}
this.nullText = nullText;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets the start text to output when a <code>Collection</code>,
* <code>Map</code> or array size is output.
* </p>
* <p>
* This is output before the size value.
* </p>
*
* @return the current start of size text
*/
protected String getSizeStartText()
{
return sizeStartText;
}
/**
* <p>
* Sets the start text to output when a <code>Collection</code>,
* <code>Map</code> or array size is output.
* </p>
* <p>
* This is output before the size value.
* </p>
* <p>
* <code>null</code> is accepted, but will be converted to an empty
* String.
* </p>
*
* @param sizeStartText
* the new start of size text
*/
protected void setSizeStartText( String sizeStartText )
{
if ( sizeStartText == null )
{
sizeStartText = "";
}
this.sizeStartText = sizeStartText;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets the end text to output when a <code>Collection</code>,
* <code>Map</code> or array size is output.
* </p>
* <p>
* This is output after the size value.
* </p>
*
* @return the current end of size text
*/
protected String getSizeEndText()
{
return sizeEndText;
}
/**
* <p>
* Sets the end text to output when a <code>Collection</code>,
* <code>Map</code> or array size is output.
* </p>
* <p>
* This is output after the size value.
* </p>
* <p>
* <code>null</code> is accepted, but will be converted to an empty
* String.
* </p>
*
* @param sizeEndText
* the new end of size text
*/
protected void setSizeEndText( String sizeEndText )
{
if ( sizeEndText == null )
{
sizeEndText = "";
}
this.sizeEndText = sizeEndText;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets the start text to output when an <code>Object</code> is output in
* summary mode.
* </p>
* <p>
* This is output before the size value.
* </p>
*
* @return the current start of summary text
*/
protected String getSummaryObjectStartText()
{
return summaryObjectStartText;
}
/**
* <p>
* Sets the start text to output when an <code>Object</code> is output in
* summary mode.
* </p>
* <p>
* This is output before the size value.
* </p>
* <p>
* <code>null</code> is accepted, but will be converted to an empty
* String.
* </p>
*
* @param summaryObjectStartText
* the new start of summary text
*/
protected void setSummaryObjectStartText( String summaryObjectStartText )
{
if ( summaryObjectStartText == null )
{
summaryObjectStartText = "";
}
this.summaryObjectStartText = summaryObjectStartText;
}
// ---------------------------------------------------------------------
/**
* <p>
* Gets the end text to output when an <code>Object</code> is output in
* summary mode.
* </p>
* <p>
* This is output after the size value.
* </p>
*
* @return the current end of summary text
*/
protected String getSummaryObjectEndText()
{
return summaryObjectEndText;
}
/**
* <p>
* Sets the end text to output when an <code>Object</code> is output in
* summary mode.
* </p>
* <p>
* This is output after the size value.
* </p>
* <p>
* <code>null</code> is accepted, but will be converted to an empty
* String.
* </p>
*
* @param summaryObjectEndText
* the new end of summary text
*/
protected void setSummaryObjectEndText( String summaryObjectEndText )
{
if ( summaryObjectEndText == null )
{
summaryObjectEndText = "";
}
this.summaryObjectEndText = summaryObjectEndText;
}
// ----------------------------------------------------------------------------
/**
* <p>
* Default <code>ToStringStyle</code>.
* </p>
* <p>
* This is an inner class rather than using
* <code>StandardToStringStyle</code> to ensure its immutability.
* </p>
*/
private static final class DefaultToStringStyle extends ToStringStyle
{
static final long serialVersionUID = -3594451267200535036L;
/**
* <p>
* Constructor.
* </p>
* <p>
* Use the static constant rather than instantiating.
* </p>
*/
private DefaultToStringStyle()
{
super();
}
/**
* <p>
* Ensure <code>Singleton</code> after serialization.
* </p>
*
* @return the singleton
*/
private Object readResolve()
{
return ToStringStyle.DEFAULT_STYLE;
}
}
// ----------------------------------------------------------------------------
/**
* <p>
* <code>ToStringStyle</code> that does not print out the field names.
* </p>
* <p>
* This is an inner class rather than using
* <code>StandardToStringStyle</code> to ensure its immutability.
*/
private static final class NoFieldNameToStringStyle extends ToStringStyle
{
static final long serialVersionUID = -3594451267200535036L;
/**
* <p>
* Constructor.
* </p>
* <p>
* Use the static constant rather than instantiating.
* </p>
*/
private NoFieldNameToStringStyle()
{
super();
this.setUseFieldNames( false );
}
/**
* <p>
* Ensure <code>Singleton</code> after serialization.
* </p>
*
* @return the singleton
*/
private Object readResolve()
{
return ToStringStyle.NO_FIELD_NAMES_STYLE;
}
}
// ----------------------------------------------------------------------------
/**
* <p>
* <code>ToStringStyle</code> that prints out the short class name and no
* identity hashcode.
* </p>
* <p>
* This is an inner class rather than using
* <code>StandardToStringStyle</code> to ensure its immutability.
* </p>
*/
private static final class ShortPrefixToStringStyle extends ToStringStyle
{
static final long serialVersionUID = -3594451267200535036L;
/**
* <p>
* Constructor.
* </p>
* <p>
* Use the static constant rather than instantiating.
* </p>
*/
private ShortPrefixToStringStyle()
{
super();
this.setUseShortClassName( true );
this.setUseIdentityHashCode( false );
}
/**
* <p>
* Ensure <code>Singleton</ode> after serialization.</p>
* @return the singleton
*/
private Object readResolve()
{
return ToStringStyle.SHORT_PREFIX_STYLE;
}
}
/**
* <p>
* <code>ToStringStyle</code> that does not print out the classname,
* identity hashcode, content start or field name.
* </p>
* <p>
* This is an inner class rather than using
* <code>StandardToStringStyle</code> to ensure its immutability.
* </p>
*/
private static final class SimpleToStringStyle extends ToStringStyle
{
static final long serialVersionUID = -3594451267200535036L;
/**
* <p>
* Constructor.
* </p>
* <p>
* Use the static constant rather than instantiating.
* </p>
*/
private SimpleToStringStyle()
{
super();
this.setUseClassName( false );
this.setUseIdentityHashCode( false );
this.setUseFieldNames( false );
this.setContentStart( "" );
this.setContentEnd( "" );
}
/**
* <p>
* Ensure <code>Singleton</ode> after serialization.</p>
* @return the singleton
*/
private Object readResolve()
{
return ToStringStyle.SIMPLE_STYLE;
}
}
// ----------------------------------------------------------------------------
/**
* <p>
* <code>ToStringStyle</code> that outputs on multiple lines.
* </p>
* <p>
* This is an inner class rather than using
* <code>StandardToStringStyle</code> to ensure its immutability.
* </p>
*/
private static final class MultiLineToStringStyle extends ToStringStyle
{
static final long serialVersionUID = -3594451267200535036L;
/**
* <p>
* Constructor.
* </p>
* <p>
* Use the static constant rather than instantiating.
* </p>
*/
private MultiLineToStringStyle()
{
super();
this.setContentStart( "[" );
this.setFieldSeparator( SystemUtils.LINE_SEPARATOR + " " );
this.setFieldSeparatorAtStart( true );
this.setContentEnd( SystemUtils.LINE_SEPARATOR + "]" );
}
/**
* <p>
* Ensure <code>Singleton</code> after serialization.
* </p>
*
* @return the singleton
*/
private Object readResolve()
{
return ToStringStyle.MULTI_LINE_STYLE;
}
}
// ----------------------------------------------------------------------------
// Removed, as the XML style needs more work for escaping characters,
// arrays,
// collections, maps and embedded beans.
// /**
// * ToStringStyle that outputs in XML style
// */
// private static class XMLToStringStyle extends ToStringStyle {
//
// /**
// * Constructor - use the static constant rather than instantiating.
// */
// private XMLToStringStyle() {
// super();
// nullText = "null";
// sizeStartText = "size=";
// sizeEndText = "";
// }
//
// /**
// * @see ToStringStyle#appendStart(StringBuffer, Object)
// */
// public void appendStart(StringBuffer buffer, Object object) {
// buffer.append('<');
// buffer.append(getShortClassName(object.getClass()));
// buffer.append(" class=\"");
// appendClassName(buffer, object);
// buffer.append("\" hashCode=\"");
// appendIdentityHashCode(buffer, object);
// buffer.append("\">");
// buffer.append(SystemUtils.LINE_SEPARATOR);
// buffer.append(" ");
// }
//
// /**
// * @see ToStringStyle#appendFieldStart(StringBuffer, String)
// */
// protected void appendFieldStart(StringBuffer buffer, String fieldName) {
// buffer.append('<');
// buffer.append(fieldName);
// buffer.append('>');
// }
//
// /**
// * @see ToStringStyle#appendFieldEnd(StringBuffer, String)
// */
// protected void appendFieldEnd(StringBuffer buffer, String fieldName) {
// buffer.append("</");
// buffer.append(fieldName);
// buffer.append('>');
// buffer.append(SystemUtils.LINE_SEPARATOR);
// buffer.append(" ");
// }
//
// /**
// * @see ToStringStyle#appendEnd(StringBuffer, Object)
// */
// public void appendEnd(StringBuffer buffer, Object object) {
// int len = buffer.length();
// if (len > 2 && buffer.charAt(len - 1) == ' ' && buffer.charAt(len - 2) ==
// ' ') {
// buffer.setLength(len - 2);
// }
// buffer.append("</");
// buffer.append(getShortClassName(object.getClass()));
// buffer.append("\">");
// }
//
// }
}