*** empty log message ***

This commit is contained in:
Eric J. Bowersox
2003-05-20 03:25:31 +00:00
commit b80fa05ed1
682 changed files with 85738 additions and 0 deletions

View File

@@ -0,0 +1,739 @@
/*
* The contents of this file are subject to the Mozilla Public License Version 1.1
* (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.mozilla.org/MPL/>.
*
* Software distributed under the License is distributed on an "AS IS" basis, WITHOUT
* WARRANTY OF ANY KIND, either express or implied. See the License for the specific
* language governing rights and limitations under the License.
*
* The Original Code is the Venice Web Communities System.
*
* The Initial Developer of the Original Code is Eric J. Bowersox <erbo@silcom.com>,
* for Silverwrist Design Studios. Portions created by Eric J. Bowersox are
* Copyright (C) 2002 Eric J. Bowersox/Silverwrist Design Studios. All Rights Reserved.
*
* Contributor(s):
*/
package com.silverwrist.dynamo.obj;
import java.lang.reflect.*;
import java.util.*;
import com.silverwrist.util.*;
import com.silverwrist.dynamo.except.*;
import com.silverwrist.dynamo.iface.*;
class JavaDynamicClass implements DynamicClass, DynamicWrapper
{
/*--------------------------------------------------------------------------------
* Internal class implementing properties
*--------------------------------------------------------------------------------
*/
private class Property
{
/*====================================================================
* Attributes
*====================================================================
*/
private String m_name;
private Field m_field = null;
private Method m_get_method = null;
private Method[] m_set_methods = null;
/*====================================================================
* Constructor
*====================================================================
*/
Property(String name)
{
m_name = name;
} // end constructor
/*====================================================================
* External operations
*====================================================================
*/
String getName()
{
return m_name;
} // end getName
void setField(Field field)
{
if (m_field==null)
m_field = field;
else
throw new IllegalStateException("multiple field defs not permitted");
} // end setField
void setGetMethod(Method method)
{
if (m_get_method==null)
m_get_method = method;
else
throw new IllegalStateException("multiple getters not permitted");
} // end setGetMethod
void setSetMethods(Method[] methods)
{
if (m_set_methods==null)
m_set_methods = methods;
// else this is a no-op
} // end setSetMethod
Object doGet(Object on_obj) throws DynamicObjectException
{
try
{ // try calling the various possible methods
if (m_get_method!=null)
return m_get_method.invoke(on_obj,NULL_ARG_LIST);
else if (m_field!=null)
return m_field.get(on_obj);
else
throw new CodeNotFoundException(JavaDynamicClass.this,CodeNotFoundException.GET,m_name);
} // end try
catch (IllegalAccessException e)
{ // translate to CallFailureException
throw new CallFailureException(JavaDynamicClass.this,e);
} // end catch
catch (InvocationTargetException e)
{ // translate to CallFailureException
throw new CallFailureException(JavaDynamicClass.this,e.getCause());
} // end catch
catch (UndeclaredThrowableException e)
{ // translate to CallFailureException
throw new CallFailureException(JavaDynamicClass.this,e.getCause());
} // end catch
} // end doGet
void doSet(Object on_obj, Object value) throws DynamicObjectException
{
try
{ // try calling the various possible methods
if (m_set_methods!=null)
{ // pick a method and invoke it
Object[] args = new Object[] { value };
Method m = selectMethod(m_set_methods,args);
if (m==null)
throw new CodeNotFoundException(JavaDynamicClass.this,CodeNotFoundException.SET,m_name);
else
m.invoke(on_obj,args);
} // end if
else if (m_field!=null)
m_field.set(on_obj,value);
else
throw new CodeNotFoundException(JavaDynamicClass.this,CodeNotFoundException.SET,m_name);
} // end try
catch (IllegalAccessException e)
{ // translate to CallFailureException
throw new CallFailureException(JavaDynamicClass.this,e);
} // end catch
catch (InvocationTargetException e)
{ // translate to CallFailureException
throw new CallFailureException(JavaDynamicClass.this,e.getCause());
} // end catch
catch (UndeclaredThrowableException e)
{ // translate to CallFailureException
throw new CallFailureException(JavaDynamicClass.this,e.getCause());
} // end catch
} // end doSet
} // end class Property
/*--------------------------------------------------------------------------------
* Static data members
*--------------------------------------------------------------------------------
*/
private static final Object[] NULL_ARG_LIST = new Object[0];
private static final Method[] METHOD_TEMPLATE = new Method[0];
/*--------------------------------------------------------------------------------
* Attributes
*--------------------------------------------------------------------------------
*/
private Class m_klass;
private Map m_static_methods;
private Map m_object_methods;
private Map m_static_properties;
private Map m_object_properties;
/*--------------------------------------------------------------------------------
* Constructor
*--------------------------------------------------------------------------------
*/
JavaDynamicClass(Class klass)
{
m_klass = klass; // save Java class
// Allocate various HashMaps required to properly introspect the class's methods
// and properties.
HashMap ometh_map = new HashMap();
HashMap smeth_map = new HashMap();
HashMap oprop_map = new HashMap();
HashMap oprop_set_map = new HashMap();
HashMap sprop_map = new HashMap();
HashMap sprop_set_map = new HashMap();
// Get the methods for the object and fill them in as object methods, and as
// property getters and setters.
Method[] meths = klass.getMethods();
int i;
for (i=0; i<meths.length; i++)
{ // look at all methods and create appropriate entries
Map meth_map, prop_map, prop_set_map;
if (Modifier.isStatic(meths[i].getModifiers()))
{ // add to "static" maps
meth_map = smeth_map;
prop_map = sprop_map;
prop_set_map = sprop_set_map;
} // end if
else
{ // add to "object" maps
meth_map = ometh_map;
prop_map = oprop_map;
prop_set_map = oprop_set_map;
} // end else
// Add method to list of methods with this name.
String name = meths[i].getName();
ArrayList al = (ArrayList)(meth_map.get(name));
if (al==null)
{ // create method list
al = new ArrayList();
meth_map.put(name,al);
} // end if
al.add(meths[i]);
Property p = null;
if (isGetterMethod(meths[i]))
{ // create property name and Property entry
name = makePropertyName(name);
p = (Property)(prop_map.get(name));
if (p==null)
{ // create new Property entry
p = new Property(name);
prop_map.put(name,p);
} // end if
p.setGetMethod(meths[i]);
} // end if (found getter)
else if (isSetterMethod(meths[i]))
{ // create property name and ArrayList for setter
name = makePropertyName(name);
al = (ArrayList)(prop_set_map.get(name));
if (al==null)
{ // create new ArrayList
al = new ArrayList();
prop_set_map.put(name,al);
} // end if
al.add(meths[i]);
} // end else if (found setter)
} // end for
// Freeze the static method map.
HashMap tmp = null;
Iterator it;
if (smeth_map.isEmpty())
m_static_methods = Collections.EMPTY_MAP;
else
{ // copy entries to fresh HashMap, converting to Method arrays
tmp = new HashMap();
it = smeth_map.keySet().iterator();
while (it.hasNext())
{ // get name, then ArrayList, then make array
String name = (String)(it.next());
ArrayList al = (ArrayList)(smeth_map.get(name));
tmp.put(name,al.toArray(METHOD_TEMPLATE));
al.clear();
} // end while
// freeze static methods
m_static_methods = Collections.unmodifiableMap(tmp);
smeth_map.clear();
} // end else
smeth_map = null;
// Freeze the object method map.
if (ometh_map.isEmpty())
m_object_methods = Collections.EMPTY_MAP;
else
{ // copy entries to fresh HashMap, converting to Method arrays
tmp = new HashMap();
it = ometh_map.keySet().iterator();
while (it.hasNext())
{ // get name, then ArrayList, then make array
String name = (String)(it.next());
ArrayList al = (ArrayList)(ometh_map.get(name));
tmp.put(name,al.toArray(METHOD_TEMPLATE));
al.clear();
} // end while
// freeze object methods
m_object_methods = Collections.unmodifiableMap(tmp);
ometh_map.clear();
} // end else
ometh_map = null;
// Load the setter arrays for static properties.
it = sprop_set_map.keySet().iterator();
while (it.hasNext())
{ // get name, then ArrayList, then Property, then save off array
String name = (String)(it.next());
ArrayList al = (ArrayList)(sprop_set_map.get(name));
Property p = (Property)(sprop_map.get(name));
if (p==null)
{ // create new Property entry
p = new Property(name);
sprop_map.put(name,p);
} // end if
p.setSetMethods((Method[])(al.toArray(METHOD_TEMPLATE)));
al.clear();
} // end while
sprop_set_map.clear(); // zap the setter maps
sprop_set_map = null;
// Load the setter arrays for object properties.
it = oprop_set_map.keySet().iterator();
while (it.hasNext())
{ // get name, then ArrayList, then Property, then save off array
String name = (String)(it.next());
ArrayList al = (ArrayList)(oprop_set_map.get(name));
Property p = (Property)(oprop_map.get(name));
if (p==null)
{ // create new Property entry
p = new Property(name);
oprop_map.put(name,p);
} // end if
p.setSetMethods((Method[])(al.toArray(METHOD_TEMPLATE)));
al.clear();
} // end while
oprop_set_map.clear(); // zap the setter maps
oprop_set_map = null;
Field[] fields = klass.getFields();
for (i=0; i<fields.length; i++)
{ // look up property entry for each field
Map prop_map;
if (Modifier.isStatic(fields[i].getModifiers()))
prop_map = sprop_map; // add to "static" maps
else // add to "object" maps
prop_map = oprop_map;
String name = fields[i].getName();
Property p = (Property)(prop_map.get(name));
if (p==null)
{ // create new Property entry
p = new Property(name);
prop_map.put(name,p);
} // end if
p.setField(fields[i]); // save off field pointer
} // end for
// Freeze the two property maps.
if (sprop_map.isEmpty())
m_static_properties = Collections.EMPTY_MAP;
else
m_static_properties = Collections.unmodifiableMap(sprop_map);
if (oprop_map.isEmpty())
m_object_properties = Collections.EMPTY_MAP;
else
m_object_properties = Collections.unmodifiableMap(oprop_map);
} // end constructor
/*--------------------------------------------------------------------------------
* Internal operations
*--------------------------------------------------------------------------------
*/
private static final boolean isGetterMethod(Method m)
{
Class[] parms = m.getParameterTypes();
if (parms.length!=0)
return false;
String name = m.getName();
if (name.startsWith("get") && (name.length()>3))
return true;
if (name.startsWith("is") && (name.length()>2))
{ // "is" is a valid getter, but only for Booleans
Class rtype = m.getReturnType();
if ((rtype==Boolean.class) || (rtype==Boolean.TYPE))
return true;
} // end if
return false;
} // end isGetterMethod
private static final boolean isSetterMethod(Method m)
{
Class[] parms = m.getParameterTypes();
if (parms.length!=1)
return false;
Class rtype = m.getReturnType();
if (rtype!=Void.TYPE)
return false;
String name = m.getName();
return (name.startsWith("set") && (name.length()>3));
} // end isSetterMethod
private static final String makePropertyName(String name)
{
String rc = null;
if (name.startsWith("get") || name.startsWith("set"))
rc = name.substring(3);
else if (name.startsWith("is"))
rc = name.substring(2);
if (Character.isUpperCase(rc.charAt(0)) && !(Character.isUpperCase(rc.charAt(1))))
return StringUtils.uncapitalise(rc);
else
return rc;
} // end makePropertyName
private static final int getFigureOfMerit(Class param_class, Class actual_class)
{
if (param_class==actual_class)
return 0;
if (param_class.isPrimitive())
return 0;
if (param_class.isInterface())
return 1;
int figm = 0;
while ((actual_class!=Object.class) && (actual_class!=param_class))
{ // go up the class hierarchy until we get a match
actual_class = actual_class.getSuperclass();
figm += 2;
} // end while
return figm;
} // end getFigureOfMerit
private static final int getFigureOfMerit(Method method, Class[] arg_classes)
{
Class[] param_classes = method.getParameterTypes();
if (param_classes.length!=arg_classes.length)
return -1; // parameter count mismatch
int figm = 0;
for (int i=0; i<param_classes.length; i++)
{ // check each parameter type to see which is right
if (!(param_classes[i].isAssignableFrom(arg_classes[i])))
return -1; // parameter type mismatch
figm += getFigureOfMerit(param_classes[i],arg_classes[i]);
} // end for
return figm;
} // end getFigureOfMerit
private static final Method selectMethod(Method[] methods, Object[] args)
{
if (methods.length==1)
return methods[0]; // trivial
Class[] arg_classes = new Class[args.length];
int i;
for (i=0; i<args.length; i++)
arg_classes[i] = args[i].getClass();
Method rc = null;
int current_figm = Integer.MAX_VALUE;
for (i=0; i<methods.length; i++)
{ // get the figure of merit for this method
int figm = getFigureOfMerit(methods[i],arg_classes);
if (figm<0)
continue;
if (figm<current_figm)
{ // this is the new "best" method
rc = methods[i];
current_figm = figm;
} // end if
if (current_figm==0)
break; // can't get any better than this
} // end for
return rc;
} // end selectMethod
private static final Object unwrapObject(Object obj)
{
while (obj instanceof DynamicWrapper)
obj = ((DynamicWrapper)obj).unwrap();
return obj;
} // end unwrapObject
private static final Object[] unwrapArray(Object[] arr)
{
for (int i=0; i<arr.length; i++)
{ // look for a dynamically wrapped object
if (arr[i] instanceof DynamicWrapper)
{ // we need to unwrap at least part of this array - do it
Object[] rc = new Object[arr.length];
if (i>0)
System.arraycopy(arr,0,rc,0,i);
for (int j=i; j<arr.length; j++)
rc[j] = unwrapObject(arr[j]);
return rc;
} // end if
} // end for
return arr; // no need to unwrap anything
} // end unwrapArray
/*--------------------------------------------------------------------------------
* Overrides from class Object
*--------------------------------------------------------------------------------
*/
public boolean equals(Object obj)
{
if (obj==null)
return false;
if (!(obj instanceof JavaDynamicClass))
return false;
JavaDynamicClass other = (JavaDynamicClass)obj;
return m_klass.equals(other.m_klass);
} // end equals
public int hashCode()
{
return m_klass.hashCode();
} // end hashCode
public String toString()
{
return "dynamic " + m_klass.toString();
} // end toString
/*--------------------------------------------------------------------------------
* Implementations from interface NamedObject
*--------------------------------------------------------------------------------
*/
public String getName()
{
return m_klass.getName();
} // end getName
/*--------------------------------------------------------------------------------
* Implementations from interface DynamicClass
*--------------------------------------------------------------------------------
*/
public Object get(String property_name) throws DynamicObjectException
{
Property p = (Property)(m_static_properties.get(property_name));
if (p==null)
throw new CodeNotFoundException(JavaDynamicClass.this,CodeNotFoundException.PROPERTY,property_name);
return p.doGet(null);
} // end get
public void set(String property_name, Object value) throws DynamicObjectException
{
Property p = (Property)(m_static_properties.get(property_name));
if (p==null)
throw new CodeNotFoundException(JavaDynamicClass.this,CodeNotFoundException.PROPERTY,property_name);
p.doSet(null,unwrapObject(value));
} // end set
public Object call(String method_name, Object[] parameters) throws DynamicObjectException
{
Method m = null;
Method[] arr = (Method[])(m_static_methods.get(method_name));
Object[] real_parameters = null;
if (arr!=null)
{ // convert parameters and select
real_parameters = unwrapArray(parameters);
m = selectMethod(arr,real_parameters);
} // end if
if (m==null)
throw new CodeNotFoundException(JavaDynamicClass.this,CodeNotFoundException.CALL,method_name);
try
{ // call the static method
return m.invoke(null,real_parameters);
} // end try
catch (IllegalAccessException e)
{ // translate to CallFailureException
throw new CallFailureException(JavaDynamicClass.this,e);
} // end catch
catch (InvocationTargetException e)
{ // translate to CallFailureException
throw new CallFailureException(JavaDynamicClass.this,e.getCause());
} // end catch
catch (UndeclaredThrowableException e)
{ // translate to CallFailureException
throw new CallFailureException(JavaDynamicClass.this,e.getCause());
} // end catch
} // end call
public Object call(String method_name, List parameters) throws DynamicObjectException
{
return call(method_name,parameters.toArray());
} // end call
public DynamicObject cast(Object source) throws ClassCastException
{
Object obj = unwrapObject(source);
if (m_klass.isInstance(obj))
return new JavaDynamicObject(this,obj);
throw new ClassCastException("not instance of class " + m_klass.getName());
} // end cast
/*--------------------------------------------------------------------------------
* Implementations from interface DynamicWrapper
*--------------------------------------------------------------------------------
*/
public Object unwrap()
{
return m_klass;
} // end unwrap
/*--------------------------------------------------------------------------------
* External operations
*--------------------------------------------------------------------------------
*/
Object getForObject(Object target, String property_name) throws DynamicObjectException
{
Property p = (Property)(m_object_properties.get(property_name));
if (p==null)
p = (Property)(m_static_properties.get(property_name));
if (p==null)
throw new CodeNotFoundException(JavaDynamicClass.this,CodeNotFoundException.PROPERTY,property_name);
return p.doGet(target);
} // end getForObject
void setForObject(Object target, String property_name, Object value) throws DynamicObjectException
{
Property p = (Property)(m_object_properties.get(property_name));
if (p==null)
p = (Property)(m_static_properties.get(property_name));
if (p==null)
throw new CodeNotFoundException(JavaDynamicClass.this,CodeNotFoundException.PROPERTY,property_name);
p.doSet(target,unwrapObject(value));
} // end setForObject
Object callForObject(Object target, String method_name, Object[] parameters) throws DynamicObjectException
{
Method m = null;
Method[] arr = (Method[])(m_object_methods.get(method_name));
if (arr==null)
arr = (Method[])(m_static_methods.get(method_name));
Object[] real_parameters = null;
if (arr!=null)
{ // convert parameters and select
real_parameters = unwrapArray(parameters);
m = selectMethod(arr,real_parameters);
} // end if
if (m==null)
throw new CodeNotFoundException(JavaDynamicClass.this,CodeNotFoundException.CALL,method_name);
try
{ // call the static method
return m.invoke(target,real_parameters);
} // end try
catch (IllegalAccessException e)
{ // translate to CallFailureException
throw new CallFailureException(JavaDynamicClass.this,e);
} // end catch
catch (InvocationTargetException e)
{ // translate to CallFailureException
throw new CallFailureException(JavaDynamicClass.this,e.getCause());
} // end catch
catch (UndeclaredThrowableException e)
{ // translate to CallFailureException
throw new CallFailureException(JavaDynamicClass.this,e.getCause());
} // end catch
} // end callForObject
} // end class JavaDynamicClass

View File

@@ -0,0 +1,121 @@
/*
* The contents of this file are subject to the Mozilla Public License Version 1.1
* (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.mozilla.org/MPL/>.
*
* Software distributed under the License is distributed on an "AS IS" basis, WITHOUT
* WARRANTY OF ANY KIND, either express or implied. See the License for the specific
* language governing rights and limitations under the License.
*
* The Original Code is the Venice Web Communities System.
*
* The Initial Developer of the Original Code is Eric J. Bowersox <erbo@silcom.com>,
* for Silverwrist Design Studios. Portions created by Eric J. Bowersox are
* Copyright (C) 2002 Eric J. Bowersox/Silverwrist Design Studios. All Rights Reserved.
*
* Contributor(s):
*/
package com.silverwrist.dynamo.obj;
import java.util.*;
import java.lang.reflect.*;
import com.silverwrist.dynamo.except.*;
import com.silverwrist.dynamo.iface.*;
class JavaDynamicObject implements DynamicObject, DynamicWrapper
{
/*--------------------------------------------------------------------------------
* Attributes
*--------------------------------------------------------------------------------
*/
private JavaDynamicClass m_dclass;
private Object m_object;
/*--------------------------------------------------------------------------------
* Constructor
*--------------------------------------------------------------------------------
*/
JavaDynamicObject(JavaDynamicClass dclass, Object obj)
{
m_dclass = dclass;
m_object = obj;
} // end constructor
/*--------------------------------------------------------------------------------
* Overrides from class Object
*--------------------------------------------------------------------------------
*/
public boolean equals(Object obj)
{
if (obj==null)
return false;
if (obj instanceof DynamicObject)
return obj.equals(m_object);
else
return m_object.equals(obj);
} // end equals
public int hashCode()
{
return m_object.hashCode();
} // end hashCode
public String toString()
{
return m_object.toString();
} // end toString
/*--------------------------------------------------------------------------------
* Implementations from interface DynamicObject
*--------------------------------------------------------------------------------
*/
public Object get(String property_name) throws DynamicObjectException
{
return m_dclass.getForObject(m_object,property_name);
} // end get
public void set(String property_name, Object value) throws DynamicObjectException
{
m_dclass.setForObject(m_object,property_name,value);
} // end set
public Object call(String method_name, Object[] parameters) throws DynamicObjectException
{
return m_dclass.callForObject(m_object,method_name,parameters);
} // end call
public Object call(String method_name, List parameters) throws DynamicObjectException
{
return m_dclass.callForObject(m_object,method_name,parameters.toArray());
} // end call
public DynamicClass getDClass()
{
return m_dclass;
} // end getDClass
/*--------------------------------------------------------------------------------
* Implementations from interface DynamicWrapper
*--------------------------------------------------------------------------------
*/
public Object unwrap()
{
return m_object;
} // end unwrap
} // end class JavaDynamicObject

View File

@@ -0,0 +1,126 @@
/*
* The contents of this file are subject to the Mozilla Public License Version 1.1
* (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.mozilla.org/MPL/>.
*
* Software distributed under the License is distributed on an "AS IS" basis, WITHOUT
* WARRANTY OF ANY KIND, either express or implied. See the License for the specific
* language governing rights and limitations under the License.
*
* The Original Code is the Venice Web Communities System.
*
* The Initial Developer of the Original Code is Eric J. Bowersox <erbo@silcom.com>,
* for Silverwrist Design Studios. Portions created by Eric J. Bowersox are
* Copyright (C) 2002 Eric J. Bowersox/Silverwrist Design Studios. All Rights Reserved.
*
* Contributor(s):
*/
package com.silverwrist.dynamo.obj;
import java.util.*;
import com.silverwrist.dynamo.iface.*;
public class JavaObjectBindery
{
/*--------------------------------------------------------------------------------
* Static data members
*--------------------------------------------------------------------------------
*/
private static JavaObjectBindery _self = null;
/*--------------------------------------------------------------------------------
* Attributes
*--------------------------------------------------------------------------------
*/
private HashMap m_class_to_dc; // Class object to DynamicClass
private HashMap m_name_to_dc; // classname to DynamicClass
/*--------------------------------------------------------------------------------
* Constructor
*--------------------------------------------------------------------------------
*/
private JavaObjectBindery()
{
m_class_to_dc = new HashMap();
m_name_to_dc = new HashMap();
} // end constructor
/*--------------------------------------------------------------------------------
* External operations
*--------------------------------------------------------------------------------
*/
public synchronized DynamicClass lookupClass(Class klass)
{
DynamicClass rc = (DynamicClass)(m_class_to_dc.get(klass));
if (rc==null)
{ // create new class object and register it
rc = new JavaDynamicClass(klass);
m_class_to_dc.put(klass,rc);
m_name_to_dc.put(klass.getName(),rc);
} // end if
return rc;
} // end lookupClass
public synchronized DynamicClass lookupClass(String name)
{
DynamicClass rc = (DynamicClass)(m_name_to_dc.get(name));
if (rc==null)
{ // class not present, try loading it
try
{ // but we have to load the regular class first
Class klass = Class.forName(name);
rc = new JavaDynamicClass(klass);
m_class_to_dc.put(klass,rc);
m_name_to_dc.put(name,rc);
} // end try
catch (ClassNotFoundException e)
{ // no class found...
return null; // TODO: exception?
} // end catch
} // end if
return rc;
} // end lookupClass
public synchronized void bind(String name, Class klass)
{
DynamicClass dc = new JavaDynamicClass(klass);
m_class_to_dc.put(klass,dc);
m_name_to_dc.put(name,dc);
} // end bind
public synchronized void bind(Class klass)
{
bind(klass.getName(),klass);
} // end bind
/*--------------------------------------------------------------------------------
* External static operations
*--------------------------------------------------------------------------------
*/
public static synchronized JavaObjectBindery get()
{
if (_self==null)
_self = new JavaObjectBindery();
return _self;
} // end get
} // end class JavaObjectBindery