eclipse-ee4j/mojarra

outputStylesheet resource expression renders invalid resource URI "/ctx/jakarta.faces.resource/library/somefile.png.faces.resource/theme.css.xhtml?ln=lib-for-css"

Closed this issue · 7 comments

Describe the bug

When using #{resource} inside css file its URI gets mangled up in ResourceImpl.getRequestPath:279
For some reason it gets FacesMapping EXTENSION with incorrect pattern, see image:
image

To Reproduce

Steps to reproduce the behavior:

  1. Include resource dynamically inside css file
  2. observe that the final css generated by application gets bad URI for the resource:

Original CSS has this expression:
src: url("#{resource['primefaces-mytheme:fonts/open-sans-v13-latin-regular.eot']}");

What ends on page is:
src: url("/ite/jakarta.faces.resource/fonts/open-sans-v13-latin-regular.eot.faces.resource/theme.css.xhtml?ln=primefaces-mytheme");
Everything starting from .faces.resource/theme.css... is unwanted and most likely coming from ´Referer´ header

I have been able to trace this to
C:/.m2/repository/org/glassfish/jakarta.faces/4.0.5/jakarta.faces-4.0.5-sources.jar!/com/sun/faces/application/resource/ResourceImpl.java:279

@Override
public String getRequestPath() {
FacesContext context = FacesContext.getCurrentInstance();
HttpServletMapping mapping = getFacesMapping(context);

// If it is prefix/path mapped, e.g *.xhtml -> /jakarta.faces.resource/name.xhtml
uri = RESOURCE_IDENTIFIER + '/' + mapping.getPattern().replace("*", getResourceName());

Where it does some replace based on the mapping resolved earlier.
Also noticed that since the URI requesting the resource is the css file itself, browser attaches the Referer to the file instead of the base xhtml page.

Expected behavior
Correct URI for the resource, same as when the #{resource} is resolved on normal FacesServlet served page.

Screenshots

Additional context
Using JEE10 stack with Mojarra Faces impl 4.0.5
OpenLiberty 23.0.0.12
Omnifaces 4.2
PrimeFaces 12.0.7
Made manual jar modifications to faces-config.xml file to exclude Omnifaces and PrimeFaces preconfigured resource-handlers.

FacesServlet defined minimally:

    <servlet-mapping>
        <servlet-name>Faces Servlet</servlet-name>
        <url-pattern>*.xhtml</url-pattern>
    </servlet-mapping>

I did manage to work around this issue for my own css files by inlining the rules that had #{resource..} however this is still issue for external resources that use dynamic resources like primeicons (tries to load fonts but gets bad URI)

Simplest way I found to reproduce this seems to be just to create css file with single rule where some url is resolved and request that css via GET, it is easily observable that the URI rendered in the css is incorrect.

Another way to bypass the issue would be to use Omnifaces UnmappedResourceHandler as it removes the need to have
#{resource[..]} and allows defining the url in a simpler way

I get you're using GlassFish. Which version exactly? The mapping info (the HttpServletMappingImpl instance) is provided by GlassFish so it's a bug in GlassFish if it gives incorrect information.

@BalusC Forgot to mention the container but I am using Open Liberty 23.0.0.12

For some reason I thought open liberty used MyFaces?

Could be - I am actually including Mojarra jar in my war as I could not get JEE 9 and 10 to run with their feature faces-4.0. It just would not recognize that faces 4 should be used and started to look for old jsf classes. With Mojarra impl included manually it runs

This is a bug in server, not in JSF. JSF does not create HttpServletMapping implementation, the server does. JSF is merely reading the information returned by server.

I guess that the OpenLiberty version being used has a bug in extracting the extension, that it is only looking at the first occurrence of the period character instead of the last occurrence, or that it forgot to split beforehand after the last slash.

Try another server and you'll see.

Ok, I will verify this with some other container at some point. Closing this for now since not classified as JSF issue but WLP bug.