KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > apache > cocoon > woody > binding > JXPathBindingBase


1 /*
2  * Copyright 1999-2004 The Apache Software Foundation.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */

16 package org.apache.cocoon.woody.binding;
17
18 import java.util.HashMap JavaDoc;
19 import java.util.Map JavaDoc;
20
21 import org.apache.avalon.framework.logger.LogEnabled;
22 import org.apache.avalon.framework.logger.Logger;
23 import org.apache.cocoon.util.jxpath.DOMFactory;
24 import org.apache.cocoon.woody.formmodel.Widget;
25 import org.apache.commons.jxpath.JXPathContext;
26 import org.w3c.dom.Node JavaDoc;
27
28 /**
29  * Provides a base class for hooking up Binding implementations that use the
30  * Jakarta Commons <a HREF="http://jakarta.apache.org/commons/jxpath/index.html">
31  * JXPath package</a>.
32  *
33  * @version CVS $Id: JXPathBindingBase.java 30932 2004-07-29 17:35:38Z vgritsenko $
34  */

35 public abstract class JXPathBindingBase implements Binding, LogEnabled {
36
37     /**
38      * Avalon Logger to use in all subclasses.
39      */

40     private Logger logger;
41
42     /**
43      * Object holding the values of the common objects on all Bindings.
44      */

45     private final JXPathBindingBuilderBase.CommonAttributes commonAtts;
46
47     /**
48      * Parent binding of this binding.
49      */

50     protected Binding parent;
51
52     /**
53      * Cache of class definitions
54      */

55     protected Map JavaDoc classes;
56
57     private JXPathBindingBase() {
58         this(JXPathBindingBuilderBase.CommonAttributes.DEFAULT);
59     }
60
61     protected JXPathBindingBase(
62             JXPathBindingBuilderBase.CommonAttributes commonAtts) {
63         this.commonAtts = commonAtts;
64     }
65
66     /**
67      * Sets parent binding.
68      */

69     public void setParent(Binding binding) {
70         this.parent = binding;
71     }
72
73     /**
74      * Returns binding definition id.
75      */

76     public String JavaDoc getId() {
77         return null;
78     }
79
80     public Binding getClass(String JavaDoc id) {
81         Binding classBinding = null;
82         if (classes != null) {
83             // Query cache for class
84
classBinding = (Binding)classes.get(id);
85         }
86         if (classBinding == null) {
87             // Query parent for class
88
if (parent != null) {
89                 classBinding = parent.getClass(id);
90                 // Cache result
91
if (classes == null) {
92                    classes = new HashMap JavaDoc();
93                 }
94                 classes.put(id, classBinding);
95             } else {
96                 // TODO: Improve message to include source location.
97
throw new RuntimeException JavaDoc("Class \"" + id + "\" not found.");
98             }
99         }
100         return classBinding;
101     }
102
103     protected Widget getWidget(Widget widget, String JavaDoc id) {
104         Widget childWidget = widget.getWidget(id);
105         if (childWidget != null) {
106             return childWidget;
107         } else {
108             throw new RuntimeException JavaDoc(getClass().getName() + ": Widget \"" +
109                     id + "\" does not exist in container \"" +
110                     widget.getFullyQualifiedId() + "\" (" +
111                     widget.getLocation() + ").");
112         }
113     }
114
115     /**
116      * Performs the actual load binding regardless of the configured value of the "direction" attribute.
117      * Abstract method that subclasses need to implement for specific activity.
118      */

119     public abstract void doLoad(Widget frmModel, JXPathContext jxpc)
120         throws BindingException;
121
122     /**
123      * Redefines the Binding action as working on a JXPathContext Type rather
124      * then on generic objects.
125      * Executes the actual loading via {@link #doLoad(Widget, JXPathContext)}
126      * depending on the configured value of the "direction" attribute.
127      */

128     public final void loadFormFromModel(Widget frmModel, JXPathContext jxpc)
129             throws BindingException {
130         boolean inheritedLeniency = jxpc.isLenient();
131         applyLeniency(jxpc);
132         if (this.commonAtts.loadEnabled) {
133             doLoad(frmModel, jxpc);
134         }
135         jxpc.setLenient(inheritedLeniency);
136     }
137
138     /**
139      * Hooks up with the more generic Binding of any objectModel by wrapping
140      * it up in a JXPathContext object and then transfering control over to
141      * the new overloaded version of this method.
142      */

143     public final void loadFormFromModel(Widget frmModel, Object JavaDoc objModel)
144             throws BindingException {
145         if (objModel != null) {
146             JXPathContext jxpc = makeJXPathContext(objModel);
147             loadFormFromModel(frmModel, jxpc);
148         } else {
149             throw new NullPointerException JavaDoc(
150                     "null object passed to loadFormFromModel() method");
151         }
152     }
153
154     /**
155      * Performs the actual save binding regardless of the configured value of the "direction" attribute.
156      * Abstract method that subclasses need to implement for specific activity.
157      */

158     public abstract void doSave(Widget frmModel, JXPathContext jxpc)
159             throws BindingException;
160
161     /**
162      * Redefines the Binding action as working on a JXPathContext Type rather
163      * then on generic objects.
164      * Executes the actual saving via {@link #doSave(Widget, JXPathContext)}
165      * depending on the configured value of the "direction" attribute.
166      */

167     public final void saveFormToModel(Widget frmModel, JXPathContext jxpc)
168             throws BindingException{
169         boolean inheritedLeniency = jxpc.isLenient();
170         applyLeniency(jxpc);
171         if (this.commonAtts.saveEnabled) {
172             doSave(frmModel, jxpc);
173         }
174         jxpc.setLenient(inheritedLeniency);
175     }
176
177     /**
178      * Hooks up with the more generic Binding of any objectModel by wrapping
179      * it up in a JXPathContext object and then transfering control over to
180      * the new overloaded version of this method.
181      */

182     public void saveFormToModel(Widget frmModel, Object JavaDoc objModel)
183                 throws BindingException {
184         if (objModel != null) {
185             JXPathContext jxpc = makeJXPathContext(objModel);
186             saveFormToModel(frmModel, jxpc);
187         } else {
188             throw new NullPointerException JavaDoc(
189                     "null object passed to saveFormToModel() method");
190         }
191     }
192
193     private void applyLeniency(JXPathContext jxpc) {
194         if (this.commonAtts.leniency != null) {
195             jxpc.setLenient(this.commonAtts.leniency.booleanValue());
196         }
197     }
198
199     private JXPathContext makeJXPathContext(Object JavaDoc objModel) {
200         JXPathContext jxpc;
201         if (!(objModel instanceof JXPathContext)) {
202             jxpc = JXPathContext.newContext(objModel);
203             jxpc.setLenient(true);
204             if (objModel instanceof Node JavaDoc) {
205                 jxpc.setFactory(new DOMFactory());
206             }
207         } else {
208             jxpc = (JXPathContext) objModel;
209         }
210         return jxpc;
211     }
212
213     /**
214      * Receives the Avalon logger to use.
215      * Subclasses should always start with <code>super.enableLogging(logger)
216      * </code> in possible overriding versions.
217      */

218     public void enableLogging(Logger logger) {
219         this.logger = logger;
220     }
221
222     protected Logger getLogger() {
223         return logger;
224     }
225 }
226
Popular Tags