001    package com.nimbusds.openid.connect.sdk;
002    
003    
004    import java.net.URL;
005    import java.util.Map;
006    
007    import com.nimbusds.oauth2.sdk.ParseException;
008    import com.nimbusds.oauth2.sdk.http.HTTPResponse;
009    import com.nimbusds.oauth2.sdk.util.URLUtils;
010    
011    
012    /**
013     * Parser of OpenID Connect authorisation response messages.
014     *
015     * <p>Related specifications:
016     *
017     * <ul>
018     *     <li>OpenID Connect Messages 1.0, sections 2.1.2 and 2.1.3.
019     * </ul>
020     *
021     * @author Vladimir Dzhuvinov
022     */
023    public class OIDCAuthorizationResponseParser { 
024    
025    
026            /**
027             * Parses an OpenID Connect authorisation success or error response
028             * from the specified redirect URI and parameters.
029             *
030             * @param redirectURI The base redirect URI. Must not be {@code null}.
031             * @param params      The response parameters to parse. Must not be 
032             *                    {@code null}.
033             *
034             * @return The OpenID Connect authorisation success or error response.
035             *
036             * @throws ParseException If the parameters couldn't be parsed to an
037             *                        OpenID Connect authorisation success or error
038             *                        response.
039             */
040            public static OIDCAuthorizationResponse parse(final URL redirectURI, 
041                                                          final Map<String,String> params)
042                    throws ParseException {
043    
044    
045                    if (params.containsKey("error"))
046                            return OIDCAuthorizationErrorResponse.parse(redirectURI, params);
047                    else
048                            return OIDCAuthorizationSuccessResponse.parse(redirectURI, params);
049            }
050    
051    
052            /**
053             * Parses an OpenID Connect authorisation success or error response
054             * from the specified URI.
055             *
056             * <p>Example URI:
057             *
058             * <pre>
059             * https://client.example.com/cb?code=SplxlOBeZQQYbYS6WxSbIA&amp;state=xyz
060             * </pre>
061             *
062             * @param uri The URI to parse. Can be absolute or relative, with a
063             *            fragment or query string containing the authorisation
064             *            response parameters. Must not be {@code null}.
065             *
066             * @return The OpenID Connect authorisation success or error response.
067             *
068             * @throws ParseException If the redirect URI couldn't be parsed to an
069             *                        OpenID Connect authorisation success or error
070             *                        response.
071             */
072            public static OIDCAuthorizationResponse parse(final URL uri)
073                    throws ParseException {
074    
075                    String paramString = null;
076                    
077                    if (uri.getQuery() != null)
078                            paramString = uri.getQuery();
079                                    
080                    else if (uri.getRef() != null)
081                            paramString = uri.getRef();
082                    
083                    else
084                            throw new ParseException("Missing authorization response parameters");
085                    
086                    Map<String,String> params = URLUtils.parseParameters(paramString);
087    
088                    if (params == null)
089                            throw new ParseException("Missing or invalid authorization response parameters");
090    
091                    return parse(URLUtils.getBaseURL(uri), params);
092            }
093    
094    
095            /**
096             * Parses an OpenID Connect authorisation success or error response 
097             * from the specified HTTP response.
098             *
099             * <p>Example HTTP response:
100             *
101             * <pre>
102             * HTTP/1.1 302 Found
103             * Location: https://client.example.com/cb?code=SplxlOBeZQQYbYS6WxSbIA&amp;state=xyz
104             * </pre>
105             *
106             * @param httpResponse The HTTP response to parse. Must not be 
107             *                     {@code null}.
108             *
109             * @return The OpenID Connect authorisation success or error response.
110             *
111             * @throws ParseException If the HTTP response couldn't be parsed to an 
112             *                        OpenID Connect authorisation success or error
113             *                        response.
114             */
115            public static OIDCAuthorizationResponse parse(final HTTPResponse httpResponse)
116                    throws ParseException {
117    
118                    if (httpResponse.getStatusCode() != HTTPResponse.SC_FOUND)
119                            throw new ParseException("Unexpected HTTP status code, must be 302 (Found): " + 
120                                                     httpResponse.getStatusCode());
121                    
122                    URL location = httpResponse.getLocation();
123                    
124                    if (location == null)
125                            throw new ParseException("Missing redirect URL / HTTP Location header");
126                    
127                    return parse(location);
128            }
129    
130    
131            /**
132             * Prevents public instantiation.
133             */
134            private OIDCAuthorizationResponseParser() { }
135    }