vgritsenko 2004/01/23 05:56:13
Modified: src/blocks/woody/java/org/apache/cocoon/woody/transformation
EffectWidgetReplacingPipe.java
Log:
Add support for <wd:validation-error/> tag.
InsertStylingContentHandler -> StylingContentHandler.
Remove unnecessary type casts.
Javadoc changes.
Revision Changes Path
1.5 +120 -69
cocoon-2.1/src/blocks/woody/java/org/apache/cocoon/woody/transformation/EffectWidgetReplacingPipe.java
Index: EffectWidgetReplacingPipe.java
===================================================================
RCS file:
/home/cvs/cocoon-2.1/src/blocks/woody/java/org/apache/cocoon/woody/transformation/EffectWidgetReplacingPipe.java,v
retrieving revision 1.4
retrieving revision 1.5
diff -u -r1.4 -r1.5
--- EffectWidgetReplacingPipe.java 5 Jan 2004 16:59:39 -0000 1.4
+++ EffectWidgetReplacingPipe.java 23 Jan 2004 13:56:13 -0000 1.5
@@ -58,10 +58,12 @@
import org.apache.avalon.excalibur.pool.Recyclable;
import org.apache.cocoon.i18n.I18nUtils;
import org.apache.cocoon.woody.Constants;
+import org.apache.cocoon.woody.datatype.ValidationError;
import org.apache.cocoon.woody.formmodel.Repeater;
import org.apache.cocoon.woody.formmodel.Struct;
import org.apache.cocoon.woody.formmodel.Union;
import org.apache.cocoon.woody.formmodel.Widget;
+import org.apache.cocoon.woody.formmodel.Field;
import org.apache.cocoon.xml.AbstractXMLPipe;
import org.apache.cocoon.xml.SaxBuffer;
import org.apache.commons.jxpath.JXPathException;
@@ -69,10 +71,10 @@
import org.xml.sax.SAXException;
import org.xml.sax.helpers.AttributesImpl;
-
// TODO: Reduce the Element creation and deletion churn by using startElement
// and endElement methods which do not create or use Elements on the stack.
// The corresponding TODO in the EffectPipe needs to be completed first.
+
/**
* The basic operation of this Pipe is that it replaces wt:widget (in the
* [EMAIL PROTECTED] Constants#WT_NS} namespace) tags (having an id
attribute)
@@ -85,11 +87,17 @@
* <p>For more information about the supported tags and their function, see
the user documentation
* for the woody template transformer.</p>
*
- * CVS $Id$
* @author Timothy Larson
+ * @version CVS $Id$
*/
public class EffectWidgetReplacingPipe extends EffectPipe {
+ /**
+ * Form location attribute on <code>wt:form-template</code> element,
containing
+ * JXPath expression which should result in Form object.
+ *
+ * @see WoodyPipelineConfig#findForm
+ */
private static final String LOCATION = "location";
private static final String CLASS = "class";
@@ -102,6 +110,7 @@
private static final String STRUCT = "struct";
private static final String STYLING_EL = "styling";
private static final String UNION = "union";
+ private static final String VALIDATION_ERROR = "validation-error";
private static final String WIDGET_LABEL = "widget-label";
private static final String WIDGET = "widget";
@@ -111,26 +120,27 @@
protected Widget widget;
protected Map classes;
- private final DocHandler docHandler = new
DocHandler();
- private final FormHandler formHandler = new
FormHandler();
- private final NestedHandler nestedHandler = new
NestedHandler();
- private final WidgetLabelHandler widgetLabelHandler = new
WidgetLabelHandler();
- private final WidgetHandler widgetHandler = new
WidgetHandler();
- private final RepeaterSizeHandler repeaterSizeHandler = new
RepeaterSizeHandler();
- private final RepeaterWidgetLabelHandler repeaterWidgetLabelHandler =
new RepeaterWidgetLabelHandler();
- private final RepeaterWidgetHandler repeaterWidgetHandler = new
RepeaterWidgetHandler();
- private final StructHandler structHandler = new
StructHandler();
- private final UnionHandler unionHandler = new
UnionHandler();
- private final UnionPassThruHandler unionPassThruHandler = new
UnionPassThruHandler();
- private final NewHandler newHandler = new
NewHandler();
- private final ClassHandler classHandler = new
ClassHandler();
- private final ContinuationIdHandler continuationIdHandler = new
ContinuationIdHandler();
- private final InsertStylingContentHandler stylingHandler = new
InsertStylingContentHandler();
+ private final DocHandler docHandler = new
DocHandler();
+ private final FormHandler formHandler = new
FormHandler();
+ private final NestedHandler nestedHandler = new
NestedHandler();
+ private final WidgetLabelHandler widgetLabelHandler = new
WidgetLabelHandler();
+ private final WidgetHandler widgetHandler = new
WidgetHandler();
+ private final RepeaterSizeHandler repeaterSizeHandler = new
RepeaterSizeHandler();
+ private final RepeaterWidgetLabelHandler repeaterWidgetLabelHandler =
new RepeaterWidgetLabelHandler();
+ private final RepeaterWidgetHandler repeaterWidgetHandler = new
RepeaterWidgetHandler();
+ private final StructHandler structHandler = new
StructHandler();
+ private final UnionHandler unionHandler = new
UnionHandler();
+ private final UnionPassThruHandler unionPassThruHandler = new
UnionPassThruHandler();
+ private final NewHandler newHandler = new
NewHandler();
+ private final ClassHandler classHandler = new
ClassHandler();
+ private final ContinuationIdHandler continuationIdHandler = new
ContinuationIdHandler();
+ private final StylingContentHandler stylingHandler = new
StylingContentHandler();
+ private final ValidationErrorHandler validationErrorHandler = new
ValidationErrorHandler();
/**
* Map containing all handlers
*/
- private final Map templates = new HashMap(10, 1);
+ private final Map templates = new HashMap(12, 1);
protected WoodyPipelineConfig pipeContext;
@@ -157,6 +167,7 @@
templates.put(NEW, newHandler);
templates.put(CLASS, classHandler);
templates.put(CONTINUATION_ID, continuationIdHandler);
+ templates.put(VALIDATION_ERROR, validationErrorHandler);
}
private void throwSAXException(String message) throws SAXException{
@@ -230,7 +241,7 @@
//==============================================
// Handler classes to transform Woody templates
//==============================================
-
+
public class DocHandler extends Handler {
public Handler process() throws SAXException {
switch (event) {
@@ -271,8 +282,7 @@
out.startPrefixMapping(Constants.WI_PREFIX, Constants.WI_NS);
// ====> Retrieve the form
-
- // first look for the form using the location attribute, if
any
+ // First look for the form using the location attribute, if
any
String formJXPath = input.attrs.getValue(LOCATION);
if (formJXPath != null) {
// remove the location attribute
@@ -291,7 +301,7 @@
pipeContext.setLocale(I18nUtils.parseLocale(localeAttr));
} else if (pipeContext.getLocaleParameter() != null) { //
then use locale specified as transformer parameter, if any
pipeContext.setLocale(pipeContext.getLocaleParameter());
- } else {
+ } else {
//TODO pull this locale stuff also up in the Config
object?
// use locale specified in bizdata supplied for form
Object locale = null;
@@ -367,10 +377,13 @@
gotStylingElement = false;
out.bufferInit();
return this;
+
case EVENT_ELEMENT:
- if (Constants.WI_NS.equals(input.uri) &&
STYLING_EL.equals(input.loc))
+ if (Constants.WI_NS.equals(input.uri) &&
STYLING_EL.equals(input.loc)) {
gotStylingElement = true;
+ }
return bufferHandler;
+
case EVENT_END_ELEMENT:
stylingHandler.recycle();
stylingHandler.setSaxFragment(out.getBuffer());
@@ -380,6 +393,7 @@
widget = null;
out.bufferFini();
return this;
+
default:
out.copy();
return this;
@@ -505,8 +519,8 @@
if ("case".equals(input.loc)) {
String id = input.attrs.getValue("id");
if (id == null) throwSAXException("Element \"case\"
missing required \"id\" attribute.");
- String value =
(String)((Union)contextWidget).getValue();
- if (id.equals( value != null ? value : "")) {
+ String value = (String)contextWidget.getValue();
+ if (id.equals(value != null ? value : "")) {
return nestedHandler;
} else {
return nullHandler;
@@ -536,7 +550,7 @@
case EVENT_ELEMENT:
if (Constants.WT_NS.equals(input.uri)) {
if ("case".equals(input.loc)) {
- if
(((Union)contextWidget).getValue().equals(input.attrs.getValue("id"))) {
+ if
(contextWidget.getValue().equals(input.attrs.getValue("id"))) {
return nestedHandler;
} else {
return nullHandler;
@@ -628,6 +642,85 @@
}
}
+ /**
+ * This ContentHandler helps in inserting SAX events before the closing
tag of the root
+ * element.
+ */
+ public class StylingContentHandler extends AbstractXMLPipe implements
Recyclable {
+ private int elementNesting;
+ private SaxBuffer saxBuffer;
+
+ public void setSaxFragment(SaxBuffer saxFragment) {
+ saxBuffer = saxFragment;
+ }
+
+ public void recycle() {
+ super.recycle();
+ elementNesting = 0;
+ saxBuffer = null;
+ }
+
+ public void startElement(String uri, String loc, String raw,
Attributes a)
+ throws SAXException {
+ elementNesting++;
+ super.startElement(uri, loc, raw, a);
+ }
+
+ public void endElement(String uri, String loc, String raw)
+ throws SAXException {
+ elementNesting--;
+ if (elementNesting == 0 && saxBuffer != null) {
+ if (gotStylingElement) {
+ // Just deserialize
+ saxBuffer.toSAX(contentHandler);
+ } else {
+ // Insert an enclosing <wi:styling>
+ out.startElement(Constants.WI_NS, STYLING_EL,
Constants.WI_PREFIX_COLON + STYLING_EL, Constants.EMPTY_ATTRS);
+ saxBuffer.toSAX(contentHandler);
+ out.endElement(Constants.WI_NS, STYLING_EL,
Constants.WI_PREFIX_COLON + STYLING_EL);
+ }
+ }
+ super.endElement(uri, loc, raw);
+ }
+ }
+
+ /**
+ * Inserts validation errors (if any) for the Field widgets
+ */
+ public class ValidationErrorHandler extends Handler {
+ public Handler process() throws SAXException {
+ switch (event) {
+ case EVENT_START_ELEMENT:
+ widgetId = getWidgetId(input.attrs);
+ widget = getWidget(widgetId);
+ out.bufferInit();
+ return this;
+
+ case EVENT_ELEMENT:
+ return bufferHandler;
+
+ case EVENT_END_ELEMENT:
+ // FIXME: Use to-be-introduced interface instead of Field
class
+ if (widget instanceof Field) {
+ ValidationError error =
((Field)widget).getValidationError();
+ if (error != null) {
+ out.startElement(Constants.WI_NS, VALIDATION_ERROR,
Constants.WI_PREFIX_COLON + VALIDATION_ERROR, Constants.EMPTY_ATTRS);
+ error.generateSaxFragment(stylingHandler);
+ out.endElement(Constants.WI_NS, VALIDATION_ERROR,
Constants.WI_PREFIX_COLON + VALIDATION_ERROR);
+ }
+ }
+ widget = null;
+ out.bufferFini();
+ return this;
+
+ default:
+ out.copy();
+ return this;
+ }
+ }
+ }
+
+
private Attributes translateAttributes(Attributes attributes, String[]
names) {
AttributesImpl newAtts = new AttributesImpl(attributes);
if (names!= null) {
@@ -635,7 +728,7 @@
String name = names[i];
int position = newAtts.getIndex(name);
String newValue =
pipeContext.translateText(newAtts.getValue(position));
- newAtts.setValue(position, newValue);
+ newAtts.setValue(position, newValue);
}
}
return newAtts;
@@ -697,47 +790,5 @@
this.widget = null;
widgetId = null;
this.namespacePrefix = null;
- }
-
- /**
- * This ContentHandler helps in inserting SAX events before the closing
tag of the root
- * element.
- */
- public class InsertStylingContentHandler extends AbstractXMLPipe
implements Recyclable {
- private int elementNesting;
- private SaxBuffer saxBuffer;
-
- public void setSaxFragment(SaxBuffer saxFragment) {
- saxBuffer = saxFragment;
- }
-
- public void recycle() {
- super.recycle();
- elementNesting = 0;
- saxBuffer = null;
- }
-
- public void startElement(String uri, String loc, String raw,
Attributes a)
- throws SAXException {
- elementNesting++;
- super.startElement(uri, loc, raw, a);
- }
-
- public void endElement(String uri, String loc, String raw)
- throws SAXException {
- elementNesting--;
- if (elementNesting == 0 && saxBuffer != null) {
- if (gotStylingElement) {
- // Just deserialize
- saxBuffer.toSAX(contentHandler);
- } else {
- // Insert an enclosing <wi:styling>
- out.startElement(Constants.WI_NS, STYLING_EL,
Constants.WI_PREFIX_COLON + STYLING_EL, Constants.EMPTY_ATTRS);
- saxBuffer.toSAX(contentHandler);
- out.endElement(Constants.WI_NS, STYLING_EL,
Constants.WI_PREFIX_COLON + STYLING_EL);
- }
- }
- super.endElement(uri, loc, raw);
- }
}
}