1 2 Previous Next 29 Replies Latest reply on Dec 11, 2009 4:50 PM by marcgemis Go to original post
      • 15. Re: Advance authentication
        kapitanpetko

        Itay Sahar wrote on Nov 30, 2009 10:11:


        Override remember me as well ? if yes which encoding should we use instead.
        In addition, we should add a bug to jira about this as well.


        You might have to override if it is indeed a bug. Attach a debugger to see what exactly happens first. Then you can decide how/if to fix it.

        • 16. Re: Advance authentication
          itays100

          After debug i came with some results:


          The following code works with no exception!


          from RememberMe component:


          
          protected String encodeToken(String username, String value)
             {
                StringBuilder sb = new StringBuilder();
                sb.append(username);
                sb.append(":");
                sb.append(value);
                return Base64.encodeBytes(sb.toString().getBytes());      
             }
          
          



          The addCookie throw the exception:


          
          protected void setCookieValueIfEnabled(String value)
             {
                FacesContext ctx = FacesContext.getCurrentInstance();
                
                if ( isCookieEnabled() && ctx != null)
                {
                   HttpServletResponse response = (HttpServletResponse) ctx.getExternalContext().getResponse();
                   Cookie cookie = new Cookie( getCookieName(), value );
                   cookie.setMaxAge( getCookieMaxAge() );
                   cookie.setPath(cookiePath);
                   response.addCookie(cookie);
                }
             }
          
          



          It seems to me that  encodeToken from rememberMe should be override to support this advance feature. Any idea how we can
          encode this to support special character.

          • 17. Re: Advance authentication
            kapitanpetko

            What is the input/output of encodeToken()? What is your locale? Depending on this getBytes() might return different things, although that might not be relevant.

            • 18. Re: Advance authentication
              itays100

              Input is:


              
              username= aaa.bbb@ccc.com
              
              value=    6de5ca4f:1254c461110:-7feb:9135486247122677484
              
              



              Output is:


              
              aXRheS5zYWhhckBnbWFpbC5jb206NmRlNWNhNGY6MTI1NGM0NjExMTA6LTdmZWI6OTEzNTQ4NjI0 
              
              FacesContext.getCurrentInstance().getExternalContext().getRequestLocale() return en_US
              
              






              Thanks!

              • 19. Re: Advance authentication
                kapitanpetko

                Itay Sahar wrote on Dec 01, 2009 23:32:


                Output is:

                aXRheS5zYWhhckBnbWFpbC5jb206NmRlNWNhNGY6MTI1NGM0NjExMTA6LTdmZWI6OTEzNTQ4NjI0 
                





                That is valid Base64 (it has your gmail in it :)), so might be a problem with your application server, rather than Seam. What server/version are you using? Try with a newer version if you have that option.

                • 20. Re: Advance authentication
                  itays100

                  tomcat 6.0.18

                  • 21. Re: Advance authentication
                    kapitanpetko

                    Itay Sahar wrote on Dec 02, 2009 09:28:


                    tomcat 6.0.18


                    Try the newest version.

                    • 22. Re: Advance authentication
                      itays100

                      this didn't help. please see below the stack trace. i think i missed something in a previous post.


                      
                      05/12/2009 02:23:00 _
                      
                      + com.sun.faces.lifecycle.Phase doPhase
                      SEVERE: JSF1054: (Phase ID: INVOKE_APPLICATION 5, View ID: /login.xhtml) Exception thrown during phase execution_: 
                      
                      javax.faces.event.PhaseEvent[source=com.sun.faces.lifecycle.LifecycleImpl@7d5
                      05/12/2009 02:23:00 org.ajax4jsf.webapp.BaseXMLFilter doXmlFilter
                      SEVERE: Exception in the filter chain
                      javax.servlet.ServletException: #{identity.login}: java.lang.IllegalArgumentException: Control character in cookie value, consider BASE64 encoding your value
                              at javax.faces.webapp.FacesServlet.service(FacesServlet.java:277)
                              at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290)
                              at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
                              at org.jboss.seam.servlet.SeamFilter$FilterChainImpl.doFilter(SeamFilter.java:83)
                              at org.jboss.seam.web.IdentityFilter.doFilter(IdentityFilter.java:40)
                              at org.jboss.seam.servlet.SeamFilter$FilterChainImpl.doFilter(SeamFilter.java:69)
                              at org.jboss.seam.web.MultipartFilter.doFilter(MultipartFilter.java:90)
                              at org.jboss.seam.servlet.SeamFilter$FilterChainImpl.doFilter(SeamFilter.java:69)
                              at org.jboss.seam.web.ExceptionFilter.doFilter(ExceptionFilter.java:64)
                              at org.jboss.seam.servlet.SeamFilter$FilterChainImpl.doFilter(SeamFilter.java:69)
                              at org.jboss.seam.web.RedirectFilter.doFilter(RedirectFilter.java:45)
                              at org.jboss.seam.servlet.SeamFilter$FilterChainImpl.doFilter(SeamFilter.java:69)
                              at org.ajax4jsf.webapp.BaseXMLFilter.doXmlFilter(BaseXMLFilter.java:178)
                              at org.ajax4jsf.webapp.BaseFilter.handleRequest(BaseFilter.java:290)
                              at org.ajax4jsf.webapp.BaseFilter.processUploadsAndHandleRequest(BaseFilter.java:390)
                              at org.ajax4jsf.webapp.BaseFilter.doFilter(BaseFilter.java:517)
                              at org.jboss.seam.web.Ajax4jsfFilter.doFilter(Ajax4jsfFilter.java:56)
                              at org.jboss.seam.servlet.SeamFilter$FilterChainImpl.doFilter(SeamFilter.java:69)
                              at org.jboss.seam.servlet.SeamFilter.doFilter(SeamFilter.java:158)
                              at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235)
                              at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
                              at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:233)
                              at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:191)
                              at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:128)
                              at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102)
                              at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109)
                              at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:293)
                              at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:849)
                              at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:583)
                              at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:454)
                              at java.lang.Thread.run(Thread.java:595)
                      Caused by: javax.faces.FacesException: #{identity.login}: java.lang.IllegalArgumentException: Control character in cookie value, consider BASE64 encoding your value
                              at com.sun.faces.application.ActionListenerImpl.processAction(ActionListenerImpl.java:118)
                              at javax.faces.component.UICommand.broadcast(UICommand.java:387)
                              at org.ajax4jsf.component.AjaxViewRoot.processEvents(AjaxViewRoot.java:321)
                              at org.ajax4jsf.component.AjaxViewRoot.broadcastEvents(AjaxViewRoot.java:296)
                              at org.ajax4jsf.component.AjaxViewRoot.processPhase(AjaxViewRoot.java:253)
                              at org.ajax4jsf.component.AjaxViewRoot.processApplication(AjaxViewRoot.java:466)
                              at com.sun.faces.lifecycle.InvokeApplicationPhase.execute(InvokeApplicationPhase.java:82)
                              at com.sun.faces.lifecycle.Phase.doPhase(Phase.java:100)
                              at com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:118)
                              at javax.faces.webapp.FacesServlet.service(FacesServlet.java:265)
                              ... 30 more
                      Caused by: javax.faces.el.EvaluationException: java.lang.IllegalArgumentException: Control character in cookie value, consider BASE64 encoding your value
                              at javax.faces.component.MethodBindingMethodExpressionAdapter.invoke(MethodBindingMethodExpressionAdapter.java:102)
                              at com.sun.faces.application.ActionListenerImpl.processAction(ActionListenerImpl.java:102)
                              ... 39 more
                      Caused by: java.lang.IllegalArgumentException: Control character in cookie value, consider BASE64 encoding your value
                              at org.apache.tomcat.util.http.ServerCookie.maybeQuote2(ServerCookie.java:396)
                              at org.apache.tomcat.util.http.ServerCookie.maybeQuote2(ServerCookie.java:389)
                              at org.apache.tomcat.util.http.ServerCookie.appendCookieValue(ServerCookie.java:293)
                              at org.apache.catalina.connector.Response.addCookieInternal(Response.java:1010)
                              at org.apache.catalina.connector.Response.addCookieInternal(Response.java:979)
                              at org.apache.catalina.connector.Response.addCookie(Response.java:967)
                              at org.apache.catalina.connector.ResponseFacade.addCookie(ResponseFacade.java:343)
                              at javax.servlet.http.HttpServletResponseWrapper.addCookie(HttpServletResponseWrapper.java:58)
                              at org.ajax4jsf.webapp.FilterServletResponseWrapper.addCookie(FilterServletResponseWrapper.java:627)
                              at javax.servlet.http.HttpServletResponseWrapper.addCookie(HttpServletResponseWrapper.java:58)
                              at org.jboss.seam.faces.Selector.setCookieValueIfEnabled(Selector.java:119)
                              at org.jboss.seam.security.RememberMe$UsernameSelector.setCookieValueIfEnabled(RememberMe.java:70)
                              at org.jboss.seam.security.RememberMe.postAuthenticate(RememberMe.java:388)
                              at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
                              at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
                              at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
                              at java.lang.reflect.Method.invoke(Method.java:585)
                              at org.jboss.seam.util.Reflections.invoke(Reflections.java:22)
                              at org.jboss.seam.util.Reflections.invokeAndWrap(Reflections.java:144)
                              at org.jboss.seam.Component.callComponentMethod(Component.java:2253)
                              at org.jboss.seam.core.Events.raiseEvent(Events.java:85)
                              at org.jboss.seam.security.Identity.postAuthenticate(Identity.java:397)
                              at org.jboss.seam.security.Identity.authenticate(Identity.java:345)
                              at org.jboss.seam.security.Identity.authenticate(Identity.java:332)
                              at org.jboss.seam.security.Identity.login(Identity.java:259)
                              at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
                              at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
                              at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
                              at java.lang.reflect.Method.invoke(Method.java:585)
                              at org.jboss.el.util.ReflectionUtil.invokeMethod(ReflectionUtil.java:335)
                              at org.jboss.el.util.ReflectionUtil.invokeMethod(ReflectionUtil.java:348)
                              at org.jboss.el.parser.AstPropertySuffix.invoke(AstPropertySuffix.java:58)
                              at org.jboss.el.parser.AstValue.invoke(AstValue.java:96)
                              at org.jboss.el.MethodExpressionImpl.invoke(MethodExpressionImpl.java:276)
                              at com.sun.facelets.el.TagMethodExpression.invoke(TagMethodExpression.java:68)
                              at javax.faces.component.MethodBindingMethodExpressionAdapter.invoke(MethodBindingMethodExpressionAdapter.java:88)
                              ... 40 more
                      
                      



                      Thanks!

                      • 23. Re: Advance authentication
                        kapitanpetko

                        Your best bet is to report this with Tomcat. You could also get the source for org.apache.tomcat.util.http.ServerCookie.maybeQuote2 and find out what is wrong, so you can work around it, if possible. Good luck.


                        • 24. Re: Advance authentication
                          itays100

                          That exactly what i did. They came with some idea but i'm not sure what i need to change.
                          Please take a look and tell me if you can suggest solution for this.


                          
                          Mark Thomas wrote:
                          itay sahar wrote:
                          Caused by: java.lang.IllegalArgumentException: Control character in cookie
                          value, consider BASE64 encoding your value
                                 at
                          org.apache.tomcat.util.http.ServerCookie.maybeQuote2(ServerCookie.java:396)
                          
                          To cause this, there must be a character in the value with an ASCII code
                           of less than 0x20 or greater or equal to 0x7f and is not 0x09.
                          
                          You need to fix that first.
                          
                          Then you'll need to worry about Base64 using '=' in cookie values. The
                          value needs to be quoted for this to work. Tomcat will do this
                          automatically if necessary.
                          
                          
                          Mark above is talking about the output value of the Base64 encoder which you are using, and which you then feed to the response.addCookie(cookie) method.
                          
                          It is not clear (to me) where the used Base64.encodeBytes() method comes from.  But wherever it comes from, it should encode any input series of bytes according to
                          http://tools.ietf.org/html/rfc3548#section-3
                          which cannot produce "control characters".
                          Except that some Base64 encoders, in some cases, will "wrap" the output string at 76 bytes, by inserting a CR/LF pair, which are both "control characters".  (Note that the output string of Base64 is longer than the input string, since it encodes 3 consecutive input bytes into 4 output bytes.)
                          My guess is that this is what happens here, and that could trigger the exception above.
                          Maybe this Base64.encodeBytes() method has an optional argument which would tell it to not wrap the output value ?
                          
                          Note also that with the code you were showing, the control character(s) could presumably be also in "cookiePath".
                          
                          Why do you not log the cookie value, just before you call setCookieValueIfEnabled(String value) ?
                          
                          



                          Thanks!

                          • 25. Re: Advance authentication
                            kapitanpetko

                            Send them the values that produce an error to get this sorted out. As for the CR/LF, you are indeed close to 76 chasr, so try this in encodeToken (override RememberMe):


                            ...
                             return Base64.encodeBytes(sb.toString().getBytes(), Base64.DONT_BREAK_LINES);  
                            

                            • 26. Re: Advance authentication
                              itays100

                              No, you are fine :-)


                              I extended RememberMe and add your fix and it works like a charm)!
                              Two more questions:


                              1. Do you know about any problem i should encounter ?
                                
                              2. I know seam RememberMe has two modes:


                                 1. Remember only the username.
                                 2. Auto login.


                                 I currently use the second (As you may know) but do you know how   
                                 to use the first choise ?
                                 


                              Thanks!

                              • 27. Re: Advance authentication
                                kapitanpetko

                                Itay Sahar wrote on Dec 07, 2009 21:10:


                                I extended RememberMe and add your fix and it works like a charm)!


                                Nice to hear. So I was wrong and this is a bug in Seam (Base64 encoding inserts newlines after 76 chars, that breaks cookies). You should report it in JIRA. And you should contact the Tomcat guys, so that they can close the issue.



                                Two more questions:

                                1. Do you know about any problem i should encounter ?


                                No. Search the forum if you do :)



                                2. I know seam RememberMe has two modes:

                                   1. Remember only the username.
                                   2. Auto login.

                                   I currently use the second (As you may know) but do you know how   
                                   to use the first choise ?


                                I haven't actually used it, but AFAIK, there is a switch for that :) Check the docs. Also be aware, that 2. is not very secure, there is a big fat warning in the docs. Again, go over those.

                                • 28. Re: Advance authentication
                                  shane.bryzak

                                  I've fixed the Base64 encoding issue in SVN.

                                  • 29. Re: Advance authentication
                                    marcgemis

                                    A related problem:


                                    I tried to use an email as username and use the usernameOnly-mode. The cookie gets properly saved (verified in browser cookies window). Howver, the class org.apache.tomcat.util.http.Cookies regards the '@'-symbol as a separator and therefore reads only part of the cookie.


                                    I guess that I have to extend RememberMe to encode/decode the username as this functionality is not supported by the current implementation (2.2.0.GA)

                                    1 2 Previous Next