Author: rony Date: Sat Jun 11 09:50:22 2005 New Revision: 190150 URL: http://svn.apache.org/viewcvs?rev=190150&view=rev Log: 2005-06-11 changed 'org.apache.bsf.util.EngineUtils.java' to 'un/box' all primitive types accordingly, tries accessibility, if invocation of a method throws up (could be in the case of Java 1.1 or non-Sun-compliant Java).
Modified: jakarta/bsf/trunk/src/org/apache/bsf/util/EngineUtils.java Modified: jakarta/bsf/trunk/src/org/apache/bsf/util/EngineUtils.java URL: http://svn.apache.org/viewcvs/jakarta/bsf/trunk/src/org/apache/bsf/util/EngineUtils.java?rev=190150&r1=190149&r2=190150&view=diff ============================================================================== --- jakarta/bsf/trunk/src/org/apache/bsf/util/EngineUtils.java (original) +++ jakarta/bsf/trunk/src/org/apache/bsf/util/EngineUtils.java Sat Jun 11 09:50:22 2005 @@ -66,7 +66,7 @@ /** * This class contains utilities that language integrators can use * when implementing the BSFEngine interface. - * + * * @author Sanjiva Weerawarana * @author Sam Ruby */ @@ -75,18 +75,34 @@ // temp directory static BSFClassLoader bsfCL; + // ---rgf, 2003-02-13, determine whether changing accessibility of Methods is possible + static boolean bMethodHasSetAccessible=false; + static { + Class mc=Method.class; // get the "Method" class object + Class arg[]={boolean.class}; // define an array with the primitive "boolean" pseudo class object + try { + Object o=mc.getMethod("setAccessible", arg ); // is this method available? + bMethodHasSetAccessible=true; // no exception, hence method exists + } + catch (Exception e) + { + bMethodHasSetAccessible=false;// exception occurred, hence method does not exist + } + } + + /** * Add a script as a listener to some event coming out of an object. The * first two args identify the src of the event and the event set * and the rest identify the script which should be run when the event * fires. - * + * * @param bean event source * @param eventSetName name of event set from event src to bind to * @param filter filter for events * @param engine BSFEngine which can run this script * @param manager BSFManager of the above engine - * @param source (context info) the source of this expression + * @param source (context info) the source of this expression * (e.g., filename) * @param lineNo (context info) the line number in source for expr * @param columnNo (context info) the column number in source for expr @@ -95,20 +111,20 @@ * @exception BSFException if anything goes wrong while running the script */ public static void addEventListener (Object bean, String eventSetName, - String filter, BSFEngine engine, + String filter, BSFEngine engine, BSFManager manager, String source, - int lineNo, int columnNo, + int lineNo, int columnNo, Object script) throws BSFException { BSFEventProcessor ep = new BSFEventProcessor (engine, manager, filter, source, lineNo, columnNo, script); - + try { ReflectionUtils.addEventListener (bean, eventSetName, ep); } catch (Exception e) { e.printStackTrace (); throw new BSFException (BSFException.REASON_OTHER_ERROR, - "ouch while adding event listener: " + "ouch while adding event listener: " + e, e); } } @@ -123,17 +139,17 @@ * @param bean the object on which to invoke the method * @param methodName name of the method * @param args arguments to be given to the method - * + * * @return the result of invoking the method, if any * * @exception BSFException if something goes wrong */ - public static Object callBeanMethod (Object bean, String methodName, + public static Object callBeanMethod (Object bean, String methodName, Object[] args) throws BSFException { Class[] argTypes = null; - // determine arg types. note that a null argtype + // determine arg types. note that a null argtype // matches any object type - + if (args != null) { argTypes = new Class[args.length]; for (int i = 0; i < args.length; i++) { @@ -142,50 +158,61 @@ } // we want to allow a static call to occur on an object, similar - // to what Java allows. So isStaticOnly is set to false. + // to what Java allows. So isStaticOnly is set to false. boolean isStaticOnly = false; - Class beanClass = (bean instanceof Class) ? (Class)bean : + Class beanClass = (bean instanceof Class) ? (Class)bean : bean.getClass (); // now try to call method with the right signature - try { - Method m = null; - - try { - m = MethodUtils.getMethod (beanClass, methodName, argTypes, - isStaticOnly); - } catch (NoSuchMethodException e) { - // ok, so that didn't work - now try converting any primitive - // wrapper types to their primitive counterparts - try { - // if args is null the NullPointerException will get caught - // below and the right thing'll happen .. ugly but works - for (int i = 0; i < args.length; i++) { - if (args[i] instanceof Number) { - // byte is convertible to all primitive numeric types, - // so this'll find anything in that order and the - // actual type will be that specified by the method decl - argTypes[i] = byte.class; - if(args[i] instanceof Float) - argTypes[i] = float.class; - else if(args[i] instanceof Double) - argTypes[i] = double.class; - } - else if (args[i] instanceof Boolean) - argTypes[i] = boolean.class; - else if (args[i] instanceof Character) - argTypes[i] = char.class; - } - m = MethodUtils.getMethod (beanClass, methodName, - argTypes, isStaticOnly); - } catch (Exception e2) { - // throw the original - throw e; - } - } + try { + Method m; + try { + m = MethodUtils.getMethod (beanClass, methodName, argTypes, + isStaticOnly); + } catch (NoSuchMethodException e) { + // ok, so that didn't work - now try converting any primitive + // wrapper types to their primitive counterparts + try { + // if args is null the NullPointerException will get caught + // below and the right thing'll happen .. ugly but works + for (int i = 0; i < args.length; i++) { + if (args[i] instanceof Number) + { + if (args[i] instanceof Byte) argTypes[i] = byte.class; + else if (args[i] instanceof Integer) argTypes[i] = int.class; + else if (args[i] instanceof Long) argTypes[i] = long.class; + else if (args[i] instanceof Float) argTypes[i] = float.class; + else if (args[i] instanceof Double ) argTypes[i] = double.class; + else if (args[i] instanceof Short ) argTypes[i] = short.class; + } + else if (args[i] instanceof Boolean) argTypes[i] = boolean.class; + else if (args[i] instanceof Character) argTypes[i] = char.class; + } + + m = MethodUtils.getMethod (beanClass, methodName, argTypes, + isStaticOnly); + } catch (Exception e2) { + // throw the original + throw e; + } + } - // call it, and return the result + // call it, and return the result + try { return m.invoke (bean, args); + } + catch (Exception e) // 2003-02-23, --rgf, maybe an IllegalAccessException? + { + if (e instanceof IllegalAccessException && + bMethodHasSetAccessible && + Modifier.isPublic(m.getModifiers()) ) // if a public method allow access to it + { + m.setAccessible(true); // allow unconditional access to method + return m.invoke (bean, args); + } + // re-throw the exception + throw e; + } } catch (Exception e) { // something went wrong while invoking method @@ -194,7 +221,7 @@ null; throw new BSFException (BSFException.REASON_OTHER_ERROR, "method invocation failed: " + e + - ((t==null) ? "" : + ((t==null) ? "" : (" target exception: " + t)), t); } } @@ -202,7 +229,7 @@ /** * Creates a new bean. The signature of the constructor that's invoked * is first taken as the types of the args, but if that fails, this tries - * to convert any primitive wrapper type args to their primitive + * to convert any primitive wrapper type args to their primitive * counterparts to see whether a method exists that way. If it does, done. * * @param className fully qualified name of class to instantiate @@ -210,11 +237,11 @@ * * @return the created bean * - * @exception BSFException if something goes wrong (@see + * @exception BSFException if something goes wrong (@see * org.apache.cs.util.MethodUtils for the real * exceptions that can occur). */ - public static Object createBean (String className, Object args[]) + public static Object createBean (String className, Object args[]) throws BSFException { Bean obj; Class[] argTypes = null; @@ -228,7 +255,7 @@ try { try { - obj = ReflectionUtils.createBean (null, className, + obj = ReflectionUtils.createBean (null, className, argTypes, args); return obj.value; } catch (NoSuchMethodException me) { @@ -245,7 +272,7 @@ else if (args[i] instanceof Character) argTypes[i] = char.class; } - obj = ReflectionUtils.createBean (null, className, + obj = ReflectionUtils.createBean (null, className, argTypes, args); return obj.value; } catch (Exception e) { @@ -264,28 +291,28 @@ * That is, return "I" for int, "J" for long, ... etc.. * * @param cl class object for whom the signature fragment is needed. - * + * * @return the string representing the type signature */ public static String getTypeSignatureString (Class cl) { if (cl.isPrimitive ()) { - if (cl == boolean.class) + if (cl == boolean.class) return "Z"; - else if (cl == byte.class) + else if (cl == byte.class) return "B"; - else if (cl == char.class) + else if (cl == char.class) return "C"; - else if (cl == short.class) + else if (cl == short.class) return "S"; - else if (cl == int.class) + else if (cl == int.class) return "I"; - else if (cl == long.class) + else if (cl == long.class) return "J"; - else if (cl == float.class) + else if (cl == float.class) return "F"; - else if (cl == double.class) + else if (cl == double.class) return "D"; - else + else return "V"; } else { StringBuffer sb = new StringBuffer ("L"); @@ -302,12 +329,12 @@ * @param mgr BSFManager who's classLoader and tempDir props are * consulted * @param name name of the class to load - * + * * @return the loaded class * * @exception BSFException if something goes wrong. */ - public static Class loadClass (BSFManager mgr, String name) + public static Class loadClass (BSFManager mgr, String name) throws BSFException { ClassLoader classLoader = mgr.getClassLoader (); --------------------------------------------------------------------- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED]