Problem with UIDL requests

Hello,

I’m making some tests with 2 UI, respectivelly 2 Servlets Vaadin project. Both are mapped respecitevelly to:

Login /* Desktop /desktop

Login servlet’s UIDL requests are working OK. Unfortunately Desktop’s UIDL requests are giving me “Communication error” and server is returning some default html not expected JSON.

I did some fast debuging and find out that ServletPortletHelper.isUIDLRequest(request) has a bug. It calls follwoing method:

    private static boolean hasPathPrefix(VaadinRequest request, String prefix) {
        String pathInfo = request.getPathInfo();

        if (pathInfo == null) {
            return false;
        }

        if (!prefix.startsWith("/")) {
            prefix = '/' + prefix;
        }

        if (pathInfo.startsWith(prefix)) {
            return true;
        }

        return false;
    

Here pathInfo is “/desktop/UIDL/” and it checks if it starts with “/UIDL/”, which actually is not the case and UIDL handler is not triggered.

I’m using Vaadin 7.3.4. Could you please propose me some solution for this problem ?

Best Regards,
paco

You mapped your Login Servlet to the /* url pattern which means that every request, whether it originates from the Login UI or any other UI of the same war/folder/project/… will be handled by the Login Servlet.
Mapping the Login Servlet to another URL (maybe paired with some additional mapping of VAADIN/* etc.) might work in your case. More information should be here
https://vaadin.com/forum#!/thread/136600
as i personally didn’t use multiple servlets in one Vaadin application.

Yes, this was the case. My mistake.

Thanks

Actually, there is a problem. I have following servlet mappings:

  <servlet-mapping>
    <servlet-name>Login</servlet-name>
    <url-pattern>/</url-pattern>
  </servlet-mapping>

  <servlet-mapping>
    <servlet-name>Desktop</servlet-name>
    <url-pattern>/desktop/*</url-pattern>
  </servlet-mapping>
  <servlet-mapping>
    <servlet-name>Desktop</servlet-name>
    <url-pattern>/VAADIN/*</url-pattern>
  </servlet-mapping>

Both Login and Desktop are Vaadin servlets. In this case Login is my default servlet, mapped to /.
As stated in the servlet specification:

“A string containing only the ’/’ character indicates the “default” servlet of the application. In this case the servlet path
is the request URI minus the context path and the path info is null”


path info is null and ServletPortletHelper.isUIDLRequest(request) returns false, when it should return true
.

I don’t have more time for this issue now and implemented very ugly workaround in the Login servlet:

  protected void service(final HttpServletRequest request,
      HttpServletResponse response) throws ServletException, IOException {
    // PATCH: Vaadin does not handle default servlet mapping when getPathInfo  
    // is null. In those cases return servlet path instead of path info.
    HttpServletRequest _request = (HttpServletRequest) Proxy.newProxyInstance(
        HttpServletRequest.class.getClassLoader(), new Class[] {
            HttpServletRequest.class }, new InvocationHandler() {
          public Object invoke(Object proxy, Method method, Object[] args)
              throws Throwable {
            if (method.getName().equals("getPathInfo")) {
              return (null != request.getPathInfo()) ?
                  request.getPathInfo() : request.getServletPath() + "/";
            }
            return method.invoke(request, args);
          }
    });
    super.service(_request, response);
 

Could you please advice what is the best way to setup a working multi-servlet Vaadin application.

Best Regards,
Paco