commons-user mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Simon Kitching <skitch...@apache.org>
Subject Re: [Digester] Inheritance ?
Date Tue, 11 Oct 2005 20:38:22 GMT
On Tue, 2005-10-11 at 09:06 +0200, Sebastian Komander wrote:
> Hi all,
> 
> I try to load an XML file into JavaBeans with Jakarta Digester.
> The xml-File looks like the following:
> 
> <?xml version="1.0" encoding="UFT-8"?>
> <survey>
> 	<title>test</title>
> 	<description>blah blah blah</description>
> 	<page ID="0">
> 		<question required="true">
> 			<text>Testfrage</text>
> 			<freeAnswer/>
> 		</question>
> 		<question>
> 			<text>Testfrage</text>
> 			<choose>
> 				<chooseText>a</chooseText>
> 				<chooseText>b</chooseText>			                 </choose>
> 		</question>
> 	</page>
> </survey>
> 
> I have a abstract class question. And two concret classes:
> TextQuestion: For a normal Textquestion(xml: survey/page/question, the
> first question)
> SelectQuestion: For a SelectQuestion(xml: survey/page/question, the second
> question).
> 
> So, if there is an element "freeAnswer", the class "TextQuestion" should
> be initiated, if there is an element "choose" found under
> survey/page/question, the SelectQuestion should be initiated and added to
> the Survey class.
> 
> It works well with only one type of question, and a concrete class
> "Question". But if I change the type to abstract and create two classes
> (TextQuestion and SelectQuestion), I geht an
> "java.lang.InstantiationException", cause the Digester tries to initiate
> the class "Question".
> 
> Can you tell me how I can use inheritance in digester.
> I can use a CreateFactory, but this isn't what I want.

This is likely to be quite complex to implement. It's trivial if the
information needed to decide what subclass you want is in the start
element attributes; FactoryCreateRule handles this. But when that info
is in a child element things aren't nearly so easy.

Digester is based upon SAX, which means that digester doesn't store data
up for decisions to be made later. So you can't ask digester to "store
all the data under the <question> tag until I have enough information to
decide what object I want to create to represent that tag, then execute
the rules". 

Maybe you could use NodeCreateRule for the <question> tag to create a
DOM tree and push it onto the stack, then have another rule which is
associated with the same element which then walks that DOM tree to
decide what object to create. You'll need to write that tree-walking
code yourself though.

ie:
  digester.addNodeCreate("survey/page/question");

  MyQuestionHandlerRule myQuestionHandlerRule 
    = new MyQuestionHandlerRule();
  digester.addRule("survey/page/question", myQuestionHandlerRule);

where MyQuestionHandlerRule has:
  public void end(String namespace, String name) {
    Node node = digester.peek();

    // walk the node tree, create the Question subclass
    // and initialise it
    Question question = ....;

    // now emulate a SetNextRule
    Page page = digester.peek(1);
    page.addQuestion(question);
  }

Good luck.

Simon


---------------------------------------------------------------------
To unsubscribe, e-mail: commons-user-unsubscribe@jakarta.apache.org
For additional commands, e-mail: commons-user-help@jakarta.apache.org


Mime
View raw message