Results 1 to 8 of 8

Thread: OAuth2. Authorization Code grant. Error when hitting AuthorizationEndpoint

  1. #1
    Join Date
    Apr 2010
    Location
    Kharkov, Ukraine
    Posts
    52

    Default OAuth2. Authorization Code grant. Error when hitting AuthorizationEndpoint

    I'm building OAuth2 authorization server using 1.0.1.RELEASE.
    My authorization server is configured like this:
    Code:
    	<oauth:authorization-server
    			client-details-service-ref="clientDetailsService"
    			token-services-ref="tokenServices">
    		<oauth:authorization-code/>
    	</oauth:authorization-server>
    When hitting '/oauth/authorize', I get following error:
    Code:
    2013-02-28 13:24:41.209:WARN::/oauth/authorize
    org.springframework.expression.spel.SpelEvaluationException: EL1008E:(pos 0): Field or property 'authorizationRequest' cannot be found on object of type 'java.util.HashMap'
            at org.springframework.expression.spel.ast.PropertyOrFieldReference.readProperty(PropertyOrFieldReference.java:208)
            at org.springframework.expression.spel.ast.PropertyOrFieldReference.getValueInternal(PropertyOrFieldReference.java:72)
            at org.springframework.expression.spel.ast.CompoundExpression.getValueInternal(CompoundExpression.java:52)
            at org.springframework.expression.spel.ast.SpelNodeImpl.getValue(SpelNodeImpl.java:93)
            at org.springframework.expression.spel.standard.SpelExpression.getValue(SpelExpression.java:88)
            at org.springframework.security.oauth2.provider.endpoint.WhitelabelApprovalEndpoint$SpelView$1.resolvePlaceholder(WhitelabelApprovalEndpoint.java:64)
            at org.springframework.util.PropertyPlaceholderHelper.parseStringValue(PropertyPlaceholderHelper.java:146)
            at org.springframework.util.PropertyPlaceholderHelper.replacePlaceholders(PropertyPlaceholderHelper.java:125)
            at org.springframework.security.oauth2.provider.endpoint.WhitelabelApprovalEndpoint$SpelView.render(WhitelabelApprovalEndpoint.java:79)
            at org.springframework.web.servlet.DispatcherServlet.render(DispatcherServlet.java:1157)
            at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:927)
            at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:827)
            at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:882)
            at org.springframework.web.servlet.FrameworkServlet.doGet(FrameworkServlet.java:778)
            at javax.servlet.http.HttpServlet.service(HttpServlet.java:707)
            at javax.servlet.http.HttpServlet.service(HttpServlet.java:820)
    I tracked the source of the issue to AuthorizationEndpoint.authorize method:
    Code:
    			model.put("authorizationRequest", outgoingRequest);
    After populating the model with 'authorizationRequest' parameter, the action redirects to
    Code:
    forward:/oauth/confirm_access
    The execution is passed to WhitelabelApprovalEndpoint.getAccessConfirmation method:
    Code:
    	@RequestMapping("/oauth/confirm_access")
    	public ModelAndView getAccessConfirmation(Map<String, Object> model) throws Exception {
    		return new ModelAndView(new SpelView(APPROVAL), model);
    	}
    From what I can see, the model here is expected to be containing 'authorizationRequest' parameter that was populated by AuthorizationEndpoint earlier. However, the model is empty, which eventually causes the exception above. When stopping on a breakpoint in this method, I can query 'authorizationRequest' parameter like this:
    Code:
    RequestContextHolder.currentRequestAttributes().getAttribute("authorizationRequest",0)
    From my understanding of Spring MVC, after forwarding from request A to request B a model populated in request A will not be passed to request B explicitly, but its attributes will be available via HttpServletRequest attributes. If so, getAccessConfirmation method may have a bug. Or (more likely) I'm just doing something wrong. If so, please suggest.
    Regards,
    Denis

  2. #2
    Join Date
    Jun 2005
    Posts
    4,230

    Default

    AuthorizationEndpoint has @SessionAttributes("authorizationRequest"), so that attribute should be in the session. Do you have a session?

  3. #3
    Join Date
    Apr 2010
    Location
    Kharkov, Ukraine
    Posts
    52

    Default

    Quote Originally Posted by Dave Syer View Post
    AuthorizationEndpoint has @SessionAttributes("authorizationRequest"), so that attribute should be in the session. Do you have a session?
    Thanks for the answer. I don't have sessions disabled in <http session-create attribute in security XML configuration, so I suppose I have a session enabled. How can I check to tell for sure?
    Regards,
    Denis

  4. #4
    Join Date
    Jun 2005
    Posts
    4,230

    Default

    You could trace the HTTP requests headers from your browser or other client. Make sure the cookie you get from the authentication step is the same as the one passed to the /confirm_access endpoint.

  5. #5
    Join Date
    Apr 2010
    Location
    Kharkov, Ukraine
    Posts
    52

    Default

    Quote Originally Posted by Dave Syer View Post
    You could trace the HTTP requests headers from your browser or other client. Make sure the cookie you get from the authentication step is the same as the one passed to the /confirm_access endpoint.
    In both AuthorizationEndpoint and WhitelabelApprovalEndpoint the value of JSESSIONID cookie is the same (I have executed
    Code:
    ((ServletRequestAttributes) RequestContextHolder.currentRequestAttributes()).getRequest().getCookies()
    at runtime).
    This is the same cookies that was sent with the original '/oauth/authorize' request.

    In fact, I think that @SessionAttributes annotation is not valid when used on different controllers. From the documentation, "Annotation that indicates the session attributes that a specific handler uses", where I guess handler=controller. I have created a simple test case which mimics the same behavior that AuthenticationEndpoint and WhitelabelApprovalEndpoint expose:
    Code:
    @SessionAttributes({"hello"})
    @Controller
    public class StartController {
    	@RequestMapping("/start")
    	public ModelAndView end(){
    		HashMap<String, Object> model = new HashMap<String, Object>();
    		model.put("hello", "world");
    		return new ModelAndView("forward:/end", model);
    	}
    }
    @SessionAttributes({"hello"})
    @Controller
    public class EndController {
    	@RequestMapping("/end")
    	public ModelAndView end(Model model){
    		System.out.println("Got model: "+ model);                    //this is empty
    		return null;
    	}
    }
    In EndController, model is empty.
    If I declare both 'start' and 'end' actions in one controller, model is populated with 'hello' attribute, as expected:
    Code:
    @SessionAttributes({"hello"})
    @Controller
    public class StartController {
    	@RequestMapping("/start")
    	public ModelAndView end(){
    		HashMap<String, Object> model = new HashMap<String, Object>();
    		model.put("hello", "world");
    		return new ModelAndView("forward:/end", model);
    	}
    
    	@RequestMapping("/end")
    	public ModelAndView end(Model model){
    		System.out.println("Got model: "+ model);         //this contains 'hello=world'
    		return null;
    	}
    }
    Does AuthenticationEndpoint -> WhitelabelApprovalEndpoint chain work for you?
    Last edited by denis_k; Mar 1st, 2013 at 07:06 AM. Reason: Examples were completely screwed up
    Regards,
    Denis

  6. #6
    Join Date
    Jun 2005
    Posts
    4,230

    Default

    Neither of your samples should compile because you have a local variable with the same name as a method parameter. I'm not surprised the first one didn't work, even if you rename one of them. The second one should also not work as you described (for the same reason) even if you changed the name of the local variable (you are adding "hello" to a local map which goes immediately out of scope not the Spring MVC model).

    Quote Originally Posted by denis_k View Post
    Does AuthenticationEndpoint -> WhitelabelApprovalEndpoint chain work for you?
    I haven't tried it explicitly in a while, but the sparklr sample has exactly the same code (with a custom handler for /confirm_access) and it works.

  7. #7
    Join Date
    Apr 2010
    Location
    Kharkov, Ukraine
    Posts
    52

    Default

    Ah, I was entering examples by hand and screwed them up completely. I'll edit. I'll also take a look at sparklr sample, thanks for suggesting it.
    Regards,
    Denis

  8. #8
    Join Date
    Apr 2010
    Location
    Kharkov, Ukraine
    Posts
    52

    Default

    OK, I figured it out. It was a bug in Spring 3.1.0.RELEASE. Starting from 3.1.2.RELEASE, @SessionAttributes are persisted among controller as expected. I don't know how this slipped from me initially when I was testing with fresher Spring versions.
    Regards,
    Denis

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •