1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20 package org.apache.fulcrum.yaafi.interceptor.util;
21
22 import java.io.PrintWriter;
23 import java.io.StringWriter;
24 import java.util.Collection;
25 import java.util.Dictionary;
26 import java.util.Iterator;
27
28 import org.apache.commons.lang3.StringUtils;
29
30
31
32
33
34
35 public class ArgumentToStringBuilderImpl implements InterceptorToStringBuilder
36 {
37
38 public static final int INCLUDE_CLASSNAME = 0x1;
39
40
41 public static final int INCLUDE_HASHCODE = 0x02;
42
43
44 private static int defaultMode = INCLUDE_CLASSNAME & INCLUDE_HASHCODE;
45
46
47 private int mode;
48
49
50 private static final int MAX_LINE_LENGTH = 2000;
51
52
53 private static final String SEPERATOR = ";";
54
55
56 private static final String NULL_STRING = "<null>";
57
58
59 private static final String LENGTH_STRING = "length=";
60
61
62 private static final String VALUE_STRING = "value=";
63
64
65 private int maxArgLength;
66
67
68 private StringBuilder buffer;
69
70
71 private Object target;
72
73
74
75
76 public ArgumentToStringBuilderImpl()
77 {
78 this.mode = ArgumentToStringBuilderImpl.defaultMode;
79 this.maxArgLength = MAX_LINE_LENGTH;
80 this.buffer = new StringBuilder();
81 }
82
83
84
85
86
87
88 public ArgumentToStringBuilderImpl(Object target)
89 {
90 this(target,MAX_LINE_LENGTH);
91 }
92
93
94
95
96
97
98
99 public ArgumentToStringBuilderImpl(Object target, int maxArgLength)
100 {
101 this(target,
102 maxArgLength,
103 ArgumentToStringBuilderImpl.defaultMode
104 );
105 }
106
107
108
109
110
111
112
113
114 public ArgumentToStringBuilderImpl(Object target, int maxArgLength, int mode)
115 {
116 this.buffer = new StringBuilder();
117 this.target = target;
118 this.maxArgLength = maxArgLength;
119 this.mode = mode;
120 }
121
122
123
124
125 public void setMaxArgLength(int maxArgLength)
126 {
127 this.maxArgLength = maxArgLength;
128 }
129
130
131
132
133 public void setTarget(Object target)
134 {
135 this.target = target;
136 }
137
138
139
140
141 public void setMode(int mode)
142 {
143 this.mode = mode;
144 }
145
146
147
148
149 public int getMode()
150 {
151 return this.mode;
152 }
153
154
155
156
157 public String toString()
158 {
159 try
160 {
161 if( this.target == null )
162 {
163 this.buffer.append(NULL_STRING);
164 }
165 else if( this.target instanceof Object[] )
166 {
167 this.appendClassName(target);
168 this.appendHashCode(target);
169 this.appendChar('[');
170 this.append( this.toString((Object[]) this.target) );
171 this.appendChar(']');
172 }
173 else if( this.target instanceof boolean[] )
174 {
175 this.appendClassName(target);
176 this.appendHashCode(target);
177 this.appendChar('[');
178 this.append( this.toString((boolean[]) this.target) );
179 this.appendChar(']');
180 }
181 else if( this.target instanceof char[] )
182 {
183 this.appendClassName(target);
184 this.appendHashCode(target);
185 this.appendChar('[');
186 this.append( this.toString((char[]) this.target) );
187 this.appendChar(']');
188 }
189 else if( this.target instanceof byte[] )
190 {
191 this.appendClassName(target);
192 this.appendHashCode(target);
193 this.appendChar('[');
194 this.append( this.toString((byte[]) this.target) );
195 this.appendChar(']');
196 }
197 else if( this.target instanceof short[] )
198 {
199 this.appendClassName(target);
200 this.appendHashCode(target);
201 this.appendChar('[');
202 this.append( this.toString((short[]) this.target) );
203 this.appendChar(']');
204 }
205 else if( this.target instanceof int[] )
206 {
207 this.appendClassName(target);
208 this.appendHashCode(target);
209 this.appendChar('[');
210 this.append( this.toString((int[]) this.target) );
211 this.appendChar(']');
212 }
213 else if( this.target instanceof long[] )
214 {
215 this.appendClassName(target);
216 this.appendHashCode(target);
217 this.appendChar('[');
218 this.append( this.toString((long[]) this.target) );
219 this.appendChar(']');
220 }
221 else if( this.target instanceof float[] )
222 {
223 this.appendClassName(target);
224 this.appendHashCode(target);
225 this.appendChar('[');
226 this.append( this.toString((float[]) this.target) );
227 this.appendChar(']');
228 }
229 else if( this.target instanceof double[] )
230 {
231 this.appendClassName(target);
232 this.appendHashCode(target);
233 this.appendChar('[');
234 this.append( this.toString((double[]) this.target) );
235 this.appendChar(']');
236 }
237 else if( this.target instanceof String )
238 {
239 this.appendClassName(target);
240 this.appendHashCode(target);
241 this.appendChar('[');
242 this.append( this.toString((String) this.target) );
243 this.appendChar(']');
244 }
245 else if( this.target instanceof Collection )
246 {
247 this.appendClassName(target);
248 this.appendHashCode(target);
249 this.appendChar('[');
250 this.append( this.toString((Collection<?>) this.target) );
251 this.appendChar(']');
252 }
253 else if( this.target instanceof Dictionary )
254 {
255 this.appendClassName(target);
256 this.appendHashCode(target);
257 this.appendChar('[');
258 this.append( this.toString((Dictionary<?, ?>) this.target) );
259 this.appendChar(']');
260 }
261 else if( this.target instanceof Throwable )
262 {
263 this.append( this.toString((Throwable) this.target) );
264 }
265 else
266 {
267 this.append( this.toString( (Object) this.target ) );
268 }
269 }
270 catch (Throwable t)
271 {
272 t.printStackTrace();
273 return "<" + t + ">";
274 }
275
276 return this.buffer.toString();
277 }
278
279
280
281
282
283
284
285
286 protected String toString(Throwable throwable)
287 {
288 String result = null;
289
290 if( throwable == null )
291 {
292 result = NULL_STRING;
293 }
294 else
295 {
296 result = this.getStackTrace(throwable);
297 }
298
299 return result;
300 }
301
302
303
304
305
306
307
308 protected String toString(Object[] array)
309 {
310 StringBuilder temp = new StringBuilder();
311 ArgumentToStringBuilderImpl toStringBuilder = null;
312
313 if( array == null )
314 {
315 return NULL_STRING;
316 }
317 else
318 {
319 temp.append(LENGTH_STRING);
320 temp.append(array.length);
321 temp.append(',');
322
323 for( int i=0; i<array.length; i++ )
324 {
325 temp.append('[');
326 temp.append(i);
327 temp.append(']');
328 temp.append('=');
329 toStringBuilder = new ArgumentToStringBuilderImpl(array[i],this.getMaxArgLength(),this.getMode());
330 temp.append(toStringBuilder.toString());
331
332 if( i<array.length-1)
333 {
334 temp.append(',');
335 }
336
337 if( temp.length() > this.getMaxArgLength() )
338 {
339 break;
340 }
341 }
342 }
343
344 return temp.toString();
345 }
346
347
348
349
350
351
352
353 protected String toString(boolean[] array)
354 {
355 StringBuilder temp = new StringBuilder();
356
357 if( array == null )
358 {
359 return NULL_STRING;
360 }
361 else
362 {
363 temp.append(LENGTH_STRING);
364 temp.append(array.length);
365 temp.append(',');
366 temp.append(VALUE_STRING);
367
368 for( int i=0; i<array.length; i++ )
369 {
370 temp.append(array[i]);
371 if( i<array.length-1)
372 {
373 temp.append(',');
374 }
375
376 if( temp.length() > this.getMaxArgLength() )
377 {
378 break;
379 }
380 }
381 }
382
383 return temp.toString();
384 }
385
386
387
388
389
390
391
392 protected String toString(char[] array)
393 {
394 StringBuilder temp = new StringBuilder();
395
396 if( array == null )
397 {
398 return NULL_STRING;
399 }
400 else
401 {
402 temp.append(LENGTH_STRING);
403 temp.append(array.length);
404 temp.append(',');
405 temp.append(VALUE_STRING);
406
407 for( int i=0; i<array.length; i++ )
408 {
409 temp.append(array[i]);
410 if( i<array.length-1)
411 {
412 temp.append('.');
413 }
414
415 if( temp.length() > this.getMaxArgLength() )
416 {
417 break;
418 }
419 }
420 }
421
422 return temp.toString();
423 }
424
425
426
427
428
429
430
431 protected String toString(short[] array)
432 {
433 StringBuilder temp = new StringBuilder();
434
435 if( array == null )
436 {
437 return NULL_STRING;
438 }
439 else
440 {
441 temp.append(LENGTH_STRING);
442 temp.append(array.length);
443 temp.append(',');
444 temp.append(VALUE_STRING);
445
446 for( int i=0; i<array.length; i++ )
447 {
448 temp.append(array[i]);
449 if( i<array.length-1)
450 {
451 temp.append(',');
452 }
453
454 if( temp.length() > this.getMaxArgLength() )
455 {
456 break;
457 }
458 }
459 }
460
461 return temp.toString();
462 }
463
464
465
466
467
468
469
470 protected String toString(int[] array)
471 {
472 StringBuilder temp = new StringBuilder();
473
474 if( array == null )
475 {
476 return NULL_STRING;
477 }
478 else
479 {
480 temp.append(LENGTH_STRING);
481 temp.append(array.length);
482 temp.append(',');
483 temp.append(VALUE_STRING);
484
485 for( int i=0; i<array.length; i++ )
486 {
487 temp.append(array[i]);
488 if( i<array.length-1)
489 {
490 temp.append(',');
491 }
492
493 if( temp.length() > this.getMaxArgLength() )
494 {
495 break;
496 }
497 }
498 }
499
500 return temp.toString();
501 }
502
503
504
505
506
507
508
509 protected String toString(long[] array)
510 {
511 StringBuilder temp = new StringBuilder();
512
513 if( array == null )
514 {
515 return NULL_STRING;
516 }
517 else
518 {
519 temp.append(LENGTH_STRING);
520 temp.append(array.length);
521 temp.append(',');
522 temp.append(VALUE_STRING);
523
524 for( int i=0; i<array.length; i++ )
525 {
526 temp.append(array[i]);
527 if( i<array.length-1)
528 {
529 temp.append(',');
530 }
531
532 if( temp.length() > this.getMaxArgLength() )
533 {
534 break;
535 }
536 }
537 }
538
539 return temp.toString();
540 }
541
542
543
544
545
546
547
548 protected String toString(float[] array)
549 {
550 StringBuilder temp = new StringBuilder();
551
552 if( array == null )
553 {
554 return NULL_STRING;
555 }
556 else
557 {
558 temp.append(LENGTH_STRING);
559 temp.append(array.length);
560 temp.append(',');
561 temp.append(VALUE_STRING);
562
563 for( int i=0; i<array.length; i++ )
564 {
565 temp.append(array[i]);
566 if( i<array.length-1)
567 {
568 temp.append(',');
569 }
570
571 if( temp.length() > this.getMaxArgLength() )
572 {
573 break;
574 }
575 }
576 }
577
578 return temp.toString();
579 }
580
581
582
583
584
585
586
587 protected String toString(double[] array)
588 {
589 StringBuilder temp = new StringBuilder();
590
591 if( array == null )
592 {
593 return NULL_STRING;
594 }
595 else
596 {
597 temp.append(LENGTH_STRING);
598 temp.append(array.length);
599 temp.append(',');
600 temp.append(VALUE_STRING);
601
602 for( int i=0; i<array.length; i++ )
603 {
604 temp.append(array[i]);
605 if( i<array.length-1)
606 {
607 temp.append(',');
608 }
609
610 if( temp.length() > this.getMaxArgLength() )
611 {
612 break;
613 }
614 }
615 }
616
617 return temp.toString();
618 }
619
620
621
622
623
624
625
626 protected String toString(String string)
627 {
628 StringBuilder temp = new StringBuilder();
629
630 if( string == null )
631 {
632 return NULL_STRING;
633 }
634 else
635 {
636 temp.append(LENGTH_STRING);
637 temp.append(string.length());
638 temp.append(',');
639 temp.append(VALUE_STRING);
640 temp.append(string);
641 }
642
643 return temp.toString();
644 }
645
646
647
648
649
650
651
652 protected String toString(byte[] array)
653 {
654 StringBuilder temp = new StringBuilder();
655
656 if( array == null )
657 {
658 temp.append(NULL_STRING);
659 }
660 else
661 {
662 temp.append(LENGTH_STRING);
663 temp.append(array.length);
664 }
665
666 return temp.toString();
667 }
668
669
670
671
672
673
674
675 protected String toString(Collection<?> collection)
676 {
677 int index = 0;
678 StringBuilder temp = new StringBuilder();
679 ArgumentToStringBuilderImpl toStringBuilder = null;
680
681 if( collection == null )
682 {
683 return NULL_STRING;
684 }
685 else
686 {
687 temp.append(LENGTH_STRING);
688 temp.append(collection.size());
689 temp.append(',');
690
691 Iterator<?> iterator = collection.iterator();
692
693 while (iterator.hasNext())
694 {
695 temp.append('[');
696 temp.append(index++);
697 temp.append(']');
698 temp.append('=');
699
700 toStringBuilder = new ArgumentToStringBuilderImpl(
701 iterator.next(),
702 this.getMaxArgLength(),
703 this.getMode()
704 );
705
706 temp.append(toStringBuilder.toString());
707
708 if( index<collection.size()-1)
709 {
710 temp.append(',');
711 }
712
713 if( temp.length() > this.getMaxArgLength() )
714 {
715 break;
716 }
717 }
718 }
719
720 return temp.toString();
721 }
722
723
724
725
726
727
728
729 protected String toString(Dictionary<?, ?> dictionary)
730 {
731 StringBuilder temp = new StringBuilder();
732
733 if( dictionary == null )
734 {
735 return NULL_STRING;
736 }
737 else
738 {
739 temp.append(LENGTH_STRING);
740 temp.append(dictionary.size());
741 temp.append(',');
742 temp.append(VALUE_STRING);
743 temp.append(dictionary.toString());
744 }
745
746 return temp.toString();
747 }
748
749
750
751
752
753
754
755 protected String toString(Object object)
756 {
757 String result = null;
758 String temp = null;
759 String className = null;
760
761 if( object == null )
762 {
763 result = NULL_STRING;
764 }
765 else
766 {
767 temp = object.toString();
768
769 className = StringUtils.replace(
770 object.getClass().getName(),
771 "java.lang.", ""
772 );
773
774 if( temp.startsWith(className) == false )
775 {
776 int hashCode = object.hashCode();
777 StringBuilder tempBuffer = new StringBuilder();
778 tempBuffer.append(className);
779 tempBuffer.append('@');
780 tempBuffer.append(hashCode);
781 tempBuffer.append('[');
782 tempBuffer.append(temp);
783 tempBuffer.append(']');
784
785 result = tempBuffer.toString();
786 }
787 else
788 {
789 result = temp;
790 }
791 }
792
793 return result;
794 }
795
796
797
798
799
800 protected void appendHashCode(Object target)
801 {
802 if ((this.mode & INCLUDE_HASHCODE) == 0)
803 {
804 return;
805 }
806
807 if( this.target != null )
808 {
809 this.buffer.append('@');
810 this.buffer.append(Integer.toHexString(target.hashCode()));
811 }
812 }
813
814
815
816
817
818 protected void appendClassName(Object target)
819 {
820 boolean skipClassName = true;
821
822 if ((this.mode & INCLUDE_CLASSNAME) == 0)
823 {
824 return;
825 }
826
827 if( this.target != null )
828 {
829 String className = target.getClass().getName();
830
831 if( target instanceof boolean[] )
832 {
833 this.buffer.append("boolean[]");
834 }
835 else if( target instanceof byte[] )
836 {
837 this.buffer.append("byte[]");
838 }
839 else if( target instanceof char[] )
840 {
841 this.buffer.append("char[]");
842 }
843 else if( target instanceof short[] )
844 {
845 this.buffer.append("short[]");
846 }
847 else if( target instanceof int[] )
848 {
849 this.buffer.append("int[]");
850 }
851 else if( target instanceof long[] )
852 {
853 this.buffer.append("[ong[]");
854 }
855 else if( target instanceof float[] )
856 {
857 this.buffer.append("float[]");
858 }
859 else if( target instanceof double[] )
860 {
861 this.buffer.append("double[]");
862 }
863 else if( target instanceof Boolean )
864 {
865 this.buffer.append("Boolean");
866 }
867 else if( target instanceof Character )
868 {
869 this.buffer.append("Character");
870 }
871 else if( target instanceof Short )
872 {
873 this.buffer.append("Short");
874 }
875 else if( target instanceof Integer )
876 {
877 this.buffer.append("Integer");
878 }
879 else if( target instanceof Long )
880 {
881 this.buffer.append("Long");
882 }
883 else if( target instanceof Float )
884 {
885 this.buffer.append("Float");
886 }
887 else if( target instanceof Double )
888 {
889 this.buffer.append("Double");
890 }
891 else if( target instanceof String )
892 {
893 this.buffer.append("String");
894 }
895 else if( target instanceof Boolean[] )
896 {
897 this.buffer.append("Boolean[]");
898 }
899 else if( target instanceof Character[] )
900 {
901 this.buffer.append("Character[]");
902 }
903 else if( target instanceof Short[] )
904 {
905 this.buffer.append("Short[]");
906 }
907 else if( target instanceof Integer[] )
908 {
909 this.buffer.append("Integer[]");
910 }
911 else if( target instanceof Long[] )
912 {
913 this.buffer.append("Long[]");
914 }
915 else if( target instanceof Float[] )
916 {
917 this.buffer.append("Float[]");
918 }
919 else if( target instanceof Double[] )
920 {
921 this.buffer.append("Double[]");
922 }
923 else if( target instanceof String[] )
924 {
925 this.buffer.append("String[]");
926 }
927 else
928 {
929 skipClassName = false;
930 }
931
932 if( skipClassName == false )
933 {
934 className = StringUtils.replace(className, "java.lang.", "");
935
936 if( className.endsWith(";") )
937 {
938 this.buffer.append(className.substring(0,className.length()-1));
939 }
940 else
941 {
942 this.buffer.append(className);
943 }
944 }
945 }
946 }
947
948
949
950
951
952 protected void appendChar(char ch)
953 {
954 this.buffer.append(ch);
955 }
956
957
958
959
960 protected int getMaxArgLength()
961 {
962 return maxArgLength;
963 }
964
965
966
967
968
969
970
971
972 protected String getStackTrace(Throwable throwable)
973 {
974 StringWriter sw = new StringWriter();
975 PrintWriter pw = new PrintWriter( sw, true );
976 throwable.printStackTrace( pw );
977 return sw.getBuffer().toString();
978 }
979
980
981
982
983
984 protected void append(String source)
985 {
986 String formattedSource = this.format(source);
987 this.buffer.append(formattedSource);
988 }
989
990
991
992
993
994
995
996
997 protected String format( String source )
998 {
999 boolean isTruncated = false;
1000
1001
1002 if ( StringUtils.isEmpty(source) )
1003 return "";
1004
1005
1006 StringUtils.replace(source, "\r", " ");
1007 StringUtils.replace(source, "\n", " ");
1008 StringUtils.replace(source, "\t", " ");
1009 StringUtils.replace(source, SEPERATOR, " ");
1010
1011
1012 StringBuilder stringBuilder = new StringBuilder(source);
1013
1014
1015 if( stringBuilder.length() > this.getMaxArgLength() )
1016 {
1017 stringBuilder.delete(this.getMaxArgLength()-1, stringBuilder.length());
1018 isTruncated = true;
1019 }
1020
1021
1022 if( isTruncated )
1023 {
1024 if (source.endsWith("]"))
1025 {
1026 stringBuilder.append(" ...]");
1027 }
1028 else
1029 {
1030 stringBuilder.append(" ...");
1031 }
1032 }
1033 return stringBuilder.toString();
1034 }
1035 }