Moved the value marshalling code out of SetFieldRule and into a separate
class. Created a digester rule that sets public fields of objects based on element attributes. git-svn-id: https://samskivert.googlecode.com/svn/trunk@477 6335cc39-0255-0410-8fd6-9bcaacd3b74c
This commit is contained in:
@@ -0,0 +1,84 @@
|
|||||||
|
//
|
||||||
|
// $Id: ValueMarshaller.java,v 1.1 2001/11/26 23:44:40 mdb Exp $
|
||||||
|
|
||||||
|
package com.samskivert.util;
|
||||||
|
|
||||||
|
import java.util.HashMap;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Provides a mechanism for converting a string representation of a value
|
||||||
|
* into a Java object when provided with the type of the target object.
|
||||||
|
* This is used to do things like populate object fields with values
|
||||||
|
* parsed from an XML file and the like.
|
||||||
|
*/
|
||||||
|
public class ValueMarshaller
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* Attempts to convert the specified value to an instance of the
|
||||||
|
* specified object type.
|
||||||
|
*
|
||||||
|
* @exception Exception thrown if no field parser exists for the
|
||||||
|
* target type or if an error occurs while parsing the value.
|
||||||
|
*/
|
||||||
|
public static Object unmarshal (Class type, String source)
|
||||||
|
throws Exception
|
||||||
|
{
|
||||||
|
// look up an argument parser for the field type
|
||||||
|
Parser parser = (Parser)_parsers.get(type);
|
||||||
|
if (parser == null) {
|
||||||
|
String errmsg = "Don't know how to convert strings into " +
|
||||||
|
"values of type '" + type + "].";
|
||||||
|
throw new Exception(errmsg);
|
||||||
|
}
|
||||||
|
return parser.parse(source);
|
||||||
|
}
|
||||||
|
|
||||||
|
protected static interface Parser
|
||||||
|
{
|
||||||
|
public Object parse (String source) throws Exception;
|
||||||
|
}
|
||||||
|
|
||||||
|
protected static HashMap _parsers;
|
||||||
|
|
||||||
|
protected static final int[] INT_ARRAY_PROTOTYPE = new int[0];
|
||||||
|
protected static final String[] STRING_ARRAY_PROTOTYPE = new String[0];
|
||||||
|
|
||||||
|
static {
|
||||||
|
_parsers = new HashMap();
|
||||||
|
|
||||||
|
// we can parse strings
|
||||||
|
_parsers.put(String.class, new Parser() {
|
||||||
|
public Object parse (String source) throws Exception {
|
||||||
|
return source;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// and ints
|
||||||
|
_parsers.put(Integer.TYPE, new Parser() {
|
||||||
|
public Object parse (String source) throws Exception {
|
||||||
|
return Integer.valueOf(source);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// and integers
|
||||||
|
_parsers.put(Integer.class, new Parser() {
|
||||||
|
public Object parse (String source) throws Exception {
|
||||||
|
return Integer.valueOf(source);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// and int arrays
|
||||||
|
_parsers.put(INT_ARRAY_PROTOTYPE.getClass(), new Parser() {
|
||||||
|
public Object parse (String source) throws Exception {
|
||||||
|
return StringUtil.parseIntArray(source);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// and string arrays, oh my!
|
||||||
|
_parsers.put(STRING_ARRAY_PROTOTYPE.getClass(), new Parser() {
|
||||||
|
public Object parse (String source) throws Exception {
|
||||||
|
return StringUtil.parseStringArray(source);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,5 +1,5 @@
|
|||||||
//
|
//
|
||||||
// $Id: SetFieldRule.java,v 1.1 2001/11/17 03:45:52 mdb Exp $
|
// $Id: SetFieldRule.java,v 1.2 2001/11/26 23:44:40 mdb Exp $
|
||||||
//
|
//
|
||||||
// samskivert library - useful routines for java programs
|
// samskivert library - useful routines for java programs
|
||||||
// Copyright (C) 2001 Walter Korman
|
// Copyright (C) 2001 Walter Korman
|
||||||
@@ -21,13 +21,13 @@
|
|||||||
package com.samskivert.xml;
|
package com.samskivert.xml;
|
||||||
|
|
||||||
import java.lang.reflect.Field;
|
import java.lang.reflect.Field;
|
||||||
import java.util.HashMap;
|
|
||||||
|
|
||||||
import org.xml.sax.Attributes;
|
import org.xml.sax.Attributes;
|
||||||
import org.apache.commons.digester.Digester;
|
import org.apache.commons.digester.Digester;
|
||||||
import org.apache.commons.digester.Rule;
|
import org.apache.commons.digester.Rule;
|
||||||
|
|
||||||
import com.samskivert.util.StringUtil;
|
import com.samskivert.util.StringUtil;
|
||||||
|
import com.samskivert.util.ValueMarshaller;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Sets a field in the object on the top of the stack with a value parsed
|
* Sets a field in the object on the top of the stack with a value parsed
|
||||||
@@ -70,70 +70,12 @@ public class SetFieldRule extends Rule
|
|||||||
_bodyText + "' on '" + top + "'.");
|
_bodyText + "' on '" + top + "'.");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// convert the source string into an object and set the field
|
||||||
Field field = top.getClass().getField(_fieldName);
|
Field field = top.getClass().getField(_fieldName);
|
||||||
|
Object value = ValueMarshaller.unmarshal(field.getType(), _bodyText);
|
||||||
// look up an argument parser for the field type
|
field.set(top, value);
|
||||||
Parser parser = (Parser)_parsers.get(field.getType());
|
|
||||||
if (parser == null) {
|
|
||||||
String errmsg = "Don't know how to convert strings into " +
|
|
||||||
"fields of type '" + field.getType() +
|
|
||||||
"' [field=" + _fieldName + ", target=" + top + "].";
|
|
||||||
throw new Exception(errmsg);
|
|
||||||
}
|
|
||||||
|
|
||||||
// parse the text and set the field
|
|
||||||
field.set(top, parser.parse(_bodyText));
|
|
||||||
}
|
|
||||||
|
|
||||||
protected static interface Parser
|
|
||||||
{
|
|
||||||
public Object parse (String source) throws Exception;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
protected String _fieldName;
|
protected String _fieldName;
|
||||||
protected String _bodyText;
|
protected String _bodyText;
|
||||||
|
|
||||||
protected static HashMap _parsers;
|
|
||||||
|
|
||||||
protected static final int[] INT_ARRAY_PROTOTYPE = new int[0];
|
|
||||||
protected static final String[] STRING_ARRAY_PROTOTYPE = new String[0];
|
|
||||||
|
|
||||||
static {
|
|
||||||
_parsers = new HashMap();
|
|
||||||
|
|
||||||
// we can parse strings
|
|
||||||
_parsers.put(String.class, new Parser() {
|
|
||||||
public Object parse (String source) throws Exception {
|
|
||||||
return source;
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
// and ints
|
|
||||||
_parsers.put(Integer.TYPE, new Parser() {
|
|
||||||
public Object parse (String source) throws Exception {
|
|
||||||
return Integer.valueOf(source);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
// and integers
|
|
||||||
_parsers.put(Integer.class, new Parser() {
|
|
||||||
public Object parse (String source) throws Exception {
|
|
||||||
return Integer.valueOf(source);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
// and int arrays
|
|
||||||
_parsers.put(INT_ARRAY_PROTOTYPE.getClass(), new Parser() {
|
|
||||||
public Object parse (String source) throws Exception {
|
|
||||||
return StringUtil.parseIntArray(source);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
// and string arrays, oh my!
|
|
||||||
_parsers.put(STRING_ARRAY_PROTOTYPE.getClass(), new Parser() {
|
|
||||||
public Object parse (String source) throws Exception {
|
|
||||||
return StringUtil.parseStringArray(source);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,78 @@
|
|||||||
|
//
|
||||||
|
// $Id: SetPropertyFieldsRule.java,v 1.1 2001/11/26 23:44:40 mdb Exp $
|
||||||
|
//
|
||||||
|
// samskivert library - useful routines for java programs
|
||||||
|
// Copyright (C) 2001 Walter Korman
|
||||||
|
//
|
||||||
|
// This library is free software; you can redistribute it and/or modify it
|
||||||
|
// under the terms of the GNU Lesser General Public License as published
|
||||||
|
// by the Free Software Foundation; either version 2.1 of the License, or
|
||||||
|
// (at your option) any later version.
|
||||||
|
//
|
||||||
|
// This library is distributed in the hope that it will be useful,
|
||||||
|
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||||
|
// Lesser General Public License for more details.
|
||||||
|
//
|
||||||
|
// You should have received a copy of the GNU Lesser General Public
|
||||||
|
// License along with this library; if not, write to the Free Software
|
||||||
|
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||||
|
|
||||||
|
package com.samskivert.xml;
|
||||||
|
|
||||||
|
import java.lang.reflect.Field;
|
||||||
|
|
||||||
|
import org.xml.sax.Attributes;
|
||||||
|
import org.apache.commons.digester.Digester;
|
||||||
|
import org.apache.commons.digester.Rule;
|
||||||
|
|
||||||
|
import com.samskivert.util.StringUtil;
|
||||||
|
import com.samskivert.util.ValueMarshaller;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Sets the fields in the object on the top of the stack from the
|
||||||
|
* attributes available in the matched element.
|
||||||
|
*/
|
||||||
|
public class SetPropertyFieldsRule extends Rule
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* Constructs a set property fields rule.
|
||||||
|
*/
|
||||||
|
public SetPropertyFieldsRule (Digester digester)
|
||||||
|
{
|
||||||
|
super(digester);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void begin (Attributes attrs)
|
||||||
|
throws Exception
|
||||||
|
{
|
||||||
|
Object top = digester.peek();
|
||||||
|
Class topclass = top.getClass();
|
||||||
|
|
||||||
|
// iterate over the attributes, setting public fields where
|
||||||
|
// applicable
|
||||||
|
for (int i = 0; i < attrs.getLength(); i++) {
|
||||||
|
String name = attrs.getLocalName(i);
|
||||||
|
if (StringUtil.blank(name)) {
|
||||||
|
name = attrs.getQName(i);
|
||||||
|
}
|
||||||
|
|
||||||
|
// look for a public field with this name
|
||||||
|
Field field = topclass.getField(name);
|
||||||
|
if (field == null) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
// convert the value into the appropriate object type
|
||||||
|
String valstr = attrs.getValue(i);
|
||||||
|
Object value = ValueMarshaller.unmarshal(field.getType(), valstr);
|
||||||
|
if (digester.getDebug() >= 9) {
|
||||||
|
digester.log(" Setting property '" + name + "' to '" +
|
||||||
|
valstr + "'");
|
||||||
|
}
|
||||||
|
|
||||||
|
// and finally set the field
|
||||||
|
field.set(top, value);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user