You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@myfaces.apache.org by ma...@apache.org on 2007/11/23 10:00:14 UTC
svn commit: r597603 - in
/myfaces/shared/trunk/core/src/main/java/org/apache/myfaces/shared:
config/MyfacesConfig.java renderkit/html/HTML.java
renderkit/html/HtmlLinkRendererBase.java
Author: manolito
Date: Fri Nov 23 01:00:12 2007
New Revision: 597603
URL: http://svn.apache.org/viewvc?rev=597603&view=rev
Log:
MYFACES-1774 HtmlLinkRenderer should output & instead of & as the url param separator within href attribute according to HTML Spec
Modified:
myfaces/shared/trunk/core/src/main/java/org/apache/myfaces/shared/config/MyfacesConfig.java
myfaces/shared/trunk/core/src/main/java/org/apache/myfaces/shared/renderkit/html/HTML.java
myfaces/shared/trunk/core/src/main/java/org/apache/myfaces/shared/renderkit/html/HtmlLinkRendererBase.java
Modified: myfaces/shared/trunk/core/src/main/java/org/apache/myfaces/shared/config/MyfacesConfig.java
URL: http://svn.apache.org/viewvc/myfaces/shared/trunk/core/src/main/java/org/apache/myfaces/shared/config/MyfacesConfig.java?rev=597603&r1=597602&r2=597603&view=diff
==============================================================================
--- myfaces/shared/trunk/core/src/main/java/org/apache/myfaces/shared/config/MyfacesConfig.java (original)
+++ myfaces/shared/trunk/core/src/main/java/org/apache/myfaces/shared/config/MyfacesConfig.java Fri Nov 23 01:00:12 2007
@@ -78,6 +78,9 @@
private static final String INIT_PARAM_RENDER_VIEWSTATE_ID = "org.apache.myfaces.RENDER_VIEWSTATE_ID";
private static final boolean INIT_PARAM_RENDER_VIEWSTATE_ID_DEFAULT = true;
+ private static final String INIT_PARAM_STRICT_XHTML_LINKS = "org.apache.myfaces.STRICT_XHTML_LINKS";
+ private static final boolean INIT_PARAM_STRICT_XHTML_LINKS_DEFAULT = true;
+
private boolean _prettyHtml;
private boolean _detectJavascript;
private boolean _allowJavascript;
@@ -88,6 +91,7 @@
private boolean _checkExtensionsFilter;
private boolean _readonlyAsDisabledForSelect;
private boolean _renderViewStateId;
+ private boolean _strictXhtmlLinks;
private static final boolean TOMAHAWK_AVAILABLE;
private static final boolean MYFACES_IMPL_AVAILABLE;
@@ -165,7 +169,9 @@
myfacesConfig.setReadonlyAsDisabledForSelect(getBooleanInitParameter(extCtx, INIT_READONLY_AS_DISABLED_FOR_SELECT,
INIT_READONLY_AS_DISABLED_FOR_SELECT_DEFAULT));
myfacesConfig.setRenderViewStateId(getBooleanInitParameter(extCtx, INIT_PARAM_RENDER_VIEWSTATE_ID,
- INIT_PARAM_RENDER_VIEWSTATE_ID_DEFAULT));
+ INIT_PARAM_RENDER_VIEWSTATE_ID_DEFAULT));
+ myfacesConfig.setStrictXhtmlLinks(getBooleanInitParameter(extCtx, INIT_PARAM_STRICT_XHTML_LINKS,
+ INIT_PARAM_STRICT_XHTML_LINKS_DEFAULT));
myfacesConfig.setConfigRefreshPeriod(getLongInitParameter(extCtx, INIT_PARAM_CONFIG_REFRESH_PERIOD,
INIT_PARAM_CONFIG_REFRESH_PERIOD_DEFAULT));
@@ -335,6 +341,28 @@
public void setRenderViewStateId(boolean renderViewStateId) {
_renderViewStateId = renderViewStateId;
+ }
+
+ /**
+ * <p>W3C recommends to use the "&amp;" entity instead of a plain "&" character within HTML.
+ * This also applies to attribute values and thus to the "href" attribute of <a> elements as well.
+ * Even more, when XHTML is used as output the usage of plain "&" characters is forbidden and would lead to
+ * invalid XML code.
+ * Therefore, since version 1.1.6 MyFaces renders the correct "&amp;" entity for links.</p>
+ * <p>The init parameter
+ * {@link #INIT_PARAM_STRICT_XHTML_LINKS} makes it possible to restore the old behaviour and to make MyFaces
+ * "bug compatible" to the Sun RI which renders plain "&" chars in links as well.</p>
+ * @see <a href="http://www.w3.org/TR/html401/charset.html#h-5.3.2">HTML 4.01 Specification</a>
+ * @see <a href="http://issues.apache.org/jira/browse/MYFACES-1774">Jira: MYFACES-1774</a>
+ * @return true if ampersand characters ("&") should be correctly rendered as "&amp;" entities within link urls (=default),
+ * false for old (XHTML incompatible) behaviour
+ */
+ public boolean isStrictXhtmlLinks() {
+ return _strictXhtmlLinks;
+ }
+
+ public void setStrictXhtmlLinks(boolean strictXhtmlLinks) {
+ _strictXhtmlLinks = strictXhtmlLinks;
}
public boolean isTomahawkAvailable()
Modified: myfaces/shared/trunk/core/src/main/java/org/apache/myfaces/shared/renderkit/html/HTML.java
URL: http://svn.apache.org/viewvc/myfaces/shared/trunk/core/src/main/java/org/apache/myfaces/shared/renderkit/html/HTML.java?rev=597603&r1=597602&r2=597603&view=diff
==============================================================================
--- myfaces/shared/trunk/core/src/main/java/org/apache/myfaces/shared/renderkit/html/HTML.java (original)
+++ myfaces/shared/trunk/core/src/main/java/org/apache/myfaces/shared/renderkit/html/HTML.java Fri Nov 23 01:00:12 2007
@@ -485,7 +485,7 @@
String HREF_PATH_SEPARATOR = "/";
String HREF_PATH_FROM_PARAM_SEPARATOR = "?";
- String HREF_PARAM_SEPARATOR = "&";
+ //removed because wrong for XHTML and not used anyway: String HREF_PARAM_SEPARATOR = "&";
String HREF_PARAM_NAME_FROM_VALUE_SEPARATOR = "=";
}
Modified: myfaces/shared/trunk/core/src/main/java/org/apache/myfaces/shared/renderkit/html/HtmlLinkRendererBase.java
URL: http://svn.apache.org/viewvc/myfaces/shared/trunk/core/src/main/java/org/apache/myfaces/shared/renderkit/html/HtmlLinkRendererBase.java?rev=597603&r1=597602&r2=597603&view=diff
==============================================================================
--- myfaces/shared/trunk/core/src/main/java/org/apache/myfaces/shared/renderkit/html/HtmlLinkRendererBase.java (original)
+++ myfaces/shared/trunk/core/src/main/java/org/apache/myfaces/shared/renderkit/html/HtmlLinkRendererBase.java Fri Nov 23 01:00:12 2007
@@ -22,6 +22,7 @@
import org.apache.myfaces.shared.renderkit.RendererUtils;
import org.apache.myfaces.shared.renderkit.html.util.FormInfo;
import org.apache.myfaces.shared.renderkit.html.util.JavascriptUtils;
+import org.apache.myfaces.shared.config.MyfacesConfig;
import javax.faces.application.StateManager;
import javax.faces.application.ViewHandler;
@@ -321,6 +322,9 @@
String viewId = facesContext.getViewRoot().getViewId();
String path = viewHandler.getActionURL(facesContext, viewId);
+ boolean strictXhtmlLinks
+ = MyfacesConfig.getCurrentInstance(facesContext.getExternalContext()).isStrictXhtmlLinks();
+
StringBuffer hrefBuf = new StringBuffer(path);
//add clientId parameter for decode
@@ -329,7 +333,11 @@
hrefBuf.append('?');
}
else {
- hrefBuf.append('&');
+ if (strictXhtmlLinks) {
+ hrefBuf.append("&");
+ } else {
+ hrefBuf.append('&');
+ }
}
String hiddenFieldName = HtmlRendererUtils.getHiddenCommandLinkFieldName(findNestingForm(component, facesContext));
hrefBuf.append(hiddenFieldName);
@@ -337,13 +345,17 @@
hrefBuf.append(clientId);
if (getChildCount(component) > 0) {
- addChildParametersToHref(component, hrefBuf,
+ addChildParametersToHref(facesContext, component, hrefBuf,
false, //not the first url parameter
writer.getCharacterEncoding());
}
StateManager stateManager = facesContext.getApplication().getStateManager();
- hrefBuf.append("&");
+ if (strictXhtmlLinks) {
+ hrefBuf.append("&");
+ } else {
+ hrefBuf.append('&');
+ }
if (stateManager.isSavingStateInClient(facesContext)) {
hrefBuf.append(URL_STATE_MARKER);
}
@@ -354,18 +366,19 @@
null);
}
- private void addChildParametersToHref(UIComponent linkComponent,
+ private void addChildParametersToHref(FacesContext facesContext,
+ UIComponent linkComponent,
StringBuffer hrefBuf,
boolean firstParameter,
- String charEncoding)
- throws IOException {
+ String charEncoding) throws IOException {
+ boolean strictXhtmlLinks
+ = MyfacesConfig.getCurrentInstance(facesContext.getExternalContext()).isStrictXhtmlLinks();
for (Iterator it = getChildren(linkComponent).iterator(); it.hasNext();) {
UIComponent child = (UIComponent) it.next();
if (child instanceof UIParameter) {
String name = ((UIParameter) child).getName();
Object value = ((UIParameter) child).getValue();
-
- addParameterToHref(name, value, hrefBuf, firstParameter, charEncoding);
+ addParameterToHref(name, value, hrefBuf, firstParameter, charEncoding, strictXhtmlLinks);
firstParameter = false;
}
}
@@ -379,7 +392,7 @@
String href = org.apache.myfaces.shared.renderkit.RendererUtils.getStringValue(facesContext, output);
if (getChildCount(output) > 0) {
StringBuffer hrefBuf = new StringBuffer(href);
- addChildParametersToHref(output, hrefBuf,
+ addChildParametersToHref(facesContext, output, hrefBuf,
(href.indexOf('?') == -1), //first url parameter?
writer.getCharacterEncoding());
href = hrefBuf.toString();
@@ -397,13 +410,26 @@
writer.flush();
}
- private static void addParameterToHref(String name, Object value, StringBuffer hrefBuf, boolean firstParameter, String charEncoding)
- throws UnsupportedEncodingException {
+ private static void addParameterToHref(String name,
+ Object value,
+ StringBuffer hrefBuf,
+ boolean firstParameter,
+ String charEncoding,
+ boolean strictXhtmlLinks) throws UnsupportedEncodingException {
if (name == null) {
throw new IllegalArgumentException("Unnamed parameter value not allowed within command link.");
}
- hrefBuf.append(firstParameter ? "?" : "&");
+ if (firstParameter) {
+ hrefBuf.append('?');
+ } else {
+ if (strictXhtmlLinks) {
+ hrefBuf.append("&");
+ } else {
+ hrefBuf.append('&');
+ }
+ }
+
hrefBuf.append(URLEncoder.encode(name, charEncoding));
hrefBuf.append('=');
if (value != null) {