KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > winstone > auth > BasicAuthenticationHandler


1 /*
2  * Copyright 2003-2006 Rick Knowles <winstone-devel at lists sourceforge net>
3  * Distributed under the terms of either:
4  * - the common development and distribution license (CDDL), v1.0; or
5  * - the GNU Lesser General Public License, v2.1 or later
6  */

7 package winstone.auth;
8
9 import java.io.IOException JavaDoc;
10 import java.util.List JavaDoc;
11 import java.util.Set JavaDoc;
12
13 import javax.servlet.http.HttpServletRequest JavaDoc;
14 import javax.servlet.http.HttpServletRequestWrapper JavaDoc;
15 import javax.servlet.http.HttpServletResponse JavaDoc;
16
17 import org.w3c.dom.Node JavaDoc;
18
19 import winstone.AuthenticationPrincipal;
20 import winstone.AuthenticationRealm;
21 import winstone.Logger;
22 import winstone.WinstoneRequest;
23
24 /**
25  * Handles HTTP basic authentication.
26  *
27  * @author mailto: <a HREF="rick_knowles@hotmail.com">Rick Knowles</a>
28  * @version $Id: BasicAuthenticationHandler.java,v 1.4 2006/02/28 07:32:47 rickknowles Exp $
29  */

30 public class BasicAuthenticationHandler extends BaseAuthenticationHandler {
31     public BasicAuthenticationHandler(Node JavaDoc loginConfigNode,
32             List JavaDoc constraintNodes, Set JavaDoc rolesAllowed,
33             AuthenticationRealm realm) {
34         super(loginConfigNode, constraintNodes, rolesAllowed, realm);
35         Logger.log(Logger.DEBUG, AUTH_RESOURCES,
36                 "BasicAuthenticationHandler.Initialised", realmName);
37     }
38
39     /**
40      * Call this once we know that we need to authenticate
41      */

42     protected void requestAuthentication(HttpServletRequest JavaDoc request,
43             HttpServletResponse JavaDoc response, String JavaDoc pathRequested)
44             throws IOException JavaDoc {
45         // Return unauthorized, and set the realm name
46
response.setHeader("WWW-Authenticate", "Basic Realm=\""
47                 + this.realmName + "\"");
48         response.sendError(HttpServletResponse.SC_UNAUTHORIZED, AUTH_RESOURCES
49                 .getString("BasicAuthenticationHandler.UnauthorizedMessage"));
50     }
51
52     /**
53      * Handling the (possible) response
54      */

55     protected boolean validatePossibleAuthenticationResponse(
56             HttpServletRequest JavaDoc request, HttpServletResponse JavaDoc response,
57             String JavaDoc pathRequested) throws IOException JavaDoc {
58         String JavaDoc authorization = request.getHeader("Authorization");
59         if ((authorization != null)
60                 && authorization.toLowerCase().startsWith("basic")) {
61             String JavaDoc decoded = decodeBase64String(authorization.substring(5).trim());
62             int delimPos = decoded.indexOf(':');
63             if (delimPos != -1) {
64                 AuthenticationPrincipal principal = this.realm
65                         .authenticateByUsernamePassword(decoded.substring(0,
66                                 delimPos).trim(), decoded.substring(
67                                 delimPos + 1).trim());
68                 if (principal != null) {
69                     principal.setAuthType(HttpServletRequest.BASIC_AUTH);
70                     if (request instanceof WinstoneRequest)
71                         ((WinstoneRequest) request).setRemoteUser(principal);
72                     else if (request instanceof HttpServletRequestWrapper JavaDoc) {
73                         HttpServletRequestWrapper JavaDoc wrapper = (HttpServletRequestWrapper JavaDoc) request;
74                         if (wrapper.getRequest() instanceof WinstoneRequest)
75                             ((WinstoneRequest) wrapper.getRequest())
76                                     .setRemoteUser(principal);
77                         else
78                             Logger.log(Logger.WARNING, AUTH_RESOURCES,
79                                     "BasicAuthenticationHandler.CantSetUser",
80                                     wrapper.getRequest().getClass().getName());
81                     } else
82                         Logger.log(Logger.WARNING, AUTH_RESOURCES,
83                                 "BasicAuthenticationHandler.CantSetUser",
84                                 request.getClass().getName());
85                 }
86             }
87         }
88         return true;
89     }
90
91     /**
92      * Useful helper method ... base 64 decoding for strings
93      */

94     public String JavaDoc decodeBase64String(String JavaDoc input) {
95         try {
96             char inChars[] = input.toCharArray();
97             byte outBytes[] = new byte[(int) Math
98                     .floor((inChars.length - 1) * 0.75)];
99             int length = input.indexOf('=');
100             if (length == -1) {
101                 length = input.length();
102             }
103             decodeBase64(inChars, 0, input.indexOf('='), outBytes, 0);
104             return new String JavaDoc(outBytes, "8859_1");
105         } catch (Throwable JavaDoc err) {
106             return null;
107         }
108     }
109
110     /**
111      * Decodes a byte array from base64
112      */

113     public static void decodeBase64(char input[], int inOffset, int inLength,
114             byte output[], int outOffset) {
115         if (inLength == 0)
116             return;
117
118         // Decode four bytes
119
int thisPassInBytes = Math.min(inLength, 4);
120         int outBuffer = 0;
121         int thisPassOutBytes = 0;
122         if (thisPassInBytes == 2) {
123             outBuffer = ((B64_DECODE_ARRAY[input[inOffset]] & 0xFF) << 18)
124                     | ((B64_DECODE_ARRAY[input[inOffset + 1]] & 0xFF) << 12);
125             output[outOffset] = (byte) ((outBuffer >> 16) & 0xFF);
126             thisPassOutBytes = 1;
127         } else if (thisPassInBytes == 3) {
128             outBuffer = ((B64_DECODE_ARRAY[input[inOffset]] & 0xFF) << 18)
129                     | ((B64_DECODE_ARRAY[input[inOffset + 1]] & 0xFF) << 12)
130                     | ((B64_DECODE_ARRAY[input[inOffset + 2]] & 0xFF) << 6);
131             output[outOffset] = (byte) ((outBuffer >> 16) & 0xFF);
132             output[outOffset + 1] = (byte) ((outBuffer >> 8) & 0xFF);
133             thisPassOutBytes = 2;
134         } else {
135             outBuffer = ((B64_DECODE_ARRAY[input[inOffset]] & 0xFF) << 18)
136                     | ((B64_DECODE_ARRAY[input[inOffset + 1]] & 0xFF) << 12)
137                     | ((B64_DECODE_ARRAY[input[inOffset + 2]] & 0xFF) << 6)
138                     | ((B64_DECODE_ARRAY[input[inOffset + 3]] & 0xFF));
139             output[outOffset] = (byte) ((outBuffer >> 16) & 0xFF);
140             output[outOffset + 1] = (byte) ((outBuffer >> 8) & 0xFF);
141             output[outOffset + 2] = (byte) (outBuffer & 0xFF);
142             thisPassOutBytes = 3;
143         }
144         // Recurse
145
decodeBase64(input, inOffset + thisPassInBytes, inLength
146                 - thisPassInBytes, output, outOffset + thisPassOutBytes);
147     }
148
149     private static byte B64_DECODE_ARRAY[] = new byte[] { -1, -1, -1, -1, -1,
150             -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
151             -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
152             -1, -1, -1, -1, 62, // Plus sign
153
-1, -1, -1, 63, // Slash
154
52, 53, 54, 55, 56, 57, 58, 59, 60, 61, // Numbers
155
-1, -1, -1, -1, -1, -1, -1, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11,
156             12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, // Large letters
157
-1, -1, -1, -1, -1, -1, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36,
158             37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, // Small letters
159
-1, -1, -1, -1 };
160 }
161
Popular Tags