How can I get JSF 2.0 to include JS as "app / javascript" instead of "text / javascript",

In our JSF 2.0 application at work, we include several javascript files through <h:outputscript> .

 <h:outputScript library="javascript" name="DoStuff.js"/> 

As a result, html refers to them as text / javascript.

 <script type="text/javascript" src="/mycontext/javax.faces.resource/DoStuff.js.jsf?ln=javascript"></script> 

According to this question , "text / javascript" is deprecated, what more, htmlunit complains about the type rather verbose. Of course, everything works fine, and I could turn off htmlunit logging, but I would prefer JSF to generate the correct type.

Is there a way to override the type selected by <h:outputscript> ?

+6
source share
1 answer

This is hard-coded in the default renderer <h:outputScript> . Assuming you are using Mojarra, this is com.sun.faces.renderkit.html_basic.ScriptRenderer . According to the source, the type attribute was set in the startElement method. You can simply override it:

 public class ExtendedScriptRenderer extends ScriptRenderer { @Override protected void startElement(ResponseWriter writer, UIComponent component) throws IOException { writer.startElement("script", component); writer.writeAttribute("type", "application/javascript", "type"); } } 

Or if you want to give enduser the ability to specify the type attribute and the default application/javascript if not specified:

 public class ExtendedScriptRenderer extends ScriptRenderer { @Override protected void startElement(ResponseWriter writer, UIComponent component) throws IOException { writer.startElement("script", component); String type = (String) component.getAttributes().get("type"); if (type == null) type = "application/javascript"; writer.writeAttribute("type", type, "type"); } } 

To run it, register it in faces-config.xml as follows:

 <render-kit> <renderer> <component-family>javax.faces.Output</component-family> <renderer-type>javax.faces.resource.Script</renderer-type> <renderer-class>com.example.ExtendedScriptRenderer</renderer-class> </renderer> </render-kit> 

There, by the way, is also a good @FacesRenderer annotation, which should work as follows

 @FacesRenderer(componentFamily="javax.faces.Output", rendererType="javax.faces.resource.Script") public class ExtendedScriptRenderer extends ScriptRenderer { // ... } 

However, if it is already defined by the standard renderer ( ScriptRenderer !), Then the user cannot override it with @FacesRenderer . See also question 1748 .

+6
source

Source: https://habr.com/ru/post/892651/


All Articles