You are viewing a plain text version of this content. The canonical link for it is here.
Posted to taglibs-dev@jakarta.apache.org by lu...@apache.org on 2001/12/18 02:53:15 UTC
cvs commit: jakarta-taglibs/standard/src/org/apache/taglibs/standard/tlv JstlFmtTLV.java JstlCoreTLV.java
luehe 01/12/17 17:53:15
Modified: standard/conf fmt-rt.tld fmt.tld
standard/doc/web I18N_FunctionalDescription_6_EA3.html
standard/examples/web/format FormatNumber.jsp
GermanLocale.jsp MessageFormat.jsp
standard/src/org/apache/taglibs/standard/resources
Resources.properties
standard/src/org/apache/taglibs/standard/tag/common/fmt
FormatNumberSupport.java MessageArgSupport.java
MessageFormatSupport.java MessageSupport.java
ParseDateSupport.java ParseNumberSupport.java
standard/src/org/apache/taglibs/standard/tlv
JstlCoreTLV.java
Added: standard/src/org/apache/taglibs/standard/tlv JstlFmtTLV.java
Log:
Made 'key' optional in <message> and 'value' optional in <messageFormat>, <formatNumber>, <parseNumber>, and <parseDate> (was already optional in <messageArg>). If missing, it is read from the tag's body content
Revision Changes Path
1.7 +8 -8 jakarta-taglibs/standard/conf/fmt-rt.tld
Index: fmt-rt.tld
===================================================================
RCS file: /home/cvs/jakarta-taglibs/standard/conf/fmt-rt.tld,v
retrieving revision 1.6
retrieving revision 1.7
diff -u -r1.6 -r1.7
--- fmt-rt.tld 2001/12/11 23:46:55 1.6
+++ fmt-rt.tld 2001/12/18 01:53:15 1.7
@@ -144,7 +144,7 @@
</description>
<attribute>
<name>key</name>
- <required>true</required>
+ <required>false</required>
<rtexprvalue>true</rtexprvalue>
</attribute>
<attribute>
@@ -178,7 +178,7 @@
</description>
<attribute>
<name>value</name>
- <required>true</required>
+ <required>false</required>
<rtexprvalue>true</rtexprvalue>
</attribute>
<attribute>
@@ -212,13 +212,13 @@
<name>formatNumber</name>
<tag-class>org.apache.taglibs.standard.tag.rt.fmt.FormatNumberTag</tag-class>
<tei-class>org.apache.taglibs.standard.tei.FormatNumberTEI</tei-class>
- <body-content>EMPTY</body-content>
+ <body-content>JSP</body-content>
<description>
Formats a numeric value as a number, currency, or percentage
</description>
<attribute>
<name>value</name>
- <required>true</required>
+ <required>false</required>
<rtexprvalue>true</rtexprvalue>
</attribute>
<attribute>
@@ -252,13 +252,13 @@
<name>parseNumber</name>
<tag-class>org.apache.taglibs.standard.tag.rt.fmt.ParseNumberTag</tag-class>
<tei-class>org.apache.taglibs.standard.tei.ParseNumberTEI</tei-class>
- <body-content>EMPTY</body-content>
+ <body-content>JSP</body-content>
<description>
Parses the string representation of a number, currency, or percentage
</description>
<attribute>
<name>value</name>
- <required>true</required>
+ <required>false</required>
<rtexprvalue>true</rtexprvalue>
</attribute>
<attribute>
@@ -347,13 +347,13 @@
<name>parseDate</name>
<tag-class>org.apache.taglibs.standard.tag.rt.fmt.ParseDateTag</tag-class>
<tei-class>org.apache.taglibs.standard.tei.ParseDateTEI</tei-class>
- <body-content>EMPTY</body-content>
+ <body-content>JSP</body-content>
<description>
Parses the string representation of a date and/or time
</description>
<attribute>
<name>value</name>
- <required>true</required>
+ <required>false</required>
<rtexprvalue>true</rtexprvalue>
</attribute>
<attribute>
1.8 +9 -9 jakarta-taglibs/standard/conf/fmt.tld
Index: fmt.tld
===================================================================
RCS file: /home/cvs/jakarta-taglibs/standard/conf/fmt.tld,v
retrieving revision 1.7
retrieving revision 1.8
diff -u -r1.7 -r1.8
--- fmt.tld 2001/12/11 23:46:55 1.7
+++ fmt.tld 2001/12/18 01:53:15 1.8
@@ -12,7 +12,7 @@
<validator>
<validator-class>
- org.apache.taglibs.standard.tlv.JstlCoreTLV
+ org.apache.taglibs.standard.tlv.JstlFmtTLV
</validator-class>
<init-param>
<param-name>expressionAttributes</param-name>
@@ -190,7 +190,7 @@
</description>
<attribute>
<name>key</name>
- <required>true</required>
+ <required>false</required>
<rtexprvalue>false</rtexprvalue>
</attribute>
<attribute>
@@ -224,7 +224,7 @@
</description>
<attribute>
<name>value</name>
- <required>true</required>
+ <required>false</required>
<rtexprvalue>false</rtexprvalue>
</attribute>
<attribute>
@@ -258,13 +258,13 @@
<name>formatNumber</name>
<tag-class>org.apache.taglibs.standard.tag.el.fmt.FormatNumberTag</tag-class>
<tei-class>org.apache.taglibs.standard.tei.FormatNumberTEI</tei-class>
- <body-content>EMPTY</body-content>
+ <body-content>JSP</body-content>
<description>
Formats a numeric value as a number, currency, or percentage
</description>
<attribute>
<name>value</name>
- <required>true</required>
+ <required>false</required>
<rtexprvalue>false</rtexprvalue>
</attribute>
<attribute>
@@ -298,13 +298,13 @@
<name>parseNumber</name>
<tag-class>org.apache.taglibs.standard.tag.el.fmt.ParseNumberTag</tag-class>
<tei-class>org.apache.taglibs.standard.tei.ParseNumberTEI</tei-class>
- <body-content>EMPTY</body-content>
+ <body-content>JSP</body-content>
<description>
Parses the string representation of a number, currency, or percentage
</description>
<attribute>
<name>value</name>
- <required>true</required>
+ <required>false</required>
<rtexprvalue>false</rtexprvalue>
</attribute>
<attribute>
@@ -393,13 +393,13 @@
<name>parseDate</name>
<tag-class>org.apache.taglibs.standard.tag.el.fmt.ParseDateTag</tag-class>
<tei-class>org.apache.taglibs.standard.tei.ParseDateTEI</tei-class>
- <body-content>EMPTY</body-content>
+ <body-content>JSP</body-content>
<description>
Parses the string representation of a date and/or time
</description>
<attribute>
<name>value</name>
- <required>true</required>
+ <required>false</required>
<rtexprvalue>false</rtexprvalue>
</attribute>
<attribute>
1.2 +45 -33 jakarta-taglibs/standard/doc/web/I18N_FunctionalDescription_6_EA3.html
Index: I18N_FunctionalDescription_6_EA3.html
===================================================================
RCS file: /home/cvs/jakarta-taglibs/standard/doc/web/I18N_FunctionalDescription_6_EA3.html,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -r1.1 -r1.2
--- I18N_FunctionalDescription_6_EA3.html 2001/12/12 20:12:35 1.1
+++ I18N_FunctionalDescription_6_EA3.html 2001/12/18 01:53:15 1.2
@@ -14,7 +14,8 @@
<hr width="100%" noshade></h3>
-<h2> I18N-Capable Formatting Tags: Functional Description</h2>
+<h2>
+I18N-Capable Formatting Tags: Functional Description</h2>
<h2>
<tt><fmt:locale><br>
@@ -29,6 +30,7 @@
<fmt:parseDate><br>
<fmt:exception><br>
<fmt:requestEncoding></tt></h2>
+
<hr width="100%" noshade>
<h3>
1. Introduction</h3>
@@ -190,9 +192,12 @@
A <tt><formatNumber></tt> or <tt><formatDate></tt> action that is
not enclosed within a <tt><bundle> </tt>action.</li>
-<p><br>After an action has called <tt>ServletResponse.setLocale()</tt>,
-it determines the character encoding associated with the locale (by calling
-<tt>ServletResponse.getCharacterEncoding()</tt>) and stores it in the <tt>javax.servlet.jsp.jstl.i18n.request.charset</tt>
+<br>
+<p>
+<p>After an action has called <tt>ServletResponse.setLocale()</tt>, it
+determines the character encoding associated with the locale (by calling
+<tt>ServletResponse.getCharacterEncoding()</tt>)
+and stores it in the <tt>javax.servlet.jsp.jstl.i18n.request.charset</tt>
session attribute. This attribute may be used by the <tt><requestEncoding></tt>
action in a page invoked by a form included in the response to set the
request charset to the same as the response charset. This makes it possible
@@ -311,8 +316,10 @@
<h3>
8. <message></h3>
The <tt><message></tt> action retrieves the localized message corresponding
-to the message key specified by the
-<tt>key</tt> attribute.
+to a given message key.
+<p>The message key may be specified via the
+<tt>key</tt> attribute; if
+missing, it is read from the tag's body content.
<p>The resource bundle in which to look up the message key may be given
by the <tt>bundle</tt> attribute. If this attribute is missing, and the
<tt><message>
@@ -371,8 +378,9 @@
<h3>
9. <messageFormat></h3>
The <tt><messageFormat> </tt>action performs parametric replacement
-on the pattern string specified via the <tt>value</tt> attribute, using
-the runtime's default locale.
+on a given pattern string , using the runtime's default locale.
+<p>The pattern string may be specified via the <tt>value</tt> attribute;
+if missing, it is read from the tag's body content.
<p>The argument values for parametric replacement must be supplied via
<tt><messageArg></tt>
subtags. Each <tt><messageArg></tt> subtag replaces one parameter in
@@ -427,12 +435,14 @@
The <tt><formatNumber></tt> action allows the formatting of numbers,
currencies, and percentages, using predefined or customized formatting
styles.
+<p>The numeric value to be formatted may be specified via the <tt>value</tt>
+attribute; if missing, it is read from the tag's body content.
<p>Depending on the value of the <tt>type</tt> attribute, which must be
-one of "number", "currency", or "percent" (default: "number"), the numeric
-value specified by the <tt>value</tt> attribute is formatted as a number,
-currency, or percentage, respectively, using the default formatting pattern
-for numbers (currencies, percentages) of the page's locale, which is determined
-according to Section 2 of this functional description.
+one of "number", "currency", or "percent" (default: "number"), the given
+numeric value is formatted as a number, currency, or percentage, respectively,
+using the default formatting pattern for numbers (currencies, percentages)
+of the page's locale, which is determined according to Section 2 of this
+functional description.
<p>The result is output to the current
<tt>JspWriter</tt> object, unless
the <tt>var</tt> attribute is given, in which case it is stored (as a string)
@@ -465,7 +475,7 @@
automatically).
<p>The <tt>value</tt> and <tt>pattern</tt> attributes accept both string
literals and EL values.
-<p>If the input to the <tt>value</tt> attribute is a string literal, it
+<p>If the numeric value to be formatted is given as a string literal, it
is first parsed into an instance of <tt>java.lang.Number
</tt>according
to the default pattern of the locale specified by the <tt>parseLocale</tt>
@@ -485,14 +495,15 @@
12. <parseNumber></h3>
The <tt><parseNumber></tt> action is used for parsing numbers, currencies,
and percentages.
+<p>The numeric string to be parsed may be specified via the <tt>value</tt>
+attribute; if missing, it is read from the tag's body content.
<p>Depending on the value of the <tt>type</tt> attribute, which must be
-one of "number", "currency", or "percent" (default: "number"), the string
-specified via the <tt>value</tt> attribute is parsed as a number, currency,
-or percentage, respectively, using the default formatting pattern for numbers
-(currencies, percentages) of the locale specified by the <tt>parseLocale</tt>
-attribute. If the <tt>parseLocale</tt> attribute is missing, the page's
-locale is used, which is determined according to Section 2 of this functional
-description.
+one of "number", "currency", or "percent" (default: "number"), the given
+numeric string is parsed as a number, currency, or percentage, respectively,
+using the default formatting pattern for numbers (currencies, percentages)
+of the locale specified by the <tt>parseLocale</tt> attribute. If the <tt>parseLocale</tt>
+attribute is missing, the page's locale is used, which is determined according
+to Section 2 of this functional description.
<p>If the number specified via the <tt>value</tt> attribute uses a format
different from the page locale's default, the pattern required to parse
it may be specified using the <tt>pattern</tt> attribute.
@@ -580,17 +591,18 @@
<h3>
14. <parseDate></h3>
The <tt><parseDate></tt> action is used for parsing date and time strings.
+<p>The date string to be parsed may be specified via the <tt>value</tt>
+attribute; if missing, it is read from the tag's body content.
<p>Depending on the value of the <tt>type</tt> attribute, which must be
-one of "time", "date", or "both" (default: "date"), the date string given
-via the
-<tt>value</tt> attribute is expected to contain only a time, a
-date, or both a time and date component, respectively. It is parsed according
-to one of the predefined formatting styles for dates (specified via the
-<tt>dateStyle</tt>
-attribute) and times (specified via the <tt>timeStyle</tt> attribute) of
-the locale specified by the <tt>parseLocale</tt> attribute. If the <tt>parseLocale</tt>
-attribute is missing, the page's locale is used, which is determined according
-to Section 2 of this functional description. Legal values for the
+one of "time", "date", or "both" (default: "date"), the given date string
+is expected to contain only a time, a date, or both a time and date component,
+respectively. It is parsed according to one of the predefined formatting
+styles for dates (specified via the
+<tt>dateStyle</tt> attribute) and times
+(specified via the <tt>timeStyle</tt> attribute) of the locale specified
+by the <tt>parseLocale</tt> attribute. If the <tt>parseLocale</tt> attribute
+is missing, the page's locale is used, which is determined according to
+Section 2 of this functional description. Legal values for the
<tt>dateStyle</tt>
and <tt>timeStyle</tt> attributes are "default", "short", "medium ", "long",
and "full" (default: "default").
@@ -688,8 +700,8 @@
<p>If the character encoding of the request parameters is not known in
advance (since the locale and thus character encoding of the page that
generated the form collecting the parameter values was determined dynamically),
-the <tt>value</tt> attribute must not be specified. In this case, the <tt><requestEncoding></tt> action
-first checks if there is a charset defined in the request <tt>Content-Type</tt>
+the <tt>value</tt> attribute must not be specified. In this case, the <tt><requestEncoding></tt>
+action first checks if there is a charset defined in the request <tt>Content-Type</tt>
header. If not, it uses the character encoding from the <tt>javax.servlet.jsp.jstl.i18n.request.charset</tt>
attribute, which is searched in the page, request, session (if valid),
and application scope(s) (in this order). If this attribute is not found,
1.4 +6 -2 jakarta-taglibs/standard/examples/web/format/FormatNumber.jsp
Index: FormatNumber.jsp
===================================================================
RCS file: /home/cvs/jakarta-taglibs/standard/examples/web/format/FormatNumber.jsp,v
retrieving revision 1.3
retrieving revision 1.4
diff -u -r1.3 -r1.4
--- FormatNumber.jsp 2001/12/03 22:43:50 1.3
+++ FormatNumber.jsp 2001/12/18 01:53:15 1.4
@@ -15,7 +15,9 @@
<fmt:formatNumber value="123456789" type="currency"/>
<li> Format as percentage:
- <fmt:formatNumber value="123456789" type="percent"/>
+ <fmt:formatNumber type="percent">
+ 123456789
+ </fmt:formatNumber>
<li> Format as currency, parse, and print parsed result:
<fmt:formatNumber value="123456789" type="currency" var="cur"/>
@@ -27,7 +29,9 @@
<li> Parse numeric string (using 'parseLocale' locale) and format as currency:
<fmt:locale value="de"/>
- <fmt:formatNumber value="12345.67" parseLocale="de" type="currency"/>
+ <fmt:formatNumber parseLocale="de" type="currency">
+ 12345.67
+ </fmt:formatNumber>
</ul>
</body>
1.2 +3 -1 jakarta-taglibs/standard/examples/web/format/GermanLocale.jsp
Index: GermanLocale.jsp
===================================================================
RCS file: /home/cvs/jakarta-taglibs/standard/examples/web/format/GermanLocale.jsp,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -r1.1 -r1.2
--- GermanLocale.jsp 2001/11/21 07:34:35 1.1
+++ GermanLocale.jsp 2001/12/18 01:53:15 1.2
@@ -9,7 +9,9 @@
<fmt:locale value="de"/>
<fmt:bundle basename="org.apache.taglibs.standard.examples.i18n.Resources">
- <fmt:message key="greetingMorning"/>
+ <fmt:message>
+ greetingMorning
+ </fmt:message>
</fmt:bundle>
</body>
1.3 +2 -1 jakarta-taglibs/standard/examples/web/format/MessageFormat.jsp
Index: MessageFormat.jsp
===================================================================
RCS file: /home/cvs/jakarta-taglibs/standard/examples/web/format/MessageFormat.jsp,v
retrieving revision 1.2
retrieving revision 1.3
diff -u -r1.2 -r1.3
--- MessageFormat.jsp 2001/11/21 22:19:52 1.2
+++ MessageFormat.jsp 2001/12/18 01:53:15 1.3
@@ -22,7 +22,8 @@
</fmt:messageFormat>
<li> Using <messageArg> body:<br>
- <fmt:messageFormat value="Current time: {0}">
+ <fmt:messageFormat>
+ Current time: {0}
<fmt:messageArg>
<fmt:formatDate type="both"/>
</fmt:messageArg>
1.4 +17 -2 jakarta-taglibs/standard/src/org/apache/taglibs/standard/resources/Resources.properties
Index: Resources.properties
===================================================================
RCS file: /home/cvs/jakarta-taglibs/standard/src/org/apache/taglibs/standard/resources/Resources.properties,v
retrieving revision 1.3
retrieving revision 1.4
diff -u -r1.3 -r1.4
--- Resources.properties 2001/12/08 22:53:48 1.3
+++ Resources.properties 2001/12/18 01:53:15 1.4
@@ -85,11 +85,26 @@
LOCALE_EMPTY_COUNTRY=\
Empty country component in "value" attribute in <locale>
-MESSAGEARG_OUTSIDE_MESSAGE=\
+MESSAGE_ARG_OUTSIDE_MESSAGE_AND_MESSAGE_FORMAT=\
<messageArg> outside <message> and <messageFormat>
-MESSAGEARG_NO_VALUE=\
+MESSAGE_NO_KEY=\
+ <message> must have "key" attribute or body
+
+MESSAGE_FORMAT_NO_VALUE=\
+ <messageFormat> must have "value" attribute or body
+
+MESSAGE_ARG_NO_VALUE=\
<messageArg> must have "value" attribute or body
+
+FORMAT_NUMBER_NO_VALUE=\
+ <formatNumber> must have "value" attribute or body
+
+PARSE_NUMBER_NO_VALUE=\
+ <parseNumber> must have "value" attribute or body
+
+PARSE_DATE_NO_VALUE=\
+ <parseDate> must have "value" attribute or body
UNDEFINED_KEY=\
Undefined key "{0}" in resource bundle "{1}"
1.5 +7 -1 jakarta-taglibs/standard/src/org/apache/taglibs/standard/tag/common/fmt/FormatNumberSupport.java
Index: FormatNumberSupport.java
===================================================================
RCS file: /home/cvs/jakarta-taglibs/standard/src/org/apache/taglibs/standard/tag/common/fmt/FormatNumberSupport.java,v
retrieving revision 1.4
retrieving revision 1.5
diff -u -r1.4 -r1.5
--- FormatNumberSupport.java 2001/12/12 01:24:19 1.4
+++ FormatNumberSupport.java 2001/12/18 01:53:15 1.5
@@ -70,7 +70,7 @@
* @author Jan Luehe
*/
-public abstract class FormatNumberSupport extends TagSupport {
+public abstract class FormatNumberSupport extends BodyTagSupport {
//*********************************************************************
// Public constants
@@ -144,6 +144,12 @@
// Tag logic
public int doEndTag() throws JspException {
+ if (value == null) {
+ String bcs = getBodyContent().getString();
+ if ((bcs == null) || (value = bcs.trim()).equals(""))
+ throw new JspTagException(
+ Resources.getMessage("FORMAT_NUMBER_NO_VALUE"));
+ }
/*
* If the value given is a string literal, it is first parsed into an
1.2 +8 -7 jakarta-taglibs/standard/src/org/apache/taglibs/standard/tag/common/fmt/MessageArgSupport.java
Index: MessageArgSupport.java
===================================================================
RCS file: /home/cvs/jakarta-taglibs/standard/src/org/apache/taglibs/standard/tag/common/fmt/MessageArgSupport.java,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -r1.1 -r1.2
--- MessageArgSupport.java 2001/11/21 07:39:00 1.1
+++ MessageArgSupport.java 2001/12/18 01:53:15 1.2
@@ -98,16 +98,17 @@
if (parent == null) {
parent = findAncestorWithClass(this, MessageFormatSupport.class);
if (parent == null)
- throw new JspTagException(
- Resources.getMessage("MESSAGEARG_OUTSIDE_MESSAGE"));
+ throw new JspTagException(Resources.getMessage(
+ "MESSAGE_ARG_OUTSIDE_MESSAGE_AND_MESSAGE_FORMAT"));
}
// get argument from 'value' attribute or body, as appropriate
- if (value == null)
- value = getBodyContent().getString();
- if (value == null)
- throw new JspTagException(
- Resources.getMessage("MESSAGEARG_NO_VALUE"));
+ if (value == null) {
+ String bcs = getBodyContent().getString();
+ if ((bcs == null) || (value = bcs.trim()).equals(""))
+ throw new JspTagException(
+ Resources.getMessage("MESSAGE_ARG_NO_VALUE"));
+ }
if (parent instanceof MessageSupport)
((MessageSupport) parent).addMessageArg(value);
1.2 +7 -1 jakarta-taglibs/standard/src/org/apache/taglibs/standard/tag/common/fmt/MessageFormatSupport.java
Index: MessageFormatSupport.java
===================================================================
RCS file: /home/cvs/jakarta-taglibs/standard/src/org/apache/taglibs/standard/tag/common/fmt/MessageFormatSupport.java,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -r1.1 -r1.2
--- MessageFormatSupport.java 2001/11/21 07:39:00 1.1
+++ MessageFormatSupport.java 2001/12/18 01:53:15 1.2
@@ -131,8 +131,14 @@
// Tag logic
public int doEndTag() throws JspException {
- String message = value;
+ if (value == null) {
+ String bcs = getBodyContent().getString();
+ if ((bcs == null) || (value = bcs.trim()).equals(""))
+ throw new JspTagException(
+ Resources.getMessage("MESSAGE_FORMAT_NO_VALUE"));
+ }
+ String message = value;
if (!arguments.isEmpty()) {
MessageFormat formatter = new MessageFormat("");
formatter.applyPattern(value);
1.3 +9 -3 jakarta-taglibs/standard/src/org/apache/taglibs/standard/tag/common/fmt/MessageSupport.java
Index: MessageSupport.java
===================================================================
RCS file: /home/cvs/jakarta-taglibs/standard/src/org/apache/taglibs/standard/tag/common/fmt/MessageSupport.java,v
retrieving revision 1.2
retrieving revision 1.3
diff -u -r1.2 -r1.3
--- MessageSupport.java 2001/12/04 01:17:40 1.2
+++ MessageSupport.java 2001/12/18 01:53:15 1.3
@@ -90,8 +90,8 @@
//*********************************************************************
// Private state
- private String var; // 'var' attribute
- private int scope; // 'scope' attribute
+ private String var; // 'var' attribute
+ private int scope; // 'scope' attribute
private List arguments;
@@ -142,8 +142,14 @@
// Tag logic
public int doEndTag() throws JspException {
- String prefix = null;
+ if (key == null) {
+ String bcs = getBodyContent().getString();
+ if ((bcs == null) || (key = bcs.trim()).equals(""))
+ throw new JspTagException(
+ Resources.getMessage("MESSAGE_NO_KEY"));
+ }
+ String prefix = null;
if (bundle == null) {
Tag t = findAncestorWithClass(this, BundleSupport.class);
if (t != null) {
1.5 +12 -4 jakarta-taglibs/standard/src/org/apache/taglibs/standard/tag/common/fmt/ParseDateSupport.java
Index: ParseDateSupport.java
===================================================================
RCS file: /home/cvs/jakarta-taglibs/standard/src/org/apache/taglibs/standard/tag/common/fmt/ParseDateSupport.java,v
retrieving revision 1.4
retrieving revision 1.5
diff -u -r1.4 -r1.5
--- ParseDateSupport.java 2001/12/12 01:24:19 1.4
+++ ParseDateSupport.java 2001/12/18 01:53:15 1.5
@@ -70,7 +70,7 @@
* @author Jan Luehe
*/
-public abstract class ParseDateSupport extends TagSupport {
+public abstract class ParseDateSupport extends BodyTagSupport {
//*********************************************************************
// Protected state
@@ -140,11 +140,16 @@
// Tag logic
public int doEndTag() throws JspException {
- DateFormat formatter = null;
+ if (value == null) {
+ String bcs = getBodyContent().getString();
+ if ((bcs == null) || (value = bcs.trim()).equals(""))
+ throw new JspTagException(
+ Resources.getMessage("PARSE_DATE_NO_VALUE"));
+ }
/*
- * Use parsing locale specified via the 'parseLocale' attribute.
- * If no such attribute, use page's locale.
+ * Set up parsing locale: Use locale specified via the 'parseLocale'
+ * attribute (if present), or else determine page's locale.
*/
Locale locale = parseLocale;
if (locale == null)
@@ -154,6 +159,8 @@
false,
DateFormat.getAvailableLocales());
+ // Get appropriate formatter instance
+ DateFormat formatter = null;
switch (type) {
case FormatDateSupport.DATE_TYPE:
formatter = DateFormat.getDateInstance(dateStyle, locale);
@@ -182,6 +189,7 @@
if (timeZone != null)
formatter.setTimeZone(timeZone);
+ // Parse date
Date parsed = null;
try {
parsed = formatter.parse(value);
1.4 +12 -4 jakarta-taglibs/standard/src/org/apache/taglibs/standard/tag/common/fmt/ParseNumberSupport.java
Index: ParseNumberSupport.java
===================================================================
RCS file: /home/cvs/jakarta-taglibs/standard/src/org/apache/taglibs/standard/tag/common/fmt/ParseNumberSupport.java,v
retrieving revision 1.3
retrieving revision 1.4
diff -u -r1.3 -r1.4
--- ParseNumberSupport.java 2001/12/12 01:24:19 1.3
+++ ParseNumberSupport.java 2001/12/18 01:53:15 1.4
@@ -70,7 +70,7 @@
* @author Jan Luehe
*/
-public abstract class ParseNumberSupport extends TagSupport {
+public abstract class ParseNumberSupport extends BodyTagSupport {
//*********************************************************************
// Protected state
@@ -127,11 +127,16 @@
// Tag logic
public int doEndTag() throws JspException {
- NumberFormat formatter = null;
+ if (value == null) {
+ String bcs = getBodyContent().getString();
+ if ((bcs == null) || (value = bcs.trim()).equals(""))
+ throw new JspTagException(
+ Resources.getMessage("PARSE_NUMBER_NO_VALUE"));
+ }
/*
- * Use parsing locale specified via the 'parseLocale' attribute.
- * If no such attribute, use page's locale.
+ * Set up parsing locale: Use locale specified via the 'parseLocale'
+ * attribute (if present), or else determine page's locale.
*/
Locale locale = parseLocale;
if (locale == null)
@@ -141,6 +146,8 @@
false,
NumberFormat.getAvailableLocales());
+ // Get appropriate formatter instance
+ NumberFormat formatter = null;
switch (type) {
case FormatNumberSupport.NUMBER_TYPE:
formatter = NumberFormat.getNumberInstance(locale);
@@ -157,6 +164,7 @@
break;
} // switch
+ // Parse number
Number parsed = null;
try {
parsed = formatter.parse(value);
1.7 +0 -39 jakarta-taglibs/standard/src/org/apache/taglibs/standard/tlv/JstlCoreTLV.java
Index: JstlCoreTLV.java
===================================================================
RCS file: /home/cvs/jakarta-taglibs/standard/src/org/apache/taglibs/standard/tlv/JstlCoreTLV.java,v
retrieving revision 1.6
retrieving revision 1.7
diff -u -r1.6 -r1.7
--- JstlCoreTLV.java 2001/12/05 23:10:11 1.6
+++ JstlCoreTLV.java 2001/12/18 01:53:15 1.7
@@ -79,8 +79,6 @@
* 'value' is specified; it *must* have a body otherwise.) For
* these purposes, "having a body" refers to non-whitespace
* content inside the tag.</li>
- * <li><message> with 'messageArgs' attribute must not have any <messageArg>
- * subtags as its direct children.</li>
* <li>Other minor constraints.</li>
* </ul>
*
@@ -119,8 +117,6 @@
private final String PARAM = "param";
private final String URL_ENCODE = "urlEncode";
private final String EXPLANG = "expressionLanguage";
- private final String MESSAGE = "message";
- private final String MESSAGE_ARG = "messageArg";
private final String JSP_TEXT = "jsp:text";
// attribute names
@@ -128,7 +124,6 @@
private final String VALUE = "value";
private final String DEFAULT = "default";
private final String VAR_READER = "varReader";
- private final String MESSAGE_ARGS = "messageArgs";
//*********************************************************************
@@ -152,8 +147,6 @@
private Stack expressionLanguage = new Stack();
private Stack importWithReaderDepths = new Stack();
private Stack importWithoutReaderDepths = new Stack();
- private Stack messageDepths = new Stack();
- private Stack messageHasMessageArgs = new Stack();
private String lastElementName = null;
private boolean bodyNecessary = false;
private boolean bodyIllegal = false;
@@ -250,17 +243,6 @@
prefix, IMPORT, qn));
}
- // check invariants for <message>
- if (isTag(qn, MESSAGE_ARG) && messageChild()
- && ((Boolean) messageHasMessageArgs.peek()).booleanValue()) {
- /*
- * we're a <messageArg> tag and the direct child of
- * <message messageArgs="...">, which is illegal
- */
- fail(Resources.getMessage("TLV_ILLEGAL_PARAM",
- prefix, MESSAGE_ARG, MESSAGE, MESSAGE_ARGS));
- }
-
// now, modify state
// we're a choose, so record new choose-specific state
@@ -277,15 +259,6 @@
importWithoutReaderDepths.push(new Integer(depth));
}
- // if we're in a <message>, record relevant state
- if (isTag(qn, MESSAGE)) {
- messageDepths.push(new Integer(depth));
- if (hasAttribute(a, MESSAGE_ARGS))
- messageHasMessageArgs.push(new Boolean(true));
- else
- messageHasMessageArgs.push(new Boolean(false));
- }
-
// set up a check against illegal attribute/body combinations
bodyIllegal = false;
bodyNecessary = false;
@@ -367,12 +340,6 @@
importWithoutReaderDepths.pop();
}
- // update <message>-related state
- if (isTag(qn, MESSAGE)) {
- messageDepths.pop();
- messageHasMessageArgs.pop();
- }
-
// update language state
if (isTag(qn, EXPLANG))
expressionLanguage.pop();
@@ -385,12 +352,6 @@
private boolean chooseChild() {
return (!chooseDepths.empty()
&& (depth - 1) == ((Integer) chooseDepths.peek()).intValue());
- }
-
- // are we directly under a <message>
- private boolean messageChild() {
- return (!messageDepths.empty()
- && (depth - 1) == ((Integer) messageDepths.peek()).intValue());
}
// returns the top int depth (peeked at) from a Stack of Integer
1.1 jakarta-taglibs/standard/src/org/apache/taglibs/standard/tlv/JstlFmtTLV.java
Index: JstlFmtTLV.java
===================================================================
/*
* The Apache Software License, Version 1.1
*
* Copyright (c) 1999 The Apache Software Foundation. All rights
* reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in
* the documentation and/or other materials provided with the
* distribution.
*
* 3. The end-user documentation included with the redistribution, if
* any, must include the following acknowlegement:
* "This product includes software developed by the
* Apache Software Foundation (http://www.apache.org/)."
* Alternately, this acknowlegement may appear in the software itself,
* if and wherever such third-party acknowlegements normally appear.
*
* 4. The names "The Jakarta Project", "Tomcat", and "Apache Software
* Foundation" must not be used to endorse or promote products derived
* from this software without prior written permission. For written
* permission, please contact apache@apache.org.
*
* 5. Products derived from this software may not be called "Apache"
* nor may "Apache" appear in their names without prior written
* permission of the Apache Group.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
* ====================================================================
*
* This software consists of voluntary contributions made by many
* individuals on behalf of the Apache Software Foundation. For more
* information on the Apache Software Foundation, please see
* <http://www.apache.org/>.
*
*/
package org.apache.taglibs.standard.tlv;
import java.io.*;
import java.util.*;
import javax.servlet.jsp.*;
import javax.servlet.jsp.tagext.*;
import javax.xml.parsers.*;
import org.xml.sax.*;
import org.xml.sax.helpers.*;
import org.apache.taglibs.standard.lang.support.ExpressionEvaluator;
import org.apache.taglibs.standard.lang.support.ExpressionEvaluatorManager;
import org.apache.taglibs.standard.resources.Resources;
/**
* <p>A SAX-based TagLibraryValidator for the JSTL i18n-capable formatting
* library. Currently implements the following checks:</p>
*
* <ul>
* <li>Expression syntax validation, with full support for
* <jx:expressionLanguage></li>
* <li><message> with 'messageArgs' attribute must not have any <messageArg>
* subtags as its direct children.</li>
* <li>Tag bodies that must either be empty or non-empty given
* particular attributes.</li>
* </ul>
*
* @author Shawn Bayern
*/
public class JstlFmtTLV extends JstlBaseTLV {
//*********************************************************************
// Implementation Overview
/*
* We essentially just run the page through a SAX parser, handling
* the callbacks that interest us. We collapse <jsp:text> elements
* into the text they contain, since this simplifies processing
* somewhat. Even a quick glance at the implementation shows its
* necessary, tree-oriented nature: multiple Stacks, an understanding
* of 'depth', and so on all are important as we recover necessary
* state upon each callback. This TLV demonstrates various techniques,
* from the general "how do I use a SAX parser for a TLV?" to
* "how do I read my init parameters and then validate?" But also,
* the specific SAX methodology was kept as general as possible to
* allow for experimentation and flexibility.
*
* Much of the code and structure is duplicated from JstlCoreTLV.
* An effort has been made to re-use code where unambiguously useful.
* However, splitting logic among parent/child classes isn't
* necessarily the cleanest approach when writing a parser like the
* one we need. I'd like to reorganize this somewhat, but it's not
* a priority.
*/
//*********************************************************************
// Constants
// tag names
private final String MESSAGE = "message";
private final String MESSAGE_ARG = "messageArg";
private final String MESSAGE_FORMAT = "messageFormat";
private final String FORMAT_NUMBER = "formatNumber";
private final String PARSE_NUMBER = "parseNumber";
private final String PARSE_DATE = "parseDate";
private final String EXPLANG = "expressionLanguage";
private final String JSP_TEXT = "jsp:text";
// attribute names
private final String EVAL = "evaluator";
private final String MESSAGE_KEY = "key";
private final String MESSAGE_ARGS = "messageArgs";
private final String VALUE = "value";
//*********************************************************************
// Contract fulfillment
protected DefaultHandler getHandler() {
return new Handler();
}
//*********************************************************************
// SAX event handler
/** The handler that provides the base of our implementation. */
private class Handler extends DefaultHandler {
// parser state
private int depth = 0;
private Stack expressionLanguage = new Stack();
private Stack messageDepths = new Stack();
private Stack messageHasMessageArgs = new Stack();
private String lastElementName = null;
private boolean bodyNecessary = false;
private boolean bodyIllegal = false;
public Handler() {
// "install" the default evaluator
String defaultEvaluator = JstlCoreTLVHelper.getEvaluatorName();
if (defaultEvaluator != null)
expressionLanguage.push(defaultEvaluator);
}
// process under the existing context (state), then modify it
public void startElement(
String ns, String ln, String qn, Attributes a) {
// substitute our own parsed 'ln' if it's not provided
if (ln == null)
ln = getLocalPart(qn);
// for simplicity, we can ignore <jsp:text> for our purposes
// (don't bother distinguishing between it and its characters)
if (qn.equals(JSP_TEXT))
return;
// check body-related constraint
if (bodyIllegal)
fail(Resources.getMessage("TLV_ILLEGAL_BODY",
lastElementName));
// temporarily "install" new expression language if appropriate
if (isTag(qn, EXPLANG))
expressionLanguage.push(a.getValue(EVAL));
// validate expression syntax if we need to
Set expAtts;
if (qn.startsWith(prefix + ":")
&& (expAtts = (Set) config.get(ln)) != null) {
for (int i = 0; i < a.getLength(); i++) {
String attName = a.getLocalName(i);
if (expAtts.contains(attName)) {
if (expressionLanguage.empty())
fail("Unexpected failure to determine "
+ "expression language.");
String vMsg =
validateExpression(
(String) expressionLanguage.peek(),
ln,
attName,
a.getValue(i));
if (vMsg != null)
fail(vMsg);
}
}
}
// validate attributes
if (!hasNoInvalidScope(a))
fail(Resources.getMessage("TLV_INVALID_ATTRIBUTE",
SCOPE, qn, a.getValue(SCOPE)));
// check invariants for <message>
if (isTag(qn, MESSAGE_ARG) && messageChild()
&& ((Boolean) messageHasMessageArgs.peek()).booleanValue()) {
/*
* we're a <messageArg> tag and the direct child of
* <message messageArgs="...">, which is illegal
*/
fail(Resources.getMessage("TLV_ILLEGAL_PARAM",
prefix, MESSAGE_ARG, MESSAGE, MESSAGE_ARGS));
}
// now, modify state
// if we're in a <message>, record relevant state
if (isTag(qn, MESSAGE)) {
messageDepths.push(new Integer(depth));
if (hasAttribute(a, MESSAGE_ARGS))
messageHasMessageArgs.push(new Boolean(true));
else
messageHasMessageArgs.push(new Boolean(false));
}
// set up a check against illegal attribute/body combinations
bodyIllegal = false;
bodyNecessary = false;
if (isTag(qn, MESSAGE_ARG)
|| isTag(qn, FORMAT_NUMBER)
|| isTag(qn, PARSE_NUMBER)
|| isTag(qn, PARSE_DATE)) {
if (hasAttribute(a, VALUE))
bodyIllegal = true;
else
bodyNecessary = true;
} else if (isTag(qn, MESSAGE) && !hasAttribute(a, MESSAGE_KEY)) {
bodyNecessary = true;
} else if (isTag(qn, MESSAGE_FORMAT) && !hasAttribute(a, VALUE)) {
bodyNecessary = true;
}
// record the most recent tag (for error reporting)
lastElementName = qn;
lastElementId = a.getValue("id");
// we're a new element, so increase depth
depth++;
}
public void characters(char[] ch, int start, int length) {
// ignore strings that are just whitespace
String s = new String(ch, start, length).trim();
if (s.equals(""))
return;
// check and update body-related constraints
if (bodyIllegal)
fail(Resources.getMessage("TLV_ILLEGAL_BODY",
lastElementName));
bodyNecessary = false; // body is no longer necessary!
}
public void endElement(String ns, String ln, String qn) {
// consistently, we ignore JSP_TEXT
if (qn.equals(JSP_TEXT))
return;
// handle body-related invariant
if (bodyNecessary)
fail(Resources.getMessage("TLV_MISSING_BODY",
lastElementName));
bodyIllegal = false; // reset: we've left the tag
// update <message>-related state
if (isTag(qn, MESSAGE)) {
messageDepths.pop();
messageHasMessageArgs.pop();
}
// update language state
if (isTag(qn, EXPLANG))
expressionLanguage.pop();
// update our depth
depth--;
}
// are we directly under a <message>
private boolean messageChild() {
return (!messageDepths.empty()
&& (depth - 1) == ((Integer) messageDepths.peek()).intValue());
}
}
}
--
To unsubscribe, e-mail: <ma...@jakarta.apache.org>
For additional commands, e-mail: <ma...@jakarta.apache.org>