This project has retired. For details please refer to its Attic page.
AutoLoginCookies xref
View Javadoc

1   package org.apache.archiva.redback.integration.util;
2   
3   /*
4    * Licensed to the Apache Software Foundation (ASF) under one
5    * or more contributor license agreements.  See the NOTICE file
6    * distributed with this work for additional information
7    * regarding copyright ownership.  The ASF licenses this file
8    * to you under the Apache License, Version 2.0 (the
9    * "License"); you may not use this file except in compliance
10   * with the License.  You may obtain a copy of the License at
11   *
12   * http://www.apache.org/licenses/LICENSE-2.0
13   *
14   * Unless required by applicable law or agreed to in writing,
15   * software distributed under the License is distributed on an
16   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
17   * KIND, either express or implied.  See the License for the
18   * specific language governing permissions and limitations
19   * under the License.
20   */
21  
22  import javax.annotation.Resource;
23  import javax.servlet.http.Cookie;
24  import javax.servlet.http.HttpServletRequest;
25  import javax.servlet.http.HttpServletResponse;
26  
27  import org.apache.archiva.redback.keys.AuthenticationKey;
28  import org.apache.archiva.redback.keys.KeyManager;
29  import org.apache.archiva.redback.keys.KeyManagerException;
30  import org.apache.archiva.redback.keys.KeyNotFoundException;
31  import org.apache.archiva.redback.policy.CookieSettings;
32  import org.apache.archiva.redback.system.SecuritySystem;
33  import org.apache.commons.lang.StringUtils;
34  import org.slf4j.Logger;
35  import org.slf4j.LoggerFactory;
36  import org.springframework.stereotype.Service;
37  
38  /**
39   * AutoLoginCookies
40   *
41   * @author <a href="mailto:joakim@erdfelt.com">Joakim Erdfelt</a>
42   *
43   */
44  @Service("autoLoginCookies")
45  public class AutoLoginCookies
46  {
47      
48      private Logger log = LoggerFactory.getLogger( getClass() );
49      
50      @Resource
51      private SecuritySystem securitySystem;
52  
53      /**
54       * Cookie key for the Remember Me functionality.
55       */
56      private static final String REMEMBER_ME_KEY = "rbkRememberMe";
57  
58      /**
59       * Cookie key for the signon cookie.
60       */
61      private static final String SIGNON_KEY = "rbkSignon";
62  
63      public AuthenticationKey getRememberMeKey(HttpServletResponse httpServletResponse, HttpServletRequest httpServletRequest )
64      {
65          if ( !isRememberMeEnabled() )
66          {
67              return null;
68          }
69  
70          Cookie rememberMeCookie = getCookie( httpServletRequest, REMEMBER_ME_KEY );
71  
72          if ( rememberMeCookie == null )
73          {
74              log.debug( "Remember Me Cookie Not Found: {}", REMEMBER_ME_KEY );
75              return null;
76          }
77  
78          // Found user with a remember me key.
79          String providedKey = rememberMeCookie.getValue();
80  
81          log.debug( "Found remember me cookie : {}", providedKey );
82  
83          CookieSettings settings = securitySystem.getPolicy().getRememberMeCookieSettings();
84          return findAuthKey( REMEMBER_ME_KEY, providedKey, settings.getDomain(), settings.getPath(), httpServletResponse, httpServletRequest );
85      }
86  
87      public void setRememberMeCookie( String principal, HttpServletResponse httpServletResponse, HttpServletRequest httpServletRequest )
88      {
89          if ( !isRememberMeEnabled() )
90          {
91              return;
92          }
93  
94          try
95          {
96              CookieSettings settings = securitySystem.getPolicy().getRememberMeCookieSettings();
97              int timeout = settings.getCookieTimeout();
98              KeyManager keyManager = securitySystem.getKeyManager();
99              AuthenticationKey authkey = keyManager.createKey( principal, "Remember Me Key", timeout );
100 
101             Cookie cookie = createCookie( REMEMBER_ME_KEY, authkey.getKey(), settings.getDomain(), settings.getPath(), httpServletRequest );
102             if ( timeout > 0 )
103             {
104                 cookie.setMaxAge( timeout );
105             }
106             httpServletResponse.addCookie( cookie );
107 
108         }
109         catch ( KeyManagerException e )
110         {
111             log.warn( "Unable to set remember me cookie." );
112         }
113     }
114 
115     public void removeRememberMeCookie( HttpServletResponse httpServletResponse, HttpServletRequest httpServletRequest )
116     {
117         CookieSettings settings = securitySystem.getPolicy().getRememberMeCookieSettings();
118         removeCookie( httpServletResponse, httpServletRequest, REMEMBER_ME_KEY, settings.getDomain(), settings.getPath() );
119     }
120 
121     public AuthenticationKey getSignonKey( HttpServletResponse httpServletResponse, HttpServletRequest httpServletRequest )
122     {
123         Cookie ssoCookie = getCookie( httpServletRequest, SIGNON_KEY );
124 
125         if ( ssoCookie == null )
126         {
127             log.debug( "Single Sign On Cookie Not Found: {}", SIGNON_KEY );
128             return null;
129         }
130 
131         // Found user with a single sign on key.
132 
133         String providedKey = ssoCookie.getValue();
134 
135         log.debug( "Found sso cookie : {}", providedKey );
136 
137         CookieSettings settings = securitySystem.getPolicy().getSignonCookieSettings();
138         return findAuthKey( SIGNON_KEY, providedKey, settings.getDomain(), settings.getPath(), httpServletResponse, httpServletRequest );
139     }
140 
141     public void setSignonCookie( String principal, HttpServletResponse httpServletResponse, HttpServletRequest httpServletRequest )
142     {
143         try
144         {
145             CookieSettings settings = securitySystem.getPolicy().getSignonCookieSettings();
146             int timeout = settings.getCookieTimeout();
147             KeyManager keyManager = securitySystem.getKeyManager();
148             AuthenticationKey authkey = keyManager.createKey( principal, "Signon Session Key", timeout );
149 
150             /* The path must remain as "/" in order for SSO to work on installations where the only
151              * all of the servers are installed into the same web container but under different 
152              * web contexts.
153              */
154             Cookie cookie = createCookie( SIGNON_KEY, authkey.getKey(), settings.getDomain(), settings.getPath(), httpServletRequest );
155             if ( timeout > 0 )
156             {
157                 cookie.setMaxAge( timeout );
158             }
159             httpServletResponse.addCookie( cookie );
160 
161         }
162         catch ( KeyManagerException e )
163         {
164             log.warn( "Unable to set single sign on cookie." );
165 
166         }
167     }
168 
169     public void removeSignonCookie( HttpServletResponse httpServletResponse, HttpServletRequest httpServletRequest )
170     {
171         CookieSettings settings = securitySystem.getPolicy().getSignonCookieSettings();
172         removeCookie( httpServletResponse, httpServletRequest, SIGNON_KEY, settings.getDomain(), settings.getPath() );
173     }
174 
175     private static String getWebappContext( HttpServletRequest httpRequest )
176     {
177         // Calculate the webapp context.
178         String webappContext = httpRequest.getContextPath();
179 
180         if ( StringUtils.isEmpty( webappContext ) )
181         {
182             // Still empty?  means you are a root context.
183             webappContext = "/";
184         }
185 
186         return webappContext;
187     }
188 
189     public boolean isRememberMeEnabled()
190     {
191         return securitySystem.getPolicy().getRememberMeCookieSettings().isEnabled();
192     }
193 
194     private AuthenticationKey findAuthKey( String cookieName, String providedKey, String domain, String path,
195                                            HttpServletResponse httpServletResponse, HttpServletRequest httpServletRequest )
196     {
197         try
198         {
199             AuthenticationKey authkey = securitySystem.getKeyManager().findKey( providedKey );
200 
201             log.debug( "Found AuthKey: {}", authkey );
202 
203             return authkey;
204         }
205         catch ( KeyNotFoundException e )
206         {
207             log.info( "Invalid AuthenticationKey {} submitted. Invalidating cookie.", providedKey );
208 
209             // Invalid Cookie.  Remove it.
210             removeCookie( httpServletResponse, httpServletRequest, cookieName, domain, path );
211         }
212         catch ( KeyManagerException e )
213         {
214             log.error( "KeyManagerException: " + e.getMessage(), e );
215         }
216 
217         return null;
218     }
219 
220     private static Cookie getCookie( HttpServletRequest request, String name )
221     {
222         Cookie[] cookies = request.getCookies();
223 
224         Cookie cookie = null;
225         if ( cookies != null && !StringUtils.isEmpty( name ) )
226         {
227             for ( int i = 0; i < cookies.length && cookie == null; i++ )
228             {
229                 if ( StringUtils.equals( name, cookies[i].getName() ) )
230                 {
231                     cookie = cookies[i];
232                 }
233             }
234         }
235 
236         return cookie;
237     }
238 
239     private static void removeCookie( HttpServletResponse response, HttpServletRequest httpRequest, String cookieName, String domain, String path )
240     {
241         Cookie cookie = createCookie( cookieName, "", domain, path, httpRequest );
242         cookie.setMaxAge( 0 );
243         response.addCookie( cookie );
244     }
245 
246     private static Cookie createCookie( String cookieName, String value, String domain, String path, HttpServletRequest httpRequest )
247     {
248         Cookie cookie = new Cookie( cookieName, value );
249         if ( domain != null )
250         {
251             cookie.setDomain( domain );
252         }
253         if ( path != null )
254         {
255             cookie.setPath( path );
256         }
257         else
258         {
259             // default to the context path, otherwise you get /security and such in some places
260             cookie.setPath( getWebappContext( httpRequest ) );
261         }
262         return cookie;
263     }
264 }