5

I've got this weird problem with ajax redirect on a security constraint:

When an ajax call is made (by clicking on a sortable p:dataTable column or when a p:poll triggers) on a role-secured page after my session timed out, a <partial-response><redirect-url=... XML from OmniFaces is shown on the screen.

When I remove OmniFaces, the ajax calls seem to fail silently and I don't get the XML shown.

Security is configured as following in web.xml:

<security-constraint>
    <web-resource-collection>
        <web-resource-name>Pages</web-resource-name>
        <url-pattern>/*</url-pattern>
    </web-resource-collection>
    <auth-constraint>
        <role-name>user</role-name>
    </auth-constraint>
</security-constraint>

<security-constraint>
    <web-resource-collection>
        <web-resource-name>Resources</web-resource-name>
        <url-pattern>/javax.faces.resource/*</url-pattern>
    </web-resource-collection>
</security-constraint>

<login-config>
    <auth-method>FORM</auth-method>
    <realm-name>myRealm</realm-name>
    <form-login-config>
        <form-login-page>/login.xhtml</form-login-page>
        <form-error-page>/login.xhtml?error=true</form-error-page>
    </form-login-config>
</login-config>

<security-role>
    <role-name>user</role-name>
</security-role>
BalusC
  • 1,082,665
  • 372
  • 3,610
  • 3,555
Xavier Dury
  • 1,530
  • 1
  • 16
  • 23
  • 1
    To exclude one and other, what if you keep the `*.xhtml` URL pattern and leave out the `/javax.faces.resource/*` URL pattern and the `UnmappedResourceHandler`? – BalusC Mar 07 '16 at 10:34
  • Still got the problem after removing `/javax.faces.resource/*` and `UnmappedResourceHandler` – Xavier Dury Mar 07 '16 at 10:38
  • 1
    OK, not related to `UnmappedResourceHandler` thus. I recommend to reframe your question based on new findings. Which authentication framework and which server are you using? – BalusC Mar 07 '16 at 10:42
  • You're right. I am using the built-in JAAS authentication from Wildfly 10. – Xavier Dury Mar 07 '16 at 10:49
  • This is really strange then, just changing the pattern of the faces servlet from `*.jsf` to `*.xhtml` causes the problem. – Xavier Dury Mar 07 '16 at 11:01
  • This suggests the partial response isn't correctly interpreted as XML. Can you please tell the headers of the response delivering the ` – BalusC Mar 07 '16 at 11:04
  • OK this is becoming even more crazy: I retested in incognito mode to be sure the browser was not caching anything and I didn't get the problem anymore... BUT if I reload the page (not resubmit) then I get the following XML on screen: `<![CDATA[ 3658514315843208572:3158599428863791426 ]]>`. If I add `/javax.faces.resource/*` and `UnmappedResourceHandler`, then I get ``. – Xavier Dury Mar 07 '16 at 11:34
  • 1
    Reproduced it, this is a WildFly specific quirk/bug. I have [fixed](https://github.com/omnifaces/omnifaces/commit/c9726022f881a143fe9cb59f20485c3f528526eb) it in OmniFaces 2.3 SNAPSHOT. Can you give it a try? – BalusC Mar 07 '16 at 12:07
  • OK, I tested the fix and it's working now. Thanks! – Xavier Dury Mar 07 '16 at 12:21

1 Answers1

5

I reproduced it. This is a strange quirk/bug in WildFly itself.

What's happening here?

By default, without OmniFaces, when a request is fired on a constrained page while the session is expired, the server by default returns the entire HTML page identified by <form-login-page> as response, regardless of the source of the request. This obviously fails with JSF ajax requests as the JavaScript responsible for processing ajax requests couldn't deal with a whole HTML page as response where it expected a special XML response. The user is left with no form of feedback. This is since OmniFaces 1.2 fixed in its OmniPartialViewContext, triggered by this related question: ViewExpiredException not thrown on ajax request if JSF page is protected by j_security_check.

With OmniFaces, a special JSF ajax redirect response in form of <partial-response><redirect url="originalURL"> is returned instead of the entire login page, and the security constraint is triggered once again, but this time with a real synchronous request instead of an JSF ajax request. When the server returns the entire <form-login-page>, it would work just fine this way.

WildFly (tested only 10.0.0 as of now), however, appears to cache the entire <form-login-page> response of the 1st security constraint hit in the session (whereas it is expected to cache only the associated request) and return exactly that response on every hit of a constrained request. That's why you see the initial <partial-response> XML response every time.

As per this commit I have bypassed it by explicitly invalidating the session once again before generating the ajax redirect in OmniPartialViewContext. The fix is available in OmniFaces 2.3.

Community
  • 1
  • 1
BalusC
  • 1,082,665
  • 372
  • 3,610
  • 3,555
  • I couldn't reproduce the `*.jsf` / `*.xhtml` problem when I tested with my browser in incognito/private mode. So, this could be some sort of caching problem on my side. – Xavier Dury Mar 07 '16 at 12:45
  • It works with WildFly 8.2.0 too. If Ajax request is made after session timeout, the is shown. Is OmniFaces 2.3-SNAPSHOT for Jsf 2.3 ? When will be the official version to use with this Bugfix? – Tony Mar 07 '16 at 13:32
  • No, OmniFaces 2.x is still for JSF 2.2. Only OmniFaces 3.x will be for JSF 2.3. I expect to release OmniFaces 2.3 RC1 this week (the most important part, is finally as good as finished) – BalusC Mar 07 '16 at 13:34
  • Thank you, it was a great help from you. – Tony Mar 07 '16 at 13:40
  • @BalusC, on this answer: http://stackoverflow.com/a/12505713/309402 you provide almost the full solution to the issue, following what you did in your commit am I right to assume it is only missing the invalidateSession() in the try {} statement? If so, it would be nice if you added the missing line in your answer for the folks like me that do not rely on omnifaces. – Guillaume Malartre May 05 '16 at 18:00