Source Code Cross Referenced for SunNetAuthHandler.java in  » Web-Server » Brazil » sunlabs » brazil » handler » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » Web Server » Brazil » sunlabs.brazil.handler 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


001:        /*
002:         * SunNetAuthHandler.java
003:         *
004:         * Brazil project web application Framework,
005:         * export version: 1.1 
006:         * Copyright (c) 1998-2000 Sun Microsystems, Inc.
007:         *
008:         * Sun Public License Notice
009:         *
010:         * The contents of this file are subject to the Sun Public License Version 
011:         * 1.0 (the "License"). You may not use this file except in compliance with 
012:         * the License. A copy of the License is included as the file "license.terms",
013:         * and also available at http://www.sun.com/
014:         * 
015:         * The Original Code is from:
016:         *    Brazil project web application Framework release 1.1.
017:         * The Initial Developer of the Original Code is: suhler.
018:         * Portions created by suhler are Copyright (C) Sun Microsystems, Inc.
019:         * All Rights Reserved.
020:         * 
021:         * Contributor(s): cstevens, rinaldo, suhler.
022:         *
023:         * Version:  1.29
024:         * Created by suhler on 98/09/30
025:         * Last modified by suhler on 00/12/11 20:23:22
026:         */
027:
028:        package sunlabs.brazil.handler;
029:
030:        import java.io.File;
031:        import java.io.FileInputStream;
032:        import java.io.IOException;
033:        import java.util.Enumeration;
034:        import java.util.Hashtable;
035:        import java.util.Random;
036:        import java.util.StringTokenizer;
037:        import java.util.Vector;
038:        import sunlabs.brazil.server.FileHandler;
039:        import sunlabs.brazil.server.Handler;
040:        import sunlabs.brazil.server.Request;
041:        import sunlabs.brazil.server.Server;
042:
043:        /**
044:         * All-in-one Handler for doing supplier.net style authentication.
045:         * <p>
046:         * The purpose of this handler is to provide an authenticated "front end"
047:         * to one or more web sites, using (hopefully) arbitrary challenge-
048:         * response based authentication via a plug-in authentication interface.
049:         * It can bridge disparate DNS domains by selectively mapping servers
050:         * on one domain into another, based on the supplied credentials, by using
051:         * the {@link MultiProxyHandler}.
052:         * <p>
053:         * The authentication step is expected to yield a list of roles, each of
054:         * which represents permission to access a specific foreign site.
055:         * Once authentication is complete, and the roles are obtained,
056:         * the handler keeps a set of credentials (a lease)
057:         * on behalf of the user, which can be tuned at setup time for a variety
058:         * of expiration conditions. Once a lease expires, re-authentication is required.
059:         * <p>
060:         * This handler starts two sets of handlers of its own, an authentication handler -
061:         * responsible for doing the authentication, and one of more virtual
062:         * proxy handlers -  one for each  possible role.  In the current
063:         * implementation, the authentication handler is specified and a configuration
064:         * property, and the proxy handlers are all instances of
065:         * {@link MultiProxyHandler}, one per role.
066:         * <p>
067:         * Operation of the handler proceeds in the following steps:
068:         * <ol>
069:         * <li> When the server starts, the handler is initialized.
070:         *  <ul>
071:         *  <li>The template file is located and read.
072:         *  <li>One {@link MultiProxyHandler} is started for each possible role
073:         *  <li>The Authentication handler is started.  Its operation is defined below.
074:         *  </ul>
075:         * <li> Browser cookies are used as a reference to the user's credentials.  If
076:         *      the cookie returned by the browser refers to a valid credential, 
077:         *      the requested url is compared to the user's roles.  If the requested
078:         *      URL is permitted, by matching one of the users's roles, the URL
079:         *      is forwarded to the proper virtual web site for delivery.  Otherwise
080:         *      the URL is considered "not found".
081:         * <li> If the credentials are not valid, either because thay had expired, 
082:         *      were removed, or there is no browser cookie, the authentication
083:         *      sequence is started, for the purpose of obtaining valid credentials.
084:         *  <ul>
085:         *  <li> A browser cookie is chosen at random, and a "set-cookie" request
086:         *       is sent to the client (in lieu of the URL requested) along with
087:         *       the login template.  An additional random value is created, retained
088:         *       by the handler on behalf of this client, and made available as a
089:         *       parameter to the login template.
090:         *  <li> The next response from the client is expected to contain the
091:         *       information required to authenticate the client.  This is normally
092:         *       accomplished by having the user fill out the form that is contained
093:         *       on the login template, and clicking the submit button.
094:         *  <li> The client's response (e.g. query data), along with the random number
095:         *       generated in the previous step, are forwarded to the authentication
096:         *       handler.
097:         *  <li> The authentication handler is expected to place a user id and a list
098:         *       of roles in the resulting request object if authentication is successful
099:         *       or an error message otherwise.  If the authentication suceeds, the
100:         *       roles are entered into the lease, and the original URL processing
101:         *       is resumed.  If instead an error is returned, the authentication 
102:         *       sequence is repeated.  The error message is may be displayed
103:         *       to the user if it is included as a parameter on the login template.
104:         *  </ul>
105:         * </ol>
106:         * <p>
107:         * The login template is ordinary HTML, except contructs of the form:
108:         * <pre>
109:         *   &lt;insert property=xx default=yy&gt;
110:         * </pre>
111:         * may be used to substitute
112:         * {@link sunlabs.brazil.server.Request#props}
113:         * into the template.  The properties <code>challenge</code> and
114:         * <code>Message</code> are automatically set to indicate the random
115:         * challange and error message (if any) from a previous attempt, respectively.
116:         * <p>
117:         * The following configuration parameters are recgnized:
118:         *
119:         * <dl class=props>
120:         * <dt>prefix	<dd> URL prefix for proxy
121:         * <dt>authenticate	<dd> URL for authentication page
122:         * <dt>cookie	<dd> name of the cookie
123:         * <dt>roles	<dd> list of roles
124:         * <dt>proxy	<dd> prefix for proxy handler
125:         * <dt>idName	<dd> property key for token id
126:         * <dt>roleName	<dd> property key for token roles
127:         * <dt>maxIdle	<dd> maximum idle time for token (seconds)
128:         * <dt>maxAge	<dd> maximum total age for token (seconds)
129:         * <dt>maxUses	<dd> maximum total uses for token
130:         * <dt>exit	<dd> prefix to exit a session
131:         * <dt>all	<dd> "free" directory suffixes
132:         * <dt>template	<dd> login template
133:         *</dl>
134:         *
135:         * Currently, the "sunlabs.brazil.handler.MultiProxyHandler" class
136:         * is called to do the actual proxying.
137:         * <i>(There should be a link to a sample config file for this one)</i>
138:         * <p>
139:         * NOTE: This handler is included for historical purposes.  It should be
140:         * upated to take advantage of features not available when it was first written.
141:         *
142:         * @author		Stephen Uhler
143:         * @version            1.29, 00/12/11
144:         */
145:
146:        public class SunNetAuthHandler implements  Handler {
147:            Hashtable proxies; // where to keep proxy handlers
148:            Handler tokenHandler; // the handler to verify the credentials
149:            String propsPrefix; // my prefix into the properties file
150:            String UrlPrefix; // The url prefix that triggers this handler
151:            String cookieName; // how to name our session cookie
152:            String authUrl; // the url for authentication
153:            String idKey; // The property name for the token id
154:            String roleKey; // The property name for the roles
155:            String template; // The file name of the login template
156:            String exitString; // Any url containing this string ends a session
157:            int maxAge; // max allowable age for token (in seconds)
158:            int maxIdle; // length of idle time (in seconds)
159:            int maxUses; // max usages for token
160:            Vector free; // no authorization required for these
161:
162:            static Random random; // our random number generator
163:            static final String PREFIX = "prefix"; // URL prefix for proxy
164:            static final String AUTH = "authenticate"; // URL for authentication page
165:            static final String COOKIE = "cookie"; // name of the cookie
166:            static final String ROLES = "roles"; // list of roles
167:            static final String PROXY = "proxy"; // prefix for proxy
168:            static final String ID_KEY = "idName"; // property key for token id
169:            static final String ROLE_KEY = "roleName"; // property key for token roles
170:            static final String MAX_IDLE = "maxIdle"; // maximum idle time for token
171:            static final String MAX_AGE = "maxAge"; // maximum total age for token
172:            static final String MAX_USES = "maxUses"; // maximum total uses for token
173:            static final String LOGOUT = "exit"; // prefix to exit a session
174:            static final String ALL = "all"; // "free" directory suffixes
175:            static final String PROXY_CLASS = "sunlabs.brazil.handler.MultiProxyHandler";
176:            static final String TEMPLATE = "template"; // login template
177:
178:            /**
179:             *  Create a "bag" for the handler hashtable
180:             */
181:
182:            static class RoleData {
183:                public String role; // name of the role
184:                public Handler handler; // handler reference
185:
186:                RoleData(String role, Handler handler) {
187:                    this .role = role;
188:                    this .handler = handler;
189:                }
190:
191:                public String toString() {
192:                    return role
193:                            + ": "
194:                            + (handler == null ? "(null)" : handler.getClass()
195:                                    .getName());
196:                }
197:            }
198:
199:            /**
200:             * Set up all of the handlers
201:             * - Secure Token Services for authentication
202:             * - MultiProxyHandler for dispatching to hosts
203:             */
204:
205:            public boolean init(Server server, String prefix) {
206:                propsPrefix = prefix;
207:
208:                /*
209:                 * Extract the configuration properties
210:                 * idKey	The name of the request property to put the
211:                 *		token id into. [id]
212:                 * roleKey	The name of the request property to put the
213:                 *		list of valid roles for this card into [roles]
214:                 * urlPrefix	The global prefix for this handler [/]
215:                 * TEMPLATE	The name of the login template page.  It must have
216:                 *		tags of the form:
217:                 *			<insert property=xx default=yy>
218:                 *		to substitute request properties.  Useful
219:                 *		values of xx include "random" and "Message" [login.html]
220:                 * authUrl	The url to send to the token handler.  The
221:                 *		query info from the client will be added automatically
222:                 * cookieName	The name to use for the browser cookie [brazil]
223:                 * roles	The list of valid roles for this url []
224:                 * maxUses	The total number of times the browser cookie
225:                 *		may be used in this session
226:                 * maxIdle	The longest interval allowed between uses of this
227:                 *		cookie (seconds)
228:                 * maxAge	Maximum lifetime allowed for this session (seconds)
229:                 * exitString	any url containing this string teminates a session
230:                 * all		Names of sub-directories anyone can access with
231:                 * 		no authentication
232:                 */
233:
234:                idKey = server.props.getProperty(propsPrefix + ID_KEY, "id");
235:                roleKey = server.props.getProperty(propsPrefix + ROLE_KEY,
236:                        "roles");
237:                UrlPrefix = server.props.getProperty(propsPrefix + PREFIX, "/");
238:                authUrl = server.props.getProperty(propsPrefix + AUTH,
239:                        "/SecureTokenServices/VerifyPin");
240:                cookieName = server.props.getProperty(propsPrefix + COOKIE,
241:                        "brazil");
242:                exitString = server.props.getProperty(propsPrefix + LOGOUT,
243:                        "exit");
244:                StringTokenizer roles = new StringTokenizer(server.props
245:                        .getProperty(propsPrefix + ROLES, ""));
246:
247:                StringTokenizer st = new StringTokenizer(server.props
248:                        .getProperty(propsPrefix + ALL, ""));
249:                free = new Vector(st.countTokens());
250:                for (int i = 0; i < free.capacity(); i++) {
251:                    free.addElement(UrlPrefix + st.nextToken());
252:                }
253:
254:                maxUses = Integer.decode(
255:                        server.props
256:                                .getProperty(propsPrefix + MAX_USES, "1000"))
257:                        .intValue();
258:                maxIdle = Integer.decode(
259:                        server.props
260:                                .getProperty(propsPrefix + MAX_IDLE, "1200"))
261:                        .intValue();
262:                maxAge = Integer.decode(
263:                        server.props
264:                                .getProperty(propsPrefix + MAX_AGE, "86400"))
265:                        .intValue();
266:
267:                server.log(Server.LOG_DIAGNOSTIC, prefix,
268:                        "Config parameters:\n" + "  url prefix: " + UrlPrefix
269:                                + "\n" + "  token URL: " + authUrl + "\n"
270:                                + "  browser cookie: " + cookieName + "\n"
271:                                + "  exit string: " + exitString + "\n"
272:                                + "  roles: " + roles + "\n" + "  max uses: "
273:                                + maxUses + "\n" + "  max idle: " + maxIdle
274:                                + "\n" + "  max age: " + maxAge + "\n"
275:                                + "  free dirs: " + free + "\n" + "---");
276:
277:                /*
278:                 * Read in the template file.  If it doesn't start with /,
279:                 * make it relative to the document root
280:                 */
281:
282:                String templateFile = server.props.getProperty(propsPrefix
283:                        + TEMPLATE, "login.html");
284:                try {
285:                    FileInputStream in;
286:
287:                    if (!templateFile.startsWith(File.separator)) {
288:                        templateFile = server.props
289:                                .getProperty(FileHandler.ROOT)
290:                                + File.separator + templateFile;
291:                    }
292:                    server.log(Server.LOG_DIAGNOSTIC, prefix, "Template: "
293:                            + templateFile);
294:                    in = new FileInputStream(templateFile);
295:                    byte[] contents = new byte[in.available()];
296:                    in.read(contents);
297:                    template = new String(contents);
298:                    in.close();
299:                } catch (Exception e) {
300:                    server.log(Server.LOG_ERROR, prefix,
301:                            "Can't read template: " + e);
302:                    return false;
303:                }
304:
305:                /*
306:                 * Start the token handler.  Set the properties appropriately
307:                 */
308:
309:                try {
310:                    String tokenName = server.props.getProperty(propsPrefix
311:                            + "token.class", "");
312:                    server.log(Server.LOG_DIAGNOSTIC, prefix, "tokenHndlr: "
313:                            + tokenName);
314:                    Class tokenClass = Class.forName(tokenName);
315:                    tokenHandler = (Handler) tokenClass.newInstance();
316:                } catch (Exception e) {
317:                    server.log(Server.LOG_WARNING, prefix,
318:                            "Error creating token handler: " + e);
319:                    return false;
320:                }
321:                if (!tokenHandler.init(server, propsPrefix + "token.")) {
322:                    server.log(Server.LOG_ERROR, prefix,
323:                            "token handler won't start");
324:                    return false;
325:                }
326:
327:                /*
328:                 * Kick off all the proxy handlers.  Make up a default
329:                 * prefix for those prefixes that aren't specified.
330:                 * If there is no handler, then  fall through (how XXX)
331:                 * New strategy:  Look for a "host" property, only start the proxy
332:                 * if "host" is specified, otherwise, skip it!
333:                 */
334:
335:                proxies = new Hashtable(roles.countTokens());
336:                while (roles.hasMoreTokens()) {
337:                    String role = roles.nextToken();
338:                    System.out.println("Working on role: " + role);
339:                    String proxyPrefix = propsPrefix + role + ".";
340:
341:                    if (!server.props.containsKey(proxyPrefix + PREFIX)) {
342:                        server.props.put(proxyPrefix + PREFIX, UrlPrefix
343:                                + (UrlPrefix.endsWith("/") ? "" : "/") + role
344:                                + "/");
345:                    }
346:                    server.log(Server.LOG_DIAGNOSTIC, prefix, "role " + role
347:                            + " prefix: "
348:                            + server.props.get(proxyPrefix + PREFIX));
349:                    try {
350:                        Class proxyClass = Class.forName(PROXY_CLASS);
351:                        Handler h = (Handler) proxyClass.newInstance();
352:                        if (h.init(server, proxyPrefix)) {
353:                            proxies.put(server.props.get(proxyPrefix + PREFIX),
354:                                    new RoleData(role, h));
355:                        } else {
356:                            server.log(Server.LOG_WARNING, prefix,
357:                                    "No proxy specified" + " for role: " + role
358:                                            + ", using local directory");
359:                            proxies.put(server.props.get(proxyPrefix + PREFIX),
360:                                    new RoleData(role, null));
361:                        }
362:                    } catch (Exception e) {
363:                        server.log(Server.LOG_WARNING, prefix,
364:                                "Error creating handler: " + e);
365:                        e.printStackTrace();
366:                    }
367:                }
368:                if (proxies.size() < 1) {
369:                    server.log(Server.LOG_ERROR, prefix,
370:                            "Can't start any proxies");
371:                    server.log(Server.LOG_ERROR, prefix, "  SECURITY ALERT!");
372:                    return false;
373:                }
374:                server.log(Server.LOG_DIAGNOSTIC, prefix, "roles: " + proxies);
375:                return true;
376:            }
377:
378:            /**
379:             * Act like a "gatekeeper".  If we have a valid browser cookie, 
380:             * Then dispatch to one of the proxies.  If not, try to authenticate
381:             * by returning the login "template", fetching the credentials, and
382:             * establising a session.
383:             */
384:
385:            public boolean respond(Request request) throws IOException {
386:
387:                if (!request.url.startsWith(UrlPrefix)) {
388:                    request.log(Server.LOG_DIAGNOSTIC, "Handler " + propsPrefix
389:                            + " ignoring: " + request.url);
390:                    return false;
391:                }
392:
393:                /*
394:                 * Extract the browser cookie - if any
395:                 */
396:
397:                String cookieValue = null;
398:                try {
399:                    String header = (String) request.headers.get("Cookie");
400:                    System.out.println("HEADERS.GET.COOKIE: " + header);
401:                    int index = header.indexOf(cookieName + "=");
402:                    StringTokenizer st = new StringTokenizer(header.substring(
403:                            index).substring(cookieName.length() + 1));
404:                    cookieValue = st.nextToken();
405:                    // Strip off the semicolon if there is one
406:                    if (cookieValue.endsWith(";")) {
407:                        cookieValue = cookieValue.substring(0, cookieValue
408:                                .length() - 1);
409:                    }
410:                    request.log(Server.LOG_DIAGNOSTIC, "  Got cookie: "
411:                            + cookieValue);
412:                } catch (Exception e) {
413:                }
414:
415:                /**
416:                 * Look for session termination.
417:                 */
418:
419:                if (request.url.indexOf(exitString) != -1) {
420:                    Token.removeToken(cookieValue);
421:                    request.log(Server.LOG_DIAGNOSTIC, "  Session teminated: "
422:                            + request.url);
423:                    return false;
424:                }
425:
426:                /*
427:                 * See if its a free-be
428:                 */
429:
430:                Enumeration e = free.elements();
431:                while (e.hasMoreElements()) {
432:                    if (request.url.startsWith((String) e.nextElement())) {
433:                        request.log(Server.LOG_DIAGNOSTIC,
434:                                "  Unprotected url: " + request.url);
435:                        return false;
436:                    }
437:                }
438:
439:                /*
440:                 * See if this prefix matches one of the roles
441:                 */
442:
443:                Handler handler = null; // the handler for this url
444:                String role = null; // the role for this url
445:                Enumeration keys = proxies.keys();
446:                while (keys.hasMoreElements()) {
447:                    String key = (String) keys.nextElement();
448:                    if (request.url.startsWith(key)) {
449:                        RoleData data = (RoleData) proxies.get(key);
450:                        handler = data.handler;
451:                        role = data.role;
452:                        break;
453:                    }
454:                }
455:
456:                if (role == null) {
457:                    request.log(Server.LOG_DIAGNOSTIC,
458:                            "  No prefix match for: " + request.url);
459:                    request.sendError(400, "Not found", "No matching role");
460:                    return true;
461:                }
462:
463:                /*
464:                 * Set a browser cookie, if it doesn't exist
465:                 */
466:
467:                if (cookieValue == null) {
468:                    do {
469:                        cookieValue = Long.toHexString(random.nextLong());
470:                    } while (cookieValue.length() < 14);
471:                    cookieValue = cookieValue.substring(0, 14);
472:                    request.log(Server.LOG_DIAGNOSTIC, "  New cookie: "
473:                            + cookieValue);
474:                    request.addHeader("Set-Cookie", cookieName + "="
475:                            + cookieValue + "; path=" + UrlPrefix);
476:                }
477:
478:                request.props.put("challenge", cookieValue);
479:
480:                /*
481:                 * No token, Send client the login page.  Then the request should
482:                 * be re-issued by the client with the credentials in the query data.
483:                 */
484:
485:                if (!Token.haveToken(cookieValue)) {
486:                    Token.getToken(cookieValue); // create a blank token
487:                    returnLogin(request, "");
488:                    return true;
489:                }
490:                Token token = Token.getToken(cookieValue);
491:
492:                /*
493:                 * Have an empty token, Call the STS handler to get the
494:                 * proper credentials.  The client card data should be
495:                 * in the query data.   Make sure we add the challenge to the
496:                 * query data.
497:                 *
498:                 * XXX Technicaly this is incorrect.  We need to generate our own request object, instead of
499:                 * trying to pervert the original one.
500:                 */
501:
502:                if (token.getId() == null) {
503:                    String save = request.url;
504:                    request.url = authUrl;
505:
506:                    if (request.query.length() > 0) {
507:                        request.query += "&random=" + cookieValue;
508:                    } else {
509:                        request.query = "random=" + cookieValue;
510:                    }
511:
512:                    request.log(Server.LOG_DIAGNOSTIC,
513:                            "  About to call token handler: " + authUrl
514:                                    + " query: " + request.query + " params: "
515:                                    + request.getQueryData(null) + " post: "
516:                                    + request.postData + " headers: "
517:                                    + request.headers + " request.method:"
518:                                    + request.method);
519:
520:                    boolean ok = tokenHandler.respond(request);
521:                    request.log(Server.LOG_DIAGNOSTIC, "  result " + ok + " ("
522:                            + request.props + ")");
523:                    request.url = save;
524:
525:                    /*
526:                     * at this point we should have the credentials in the request.
527:                     * If not - return to the login page.
528:                     * If so, remember the credentials in our token object.
529:                     */
530:
531:                    String id = (String) request.props.get(idKey);
532:                    String error = request.props
533:                            .getProperty("error", "unknown");
534:                    if (id == null) {
535:                        request.log(Server.LOG_DIAGNOSTIC, "   Can't find: "
536:                                + idKey + " in request data");
537:                        returnLogin(request,
538:                                "No token id found in request data: "
539:                                        + error.substring(error
540:                                                .lastIndexOf(":") + 1));
541:                        return true;
542:                    }
543:                    String roles = (String) request.props.get(roleKey);
544:                    if (roles == null) {
545:                        request.log(Server.LOG_DIAGNOSTIC, "   Can't find: "
546:                                + roleKey + " in request data");
547:                        returnLogin(request, "No roles available for id " + id);
548:                        return true;
549:                    }
550:                    token.setToken(id, roles);
551:
552:                    /*
553:                     * Strip off the query data used for token validation.
554:                     * This should restore the query info that was presented as
555:                     * part of the original request.
556:                     */
557:
558:                    // request.query="";
559:                }
560:
561:                /*
562:                 * Have a token, make sure its still valid.  If so, call the
563:                 * proper handler, otherwise redirect to the login page with
564:                 * the appropriate error message.  We should remember the URL, 
565:                 * so we can redirect back here when reauthentication is complete.
566:                 */
567:
568:                if (token.getAge() > maxAge || token.getIdle() > maxIdle
569:                        || token.getUses() > maxUses) {
570:                    String message;
571:                    if (token.getAge() > maxAge) {
572:                        message = "Session is too old";
573:                    } else if (token.getIdle() > maxIdle) {
574:                        message = "Session was idle too long";
575:                    } else {
576:                        message = "Session was used up";
577:                    }
578:                    Token.removeToken(cookieValue);
579:                    returnLogin(request, message);
580:                    return true;
581:                }
582:                request.log(Server.LOG_DIAGNOSTIC, "Credentials check: "
583:                        + " age=" + token.getAge() + " idle=" + token.getIdle()
584:                        + " uses=" + token.getUses());
585:
586:                /*
587:                 * Now check the url against the list of allowed roles
588:                 */
589:
590:                Vector valid = token.getRoles();
591:                if (valid.contains(role)) {
592:                    if (handler != null) {
593:                        request.log(Server.LOG_DIAGNOSTIC,
594:                                "  dispatching to proxy " + role);
595:                        return handler.respond(request);
596:                    } else {
597:                        request.log(Server.LOG_DIAGNOSTIC,
598:                                "  dispatching next handler");
599:                        return false;
600:                    }
601:                } else {
602:                    request.sendError(400, "Not found", "Invalid role");
603:                    return true;
604:                }
605:            }
606:
607:            /**
608:             * return the login page with the appropriate message substituted in
609:             */
610:
611:            public void returnLogin(Request request, String message) {
612:                request.props.put("Message", message);
613:                request.log(Server.LOG_DIAGNOSTIC, "sending login page: "
614:                        + message);
615:                String result = processTemplate(template, request.props);
616:                try {
617:                    request.sendResponse(result);
618:                } catch (IOException e) {
619:                    request.log(Server.LOG_ERROR, e.toString());
620:                }
621:            }
622:
623:            /**
624:             * Process a template page, and send to the client.
625:             * This should be re-done to use the template handler.
626:             * Look for html tags of the form:
627:             *   <insert property=[name] default=[default]>
628:             * Also look for:
629:             *   <param name=[name] value=[value]>
630:             * and replace the tag with the value of the request property.
631:             * @param template		The template to process
632:             * @param data		The hashtable containing the data to subst
633:             */
634:
635:            public static String processTemplate(String template, Hashtable data) {
636:                // System.out.println(" munge: " + data);
637:                HtmlRewriter hr = new HtmlRewriter(template);
638:                while (hr.nextTag()) {
639:                    String tag = hr.getTag();
640:                    if (tag.equals("insert")) {
641:                        String property = hr.get("property");
642:                        String def;
643:                        if ((property != null) && data.containsKey(property)) {
644:                            hr.append((String) data.get(property));
645:                        } else if ((def = hr.get("default")) != null) {
646:                            hr.append(def);
647:                        }
648:                    } else if (tag.equals("param")) {
649:                        // System.out.println(" param: " + h);
650:                        String property = hr.get("name");
651:                        if (data.containsKey(property)) {
652:                            hr.put("value", (String) data.get(property));
653:                        }
654:                    }
655:                }
656:                return hr.toString();
657:            }
658:
659:            /**
660:             * Seed the random number generator.
661:             */
662:
663:            static {
664:                random = new Random();
665:            }
666:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.