📄 valuestack.java
字号:
public String toString() {
String str = "Value stack\n";
str += "===========\n";
for (int i = 0; i < valueList.size(); i++) {
Object val = valueList.get(i);
str += val == null ? "null\n" : val.toString() + "\n";
}
str += "===========\n";
return str;
}
/**
* Get the parser associated with this ValueStack
*
* @return the Parser for this ValueStack
*/
private Parser getParser(String expression) {
if (parser == null) {
parser = new Parser(new StringReader(expression));
parser.setValueStack(this);
} else {
parser.ReInit(new StringReader(expression));
}
return parser;
}
/**
* Get a method with a given name.
*
* @param cl the class of the method
* @param name the name of the method
* @return the wanted method
* @exception IntrospectionException
*/
protected MethodInfo[] getMethod(Class cl, String name)
throws IntrospectionException {
Map methods = (Map) classes.get(cl);
if (methods == null) {
// Get methods that can be invoked for this class
methods = new HashMap();
// Find get methods for properties
BeanInfo bi = Introspector.getBeanInfo(cl);
PropertyDescriptor[] pd = bi.getPropertyDescriptors();
for (int i = 0; i < pd.length; ++i) {
Method method = pd[i].getReadMethod();
// Check if readable property
if (method != null) {
if (!Modifier.isPublic(cl.getModifiers())) {
// Find a method in an interface that *is* public
Class[] interfaces = bi.getBeanDescriptor().getBeanClass().getInterfaces();
for (int j = 0; j < interfaces.length; j++) {
try {
//log.debug("Try "+interfaces[j]);
method = interfaces[j].getMethod(method.getName(), new Class[0]);
break;
} catch (Exception e) {
// Ignore
}
}
// We're in trouble! Try to sneak through security
if (method.equals(pd[i].getReadMethod())) {
AccessibleObject.setAccessible(new AccessibleObject[]{method}, true);
}
}
// Save method in map
//log.debug( "GET_METHOD: class: " + cl + " method: " + method.getName());
methods.put(pd[i].getName(), new MethodInfo[]{new MethodInfo(method)});
}
}
// Find param methods
Method[] getters = cl.getMethods();
for (int i = 0; i < getters.length; i++) {
Method method = getters[i];
if (!method.getName().startsWith("set") && !method.getReturnType().equals(Void.TYPE)) {
// Valid method
// Check if public
if (!Modifier.isPublic(cl.getModifiers())) {
// Find a method in an interface that *is* public
Class[] interfaces = cl.getInterfaces();
for (int j = 0; j < interfaces.length; j++) {
try {
method = interfaces[j].getMethod(method.getName(), method.getParameterTypes());
break;
} catch (Exception e) {
// Ignore
}
}
// We're in trouble! Try to sneak through security
if (method.equals(getters[i])) {
AccessibleObject.setAccessible(new AccessibleObject[]{method}, true);
}
}
// Get name
String methodName = method.getName();
if (methodName.startsWith("get"))
methodName = Introspector.decapitalize(methodName.substring(3));
else if (methodName.startsWith("is"))
methodName = Introspector.decapitalize(methodName.substring(2));
// Save method in map
MethodInfo[] current = (MethodInfo[]) methods.get(methodName);
MethodInfo[] newlist;
if (current == null) {
newlist = new MethodInfo[]{new MethodInfo(method)};
} else {
newlist = new MethodInfo[current.length + 1];
System.arraycopy(current, 0, newlist, 0, current.length);
newlist[current.length] = new MethodInfo(method);
}
methods.put(methodName, newlist);
//log.debug( "GET_METHOD: class: " + cl + " method: " + method.getName());
}
}
// Add map to class map
// RO: Use clone to avoid synchronization
Map newClassMap = (Map) ((HashMap) classes).clone();
newClassMap.put(cl, methods);
classes = newClassMap;
//log.debug("Added "+cl+" to class map:"+methods);
}
// Get named method/property getter
MethodInfo[] nameMethods = (MethodInfo[]) methods.get(name);
//log.debug("Got "+cl+" "+name+":"+m);
return nameMethods;
}
protected MethodInfo findMethod(MethodInfo[] m, Object[] params) {
if (m.length == 1)
return m[0];
MethodInfo oneMatch = null;
List match = null;
int noOfArgument = params.length;
// Do not create the ArrayList when it is not necessary (the most common case!)
for (int i = 0; i < m.length; i++) {
if (m[i].getNrOfParameters() == noOfArgument)
{
if (oneMatch == null)
oneMatch = m[i];
else
{
if (match == null)
{
match = new ArrayList();
match.add(oneMatch);
}
match.add(m[i]);
}
}
}
// If there is no list then there is either 1 match or 0 matches.
// Just return the oneMatch variable then
if (match == null)
return oneMatch;
//log.debug("No of match for: " + m[0].getName() + " , " + noOfArgument + ", " + match.size());
MethodInfo exact = null;
List close = new ArrayList();
List convert = new ArrayList();
for (Iterator i = match.iterator(); i.hasNext();) {
MethodInfo current = (MethodInfo) i.next();
Class[] paramClass = current.getParameterTypes();
boolean exactMatch = true;
boolean closeMatch = true;
boolean convertable = true;
for (int j = 0; j < paramClass.length; j++) {
Class p = params[j].getClass();
//log.debug("Argument: " + j + " , parameterClass: " + paramClass[j].getName()
//+ " , argumentClass: " + p.getName());
if (paramClass[j].getName().equals(p.getName())) {
continue;
} else if (paramClass[j].isAssignableFrom(p)) {
exactMatch = false;
continue;
} else {
exactMatch = false;
closeMatch = false;
try {
// Get property editor
PropertyEditor pe = BeanUtil.getPropertyEditor(paramClass[j]);
if (pe == null) {
convertable = false;
}
else {
// Convert value
BeanUtil.getAsValue(pe, params[j].toString());
}
} catch (Exception e) {
convertable = false;
}
if (!convertable)
break;
}
}
if (exactMatch) {
exact = current;
break;
} else if (closeMatch) {
close.add(current);
} else if (convertable) {
convert.add(current);
}
}
if (exact != null)
return exact;
else if (close.size() > 0)
return (MethodInfo) close.get(0);
else if (convert.size() > 0)
return (MethodInfo) convert.get(0);
else
return null;
}
/**
* Class that holds information about a method and the parameter types
* that the method accepts, and the number of parameters
*/
private static class MethodInfo
{
Method _method;
Class[] _parameterTypes;
int _nrOfParameters;
public MethodInfo(Method method)
{
_method = method;
_parameterTypes = method.getParameterTypes();
_nrOfParameters = _parameterTypes.length;
}
public Method getMethod()
{
return _method;
}
public Class[] getParameterTypes()
{
return _parameterTypes;
}
public int getNrOfParameters()
{
return _nrOfParameters;
}
}
protected Object getParameter(String aName)
{
return ActionContext.getParameters().get(aName);
}
// Inner classes -------------------------------------------------
// Value providers that want to use lazy evaluation should use this
// interface
public interface ValueHolder {
// Public -----------------------------------------------------
public Object getValue();
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -