001 /* 002 * Licensed to the Apache Software Foundation (ASF) under one or more 003 * contributor license agreements. See the NOTICE file distributed with 004 * this work for additional information regarding copyright ownership. 005 * The ASF licenses this file to You under the Apache License, Version 2.0 006 * (the "License"); you may not use this file except in compliance with 007 * the License. You may obtain a copy of the License at 008 * 009 * http://www.apache.org/licenses/LICENSE-2.0 010 * 011 * Unless required by applicable law or agreed to in writing, software 012 * distributed under the License is distributed on an "AS IS" BASIS, 013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 014 * See the License for the specific language governing permissions and 015 * limitations under the License. 016 */ 017 018 019 package org.apache.commons.modeler.util; 020 021 import java.io.File; 022 import java.io.FilenameFilter; 023 import java.io.IOException; 024 import java.lang.reflect.InvocationTargetException; 025 import java.lang.reflect.Method; 026 import java.net.InetAddress; 027 import java.net.MalformedURLException; 028 import java.net.URL; 029 import java.net.UnknownHostException; 030 import java.util.Hashtable; 031 import java.util.StringTokenizer; 032 import java.util.Vector; 033 034 // Depends: 035 // JDK1.1 036 037 /** 038 * Utils for introspection and reflection 039 * 040 * Source: jakarta-tomcat-connector/util 041 */ 042 public final class IntrospectionUtils { 043 static final Class NO_PARAMS[]=new Class[0]; 044 static final Class STRING_OBJ_PARAM[]=new Class[] { 045 String.class, Object.class }; 046 static final Class STRING_PARAM[]=new Class[] { 047 String.class }; 048 049 /** Execute a no-param method. 050 */ 051 public static void execute( Object proxy, String method ) 052 throws Exception 053 { 054 Method executeM=null; 055 Class c=proxy.getClass(); 056 executeM=findMethod( c, method, NO_PARAMS ); 057 if( executeM == null ) { 058 throw new RuntimeException("No method " + method + " in " + 059 proxy.getClass() ); 060 } 061 executeM.invoke(proxy, (Object [])null ); 062 } 063 064 /** 065 * Call void setAttribute( String ,Object ) 066 */ 067 public static void setAttribute( Object proxy, String n, Object v) 068 throws Exception 069 { 070 if( proxy instanceof AttributeHolder ) { 071 ((AttributeHolder)proxy).setAttribute( n, v ); 072 return; 073 } 074 075 Method executeM=null; 076 Class c=proxy.getClass(); 077 executeM=findMethod( c, "setAttribute", STRING_OBJ_PARAM ); 078 079 if( executeM == null ) { 080 System.out.println("No setAttribute in " + proxy.getClass() ); 081 return; 082 } 083 executeM.invoke(proxy, new Object[] { n, v }); 084 return; 085 } 086 087 088 /** 089 * Call void getAttribute( String ) 090 */ 091 public static Object getAttribute( Object proxy, String n) 092 throws Exception 093 { 094 Method executeM=null; 095 Class c=proxy.getClass(); 096 executeM=findMethod( c, "getAttribute", STRING_PARAM); 097 if( executeM == null ) { 098 System.out.println("No getAttribute in " + proxy.getClass() ); 099 return null; 100 } 101 return executeM.invoke(proxy, new Object[] { n }); 102 } 103 104 105 /** Construct a URLClassLoader. Will compile and work in JDK1.1 too. 106 */ 107 public static ClassLoader getURLClassLoader( URL urls[], 108 ClassLoader parent ) 109 { 110 try { 111 Class urlCL=Class.forName( "java.net.URLClassLoader"); 112 Class paramT[]=new Class[2]; 113 paramT[0]= urls.getClass(); 114 paramT[1]=ClassLoader.class; 115 Method m=findMethod( urlCL, "newInstance", paramT); 116 if( m==null ) return null; 117 118 ClassLoader cl=(ClassLoader)m.invoke( urlCL, 119 new Object[] { urls, 120 parent } ); 121 return cl; 122 } catch(ClassNotFoundException ex ) { 123 // jdk1.1 124 return null; 125 } catch(Exception ex ) { 126 ex.printStackTrace(); 127 return null; 128 } 129 } 130 131 132 public static String guessInstall(String installSysProp, 133 String homeSysProp, String jarName) { 134 return guessInstall( installSysProp, homeSysProp, jarName, null); 135 } 136 137 /** Guess a product install/home by analyzing the class path. 138 * It works for product using the pattern: lib/executable.jar 139 * or if executable.jar is included in classpath by a shell 140 * script. ( java -jar also works ) 141 * 142 * Insures both "install" and "home" System properties are set. 143 * If either or both System properties are unset, "install" and 144 * "home" will be set to the same value. This value will be 145 * the other System property that is set, or the guessed value 146 * if neither is set. 147 */ 148 public static String guessInstall(String installSysProp, String homeSysProp, 149 String jarName, String classFile) { 150 String install=null; 151 String home=null; 152 153 if ( installSysProp != null ) 154 install=System.getProperty( installSysProp ); 155 156 if( homeSysProp != null ) 157 home=System.getProperty( homeSysProp ); 158 159 if ( install != null ) { 160 if ( home == null ) 161 System.getProperties().put( homeSysProp, install ); 162 return install; 163 } 164 165 // Find the directory where jarName.jar is located 166 167 String cpath=System.getProperty( "java.class.path"); 168 String pathSep=System.getProperty( "path.separator"); 169 StringTokenizer st=new StringTokenizer( cpath, pathSep ); 170 while( st.hasMoreTokens() ) { 171 String path=st.nextToken(); 172 // log( "path " + path ); 173 if( path.endsWith( jarName ) ) { 174 home=path.substring( 0, path.length() - jarName.length() ); 175 try { 176 if( "".equals(home) ) { 177 home=new File("./").getCanonicalPath(); 178 } else if( home.endsWith(File.separator) ) { 179 home = home.substring(0,home.length()-1); 180 } 181 File f=new File( home ); 182 String parentDir = f.getParent(); 183 if(parentDir == null) 184 parentDir = home; // unix style 185 File f1=new File ( parentDir ); 186 install = f1.getCanonicalPath(); 187 if( installSysProp != null ) 188 System.getProperties().put( installSysProp, install ); 189 if( home == null && homeSysProp != null ) 190 System.getProperties().put( homeSysProp, install ); 191 return install; 192 } catch( Exception ex ) { 193 ex.printStackTrace(); 194 } 195 } else { 196 String fname=path + ( path.endsWith("/") ?"":"/" ) + classFile; 197 if( new File( fname ).exists()) { 198 try { 199 File f=new File( path ); 200 String parentDir = f.getParent(); 201 if( parentDir == null ) 202 parentDir = path; // unix style 203 File f1=new File ( parentDir ); 204 install = f1.getCanonicalPath(); 205 if( installSysProp != null ) 206 System.getProperties().put( installSysProp, 207 install ); 208 if( home == null && homeSysProp != null ) 209 System.getProperties().put( homeSysProp, install ); 210 return install; 211 } catch( Exception ex ) { 212 ex.printStackTrace(); 213 } 214 } 215 } 216 } 217 218 // if install directory can't be found, use home as the default 219 if ( home != null ) { 220 System.getProperties().put( installSysProp, home ); 221 return home; 222 } 223 224 return null; 225 } 226 227 /** Debug method, display the classpath 228 */ 229 public static void displayClassPath( String msg, URL[] cp ) { 230 System.out.println(msg); 231 for( int i=0; i<cp.length; i++ ) { 232 System.out.println( cp[i].getFile() ); 233 } 234 } 235 236 public static String PATH_SEPARATOR = System.getProperty("path.separator"); 237 /** 238 * Adds classpath entries from a vector of URL's to the 239 * "tc_path_add" System property. This System property lists 240 * the classpath entries common to web applications. This System 241 * property is currently used by Jasper when its JSP servlet 242 * compiles the Java file for a JSP. 243 */ 244 public static String classPathAdd(URL urls[], String cp ) 245 { 246 if( urls==null ) return cp; 247 248 for( int i=0; i<urls.length; i++ ) { 249 if( cp != null) 250 cp += PATH_SEPARATOR + urls[i].getFile(); 251 else 252 cp = urls[i].getFile(); 253 } 254 return cp; 255 } 256 257 /** Find a method with the right name 258 If found, call the method ( if param is int or boolean we'll convert 259 value to the right type before) - that means you can have setDebug(1). 260 */ 261 public static void setProperty( Object o, String name, String value ) { 262 if( dbg > 1 ) d("setProperty(" + 263 o.getClass() + " " + name + "=" + 264 value +")" ); 265 266 String setter= "set" +capitalize(name); 267 268 try { 269 Method methods[]=findMethods( o.getClass() ); 270 Method setPropertyMethod=null; 271 272 // First, the ideal case - a setFoo( String ) method 273 for( int i=0; i< methods.length; i++ ) { 274 Class paramT[]=methods[i].getParameterTypes(); 275 if( setter.equals( methods[i].getName() ) && 276 paramT.length == 1 && 277 "java.lang.String".equals( paramT[0].getName())) { 278 279 methods[i].invoke( o, new Object[] { value } ); 280 return; 281 } 282 } 283 284 // Try a setFoo ( int ) or ( boolean ) 285 for( int i=0; i< methods.length; i++ ) { 286 boolean ok=true; 287 if( setter.equals( methods[i].getName() ) && 288 methods[i].getParameterTypes().length == 1) { 289 290 // match - find the type and invoke it 291 Class paramType=methods[i].getParameterTypes()[0]; 292 Object params[]=new Object[1]; 293 294 // Try a setFoo ( int ) 295 if ("java.lang.Integer".equals( paramType.getName()) || 296 "int".equals( paramType.getName())) { 297 try { 298 params[0]=new Integer(value); 299 } catch( NumberFormatException ex ) {ok=false;} 300 301 // Try a setFoo ( boolean ) 302 } else if ("java.lang.Boolean". 303 equals( paramType.getName()) || 304 "boolean".equals( paramType.getName())) { 305 params[0]=new Boolean(value); 306 307 // Try a setFoo ( InetAddress ) 308 } else if ("java.net.InetAddress". 309 equals( paramType.getName())){ 310 try{ 311 params[0]= InetAddress.getByName(value); 312 }catch(UnknownHostException exc) { 313 d("Unable to resolve host name:" + value); 314 ok=false; 315 } 316 317 // Try a setFoo ( Object ) 318 } else if ("java.lang.Object". 319 equals( paramType.getName())) { 320 params[0] = value; 321 322 // Unknown type 323 } else { 324 d("Unknown type " + paramType.getName() ); 325 } 326 327 if( ok ) { 328 methods[i].invoke( o, params ); 329 return; 330 } 331 } 332 333 // save "setProperty" for later 334 if( "setProperty".equals( methods[i].getName())) { 335 setPropertyMethod=methods[i]; 336 } 337 } 338 339 // Ok, no setXXX found, try a setProperty("name", "value") 340 if( setPropertyMethod != null ) { 341 Object params[]=new Object[2]; 342 params[0]=name; 343 params[1]=value; 344 setPropertyMethod.invoke( o, params ); 345 } 346 347 } catch( IllegalArgumentException ex2 ) { 348 System.err.println("IAE " + o + " " + name + " " + value); 349 ex2.printStackTrace(); 350 } catch( SecurityException ex1 ) { 351 if( dbg > 0 ) 352 d("SecurityException for " + o.getClass() + " " + 353 name + "=" + value +")" ); 354 if( dbg > 1 ) ex1.printStackTrace(); 355 } catch (IllegalAccessException iae) { 356 if( dbg > 0 ) 357 d("IllegalAccessException for " + 358 o.getClass() + " " + name + "=" + value +")" ); 359 if( dbg > 1 ) iae.printStackTrace(); 360 } catch (InvocationTargetException ie) { 361 if( dbg > 0 ) 362 d("InvocationTargetException for " + o.getClass() + 363 " " + name + "=" + value +")" ); 364 if( dbg > 1 ) ie.printStackTrace(); 365 } 366 } 367 368 public static Object getProperty( Object o, String name ) { 369 String getter= "get" +capitalize(name); 370 371 try { 372 Method methods[]=findMethods( o.getClass() ); 373 Method getPropertyMethod=null; 374 375 // First, the ideal case - a getFoo() method 376 for( int i=0; i< methods.length; i++ ) { 377 Class paramT[]=methods[i].getParameterTypes(); 378 if( getter.equals( methods[i].getName() ) && 379 paramT.length == 0 ) { 380 return methods[i].invoke( o, (Object [])null ); 381 } 382 383 if( "getProperty".equals( methods[i].getName())) { 384 getPropertyMethod=methods[i]; 385 } 386 if( "getAttribute".equals( methods[i].getName())) { 387 getPropertyMethod=methods[i]; 388 } 389 } 390 391 // Ok, no setXXX found, try a getProperty("name") 392 if( getPropertyMethod != null ) { 393 Object params[]=new Object[1]; 394 params[0]=name; 395 getPropertyMethod.invoke( o, params ); 396 } 397 398 } catch( IllegalArgumentException ex2 ) { 399 System.err.println("IAE " + o + " " + name ); 400 ex2.printStackTrace(); 401 } catch( SecurityException ex1 ) { 402 if( dbg > 0 ) 403 d("SecurityException for " + o.getClass() + " " + 404 name + ")" ); 405 if( dbg > 1 ) ex1.printStackTrace(); 406 } catch (IllegalAccessException iae) { 407 if( dbg > 0 ) 408 d("IllegalAccessException for " + 409 o.getClass() + " " + name +")" ); 410 if( dbg > 1 ) iae.printStackTrace(); 411 } catch (InvocationTargetException ie) { 412 if( dbg > 0 ) 413 d("InvocationTargetException for " + o.getClass() + 414 " " + name +")" ); 415 if( dbg > 1 ) ie.printStackTrace(); 416 } 417 return null; 418 } 419 420 /** 421 */ 422 public static void setProperty( Object o, String name ) { 423 String setter= "set" +capitalize(name); 424 try { 425 Method methods[]=findMethods( o.getClass() ); 426 Method setPropertyMethod=null; 427 // find setFoo() method 428 for( int i=0; i< methods.length; i++ ) { 429 Class paramT[]=methods[i].getParameterTypes(); 430 if( setter.equals( methods[i].getName() ) && 431 paramT.length == 0 ) { 432 methods[i].invoke( o, new Object[] {} ); 433 return; 434 } 435 } 436 } catch( Exception ex1 ) { 437 if( dbg > 0 ) 438 d("Exception for " + o.getClass() + " " + name); 439 if( dbg > 1 ) ex1.printStackTrace(); 440 } 441 } 442 443 /** Replace ${NAME} with the property value 444 * @deprecated Use the explicit method 445 */ 446 public static String replaceProperties(String value, 447 Object getter ) 448 { 449 if( getter instanceof Hashtable ) 450 return replaceProperties( value, (Hashtable)getter, null ); 451 452 if( getter instanceof PropertySource ) { 453 PropertySource src[]=new PropertySource[] {(PropertySource)getter}; 454 return replaceProperties( value, null, src); 455 } 456 return value; 457 } 458 459 /** Replace ${NAME} with the property value 460 */ 461 public static String replaceProperties(String value, 462 Hashtable staticProp, PropertySource dynamicProp[] ) 463 { 464 StringBuffer sb=new StringBuffer(); 465 int prev=0; 466 // assert value!=nil 467 int pos; 468 while( (pos=value.indexOf( "$", prev )) >= 0 ) { 469 if(pos>0) { 470 sb.append( value.substring( prev, pos ) ); 471 } 472 if( pos == (value.length() - 1)) { 473 sb.append('$'); 474 prev = pos + 1; 475 } 476 else if (value.charAt( pos + 1 ) != '{' ) { 477 sb.append( value.charAt( pos + 1 ) ); 478 prev=pos+2; // XXX 479 } else { 480 int endName=value.indexOf( '}', pos ); 481 if( endName < 0 ) { 482 sb.append( value.substring( pos )); 483 prev=value.length(); 484 continue; 485 } 486 String n=value.substring( pos+2, endName ); 487 String v= null; 488 if( staticProp != null ) { 489 v=(String)((Hashtable)staticProp).get(n); 490 } 491 if( v==null && dynamicProp != null) { 492 for( int i=0; i<dynamicProp.length; i++ ) { 493 v=dynamicProp[i].getProperty( n ); 494 if( v!=null ) { 495 break; 496 } 497 } 498 } 499 if( v== null ) 500 v = "${"+n+"}"; 501 502 sb.append( v ); 503 prev=endName+1; 504 } 505 } 506 if( prev < value.length() ) sb.append( value.substring( prev ) ); 507 return sb.toString(); 508 } 509 510 /** Reverse of Introspector.decapitalize 511 */ 512 public static String capitalize(String name) { 513 if (name == null || name.length() == 0) { 514 return name; 515 } 516 char chars[] = name.toCharArray(); 517 chars[0] = Character.toUpperCase(chars[0]); 518 return new String(chars); 519 } 520 521 public static String unCapitalize(String name) { 522 if (name == null || name.length() == 0) { 523 return name; 524 } 525 char chars[] = name.toCharArray(); 526 chars[0] = Character.toLowerCase(chars[0]); 527 return new String(chars); 528 } 529 530 // -------------------- Class path tools -------------------- 531 532 /** Add all the jar files in a dir to the classpath, 533 * represented as a Vector of URLs. 534 */ 535 public static void addToClassPath( Vector cpV, String dir ) { 536 try{ 537 String cpComp[]=getFilesByExt(dir, ".jar"); 538 if (cpComp != null){ 539 int jarCount=cpComp.length; 540 for( int i=0; i< jarCount ; i++ ) { 541 URL url=getURL( dir , cpComp[i] ); 542 if( url!=null ) 543 cpV.addElement( url ); 544 } 545 } 546 }catch(Exception ex){ 547 ex.printStackTrace(); 548 } 549 } 550 551 552 public static void addToolsJar( Vector v ) 553 { 554 try { 555 // Add tools.jar in any case 556 File f=new File( System.getProperty( "java.home" ) + 557 "/../lib/tools.jar"); 558 559 if( ! f.exists() ) { 560 // On some systems java.home gets set to the root of jdk. 561 // That's a bug, but we can work around and be nice. 562 f=new File( System.getProperty( "java.home" ) + 563 "/lib/tools.jar"); 564 if( f.exists() ) { 565 System.out.println("Detected strange java.home value " + 566 System.getProperty( "java.home" ) + 567 ", it should point to jre"); 568 } 569 } 570 URL url=new URL( "file", "" , f.getAbsolutePath() ); 571 572 v.addElement( url ); 573 } catch ( MalformedURLException ex ) { 574 ex.printStackTrace(); 575 } 576 } 577 578 579 /** Return all files with a given extension in a dir 580 */ 581 public static String[] getFilesByExt( String ld, String ext ) { 582 File dir = new File(ld); 583 String[] names=null; 584 final String lext=ext; 585 if (dir.isDirectory()){ 586 names = dir.list( new FilenameFilter(){ 587 public boolean accept(File d, String name) { 588 if (name.endsWith(lext)){ 589 return true; 590 } 591 return false; 592 } 593 }); 594 } 595 return names; 596 } 597 598 599 /** Construct a file url from a file, using a base dir 600 */ 601 public static URL getURL( String base, String file ) { 602 try { 603 File baseF = new File(base); 604 File f = new File(baseF,file); 605 String path = f.getCanonicalPath(); 606 if( f.isDirectory() ){ 607 path +="/"; 608 } 609 if( ! f.exists() ) return null; 610 return new URL( "file", "", path ); 611 } catch (Exception ex) { 612 ex.printStackTrace(); 613 return null; 614 } 615 } 616 617 /** 618 * add elements from the classpath <i>cp</i> to a Vector 619 * <i>jars</i> as file URLs (We use Vector for JDK 1.1 compat). 620 * 621 * @param jars A vector of URLs 622 * @param cp a String classpath of directory or jar file 623 * elements separated by path.separator delimiters. 624 */ 625 public static void addJarsFromClassPath(Vector jars, String cp) 626 throws IOException,MalformedURLException 627 { 628 String sep = System.getProperty("path.separator"); 629 String token; 630 StringTokenizer st; 631 if(cp!=null){ 632 st = new StringTokenizer(cp,sep); 633 while(st.hasMoreTokens()){ 634 File f = new File(st.nextToken()); 635 String path = f.getCanonicalPath(); 636 if(f.isDirectory()){ 637 path += "/"; 638 } 639 URL url = new URL("file","",path); 640 if(!jars.contains(url)){ 641 jars.addElement(url); 642 } 643 } 644 } 645 } 646 647 /** Return a URL[] that can be used to construct a class loader 648 */ 649 public static URL[] getClassPath(Vector v){ 650 URL[] urls=new URL[ v.size() ]; 651 for( int i=0; i<v.size(); i++ ) { 652 urls[i]=(URL)v.elementAt( i ); 653 } 654 return urls; 655 } 656 657 /** Construct a URL classpath from files in a directory, 658 * a cpath property, and tools.jar. 659 */ 660 public static URL[] getClassPath( String dir, String cpath, 661 String cpathProp, boolean addTools ) 662 throws IOException, MalformedURLException 663 { 664 Vector jarsV = new Vector(); 665 if( dir!=null ) { 666 // Add dir/classes first, if it exists 667 URL url=getURL( dir, "classes"); 668 if( url!=null ) 669 jarsV.addElement(url); 670 addToClassPath( jarsV, dir ); 671 } 672 673 if( cpath != null ) 674 addJarsFromClassPath(jarsV,cpath); 675 676 if( cpathProp!=null ) { 677 String cpath1=System.getProperty( cpathProp ); 678 addJarsFromClassPath(jarsV,cpath1); 679 } 680 681 if(addTools) 682 addToolsJar( jarsV ); 683 684 return getClassPath(jarsV); 685 } 686 687 // -------------------- Mapping command line params to setters 688 689 public static boolean processArgs(Object proxy, String args[] ) 690 throws Exception 691 { 692 String args0[]=null; 693 if( null != findMethod( proxy.getClass(), 694 "getOptions1", new Class[] {} )) { 695 args0=(String[])callMethod0( proxy, "getOptions1"); 696 } 697 698 if( args0==null ) { 699 //args0=findVoidSetters(proxy.getClass()); 700 args0=findBooleanSetters(proxy.getClass()); 701 } 702 Hashtable h=null; 703 if( null != findMethod( proxy.getClass(), 704 "getOptionAliases", new Class[] {} )) { 705 h=(Hashtable)callMethod0( proxy, "getOptionAliases"); 706 } 707 return processArgs( proxy, args, args0, null, h ); 708 } 709 710 public static boolean processArgs(Object proxy, String args[], 711 String args0[], String args1[], 712 Hashtable aliases ) 713 throws Exception 714 { 715 for( int i=0; i< args.length; i++ ) { 716 String arg=args[i]; 717 if( arg.startsWith("-")) 718 arg=arg.substring(1); 719 if( aliases != null && aliases.get( arg ) != null) 720 arg=(String)aliases.get(arg); 721 722 if( args0!=null ) { 723 boolean set=false; 724 for( int j=0; j< args0.length ; j++ ) { 725 if( args0[j].equalsIgnoreCase( arg )) { 726 setProperty( proxy, args0[j], "true"); 727 set=true; 728 break; 729 } 730 } 731 if( set ) continue; 732 } 733 if( args1!=null ) { 734 for( int j=0; j< args1.length ; j++ ) { 735 if( args1[j].equalsIgnoreCase( arg )) { 736 i++; 737 if( i >= args.length ) 738 return false; 739 setProperty( proxy, arg, args[i]); 740 break; 741 } 742 } 743 } else { 744 // if args1 is not specified,assume all other options have param 745 i++; 746 if( i >= args.length ) 747 return false; 748 setProperty( proxy,arg, args[i]); 749 } 750 751 } 752 return true; 753 } 754 755 // -------------------- other utils -------------------- 756 public static String[] findVoidSetters( Class c ) { 757 Method m[]=findMethods( c ); 758 if( m==null ) return null; 759 Vector v=new Vector(); 760 for( int i=0; i<m.length; i++ ) { 761 if( m[i].getName().startsWith("set") && 762 m[i].getParameterTypes().length == 0 ) { 763 String arg=m[i].getName().substring( 3 ); 764 v.addElement( unCapitalize( arg )); 765 } 766 } 767 String s[]=new String[v.size()]; 768 for( int i=0; i<s.length; i++ ) { 769 s[i]=(String)v.elementAt( i ); 770 } 771 return s; 772 } 773 774 public static String[] findBooleanSetters( Class c ) { 775 Method m[]=findMethods( c ); 776 if( m==null ) return null; 777 Vector v=new Vector(); 778 for( int i=0; i<m.length; i++ ) { 779 if( m[i].getName().startsWith("set") && 780 m[i].getParameterTypes().length == 1 && 781 "boolean".equalsIgnoreCase( m[i].getParameterTypes()[0].getName()) ) { 782 String arg=m[i].getName().substring( 3 ); 783 v.addElement( unCapitalize( arg )); 784 } 785 } 786 String s[]=new String[v.size()]; 787 for( int i=0; i<s.length; i++ ) { 788 s[i]=(String)v.elementAt( i ); 789 } 790 return s; 791 } 792 793 static Hashtable objectMethods=new Hashtable(); 794 795 public static void clear() { 796 objectMethods.clear(); 797 } 798 799 public static Method[] findMethods( Class c ) { 800 Method methods[]= (Method [])objectMethods.get( c ); 801 if( methods != null ) return methods; 802 803 methods=c.getMethods(); 804 objectMethods.put( c, methods ); 805 return methods; 806 } 807 808 public static Method findMethod( Class c, String name, Class params[] ) { 809 Method methods[] = findMethods( c ); 810 if( methods==null ) return null; 811 for (int i = 0; i < methods.length; i++) { 812 if (methods[i].getName().equals(name) ) { 813 Class methodParams[]=methods[i].getParameterTypes(); 814 if( methodParams==null ) 815 if( params==null || params.length==0 ) 816 return methods[i]; 817 if( params==null ) 818 if( methodParams==null || methodParams.length==0 ) 819 return methods[i]; 820 if( params.length != methodParams.length ) 821 continue; 822 boolean found=true; 823 for( int j=0; j< params.length; j++ ) { 824 if( params[j] != methodParams[j] ) { 825 found=false; 826 break; 827 } 828 } 829 if( found ) return methods[i]; 830 } 831 } 832 return null; 833 } 834 835 /** Test if the object implements a particular 836 * method 837 */ 838 public static boolean hasHook( Object obj, String methodN ) { 839 try { 840 Method myMethods[]=findMethods( obj.getClass() ); 841 for( int i=0; i< myMethods.length; i++ ) { 842 if( methodN.equals ( myMethods[i].getName() )) { 843 // check if it's overriden 844 Class declaring=myMethods[i].getDeclaringClass(); 845 Class parentOfDeclaring=declaring.getSuperclass(); 846 // this works only if the base class doesn't extend 847 // another class. 848 849 // if the method is declared in a top level class 850 // like BaseInterceptor parent is Object, otherwise 851 // parent is BaseInterceptor or an intermediate class 852 if( ! "java.lang.Object". 853 equals(parentOfDeclaring.getName() )) { 854 return true; 855 } 856 } 857 } 858 } catch ( Exception ex ) { 859 ex.printStackTrace(); 860 } 861 return false; 862 } 863 864 public static void callMain( Class c, String args[] ) 865 throws Exception 866 { 867 Class p[]=new Class[1]; 868 p[0]=args.getClass(); 869 Method m=c.getMethod( "main", p); 870 m.invoke( c, new Object[] {args} ); 871 } 872 873 public static Object callMethod1( Object target, 874 String methodN, 875 Object param1, 876 String typeParam1, 877 ClassLoader cl) 878 throws Exception 879 { 880 if( target==null || param1==null ) { 881 d("Assert: Illegal params " + target + " " + param1 ); 882 } 883 if( dbg > 0 ) d("callMethod1 " + target.getClass().getName() + 884 " " + param1.getClass().getName() + 885 " " + typeParam1 ); 886 887 Class params[]=new Class[1]; 888 if( typeParam1==null ) 889 params[0]=param1.getClass(); 890 else 891 params[0]=cl.loadClass( typeParam1 ); 892 Method m=findMethod( target.getClass(), methodN, params); 893 if( m==null ) 894 throw new NoSuchMethodException(target.getClass().getName() + 895 " " + methodN); 896 return m.invoke(target, new Object[] {param1 } ); 897 } 898 899 public static Object callMethod0( Object target, 900 String methodN) 901 throws Exception 902 { 903 if( target==null ) { 904 d("Assert: Illegal params " + target ); 905 return null; 906 } 907 if( dbg > 0 ) 908 d("callMethod0 " + target.getClass().getName() + "." + methodN); 909 910 Class params[]=new Class[0]; 911 Method m=findMethod( target.getClass(), methodN, params); 912 if( m==null ) 913 throw new NoSuchMethodException(target.getClass().getName() + 914 " " + methodN); 915 return m.invoke(target, emptyArray ); 916 } 917 918 static Object[] emptyArray=new Object[] {}; 919 920 public static Object callMethodN( Object target, String methodN, 921 Object params[], Class typeParams[] ) 922 throws Exception 923 { 924 Method m=null; 925 m=findMethod( target.getClass(), methodN, typeParams ); 926 if( m== null ) { 927 d("Can't find method " + methodN + " in " + 928 target + " CLASS " + target.getClass()); 929 return null; 930 } 931 Object o=m.invoke( target, params ); 932 933 if(dbg > 0 ) { 934 // debug 935 StringBuffer sb=new StringBuffer(); 936 sb.append("" + target.getClass().getName() + "." + methodN + "( " ); 937 for(int i=0; i<params.length; i++ ) { 938 if(i>0) sb.append( ", "); 939 sb.append(params[i]); 940 } 941 sb.append(")"); 942 d(sb.toString()); 943 } 944 return o; 945 } 946 947 // -------------------- Get property -------------------- 948 // This provides a layer of abstraction 949 950 public static interface PropertySource { 951 952 public String getProperty( String key ); 953 954 } 955 956 public static interface AttributeHolder { 957 958 public void setAttribute( String key, Object o ); 959 960 } 961 962 963 // debug -------------------- 964 static final int dbg=0; 965 static void d(String s ) { 966 System.out.println("IntrospectionUtils: " + s ); 967 } 968 }