JDK-4303463 : Authenticator will not work in Kiosk situations because of assumptions
  • Type: Enhancement
  • Component: core-libs
  • Sub-Component: java.net
  • Affected Version: 1.3.0,1.4.2_14,5.0,6u10
  • Priority: P4
  • Status: Closed
  • Resolution: Won't Fix
  • OS: solaris_10,windows_nt,windows_xp
  • CPU: generic,x86,sparc
  • Submitted: 2000-01-09
  • Updated: 2017-07-28
  • Resolved: 2017-07-28
Related Reports
Duplicate :  
Relates :  
Description
Name: mc57594			Date: 01/08/2000


java version "1.3beta"
Java(TM) 2 Runtime Environment, Standard Edition (build 1.3beta-O)
Java(TM) HotSpot Client VM (build 1.3beta-O, mixed mode)


When setting up a multi-user Kiosk for a web-browser-like application, it would
be nice to be able to "restart" the authentication. For instance, if one kiosk
user provides a username and password to access a restricted file on a remote
web server, the Authenticator retains that username and password and tries to
use it for the next URLConnection to the same web page. This allows a
subsequent user to gain access to the first users pages without typing a
password. I would like to be able to tell the Authenticator to reset its
internal state and not try to reuse the username and password. Right now, that
is impossible, without restarting the Java VM.

My application allows a user A to go to a web server and retrieve a number of
pages in her own realm. When another user B walks up to the kiosk, that user is
asked for his password only if the authentication didn't work. If user B
decides to look at user A's documents instead of his own, he is never asked for
a username and password. URLConnection automatically uses the username and
password already acquired from an Authenticator without asking user B or giving
the application a chance to deny access.

Right now there is no way to invalidate an authenticator and log someone out
from their basic authentication.

The workaround is set up my own password system that asks for a password when
user A logs out.


Example code:

      if (sess != null)
	    sess.setDefaultAuthenticator();  // Installs new Authenticator.

      System.out.println("Connecting to "+userURL);
      URLConnection UC = userURL.openConnection();
      System.out.println("Auth request prop: "+UC.getRequestProperty
("Authorization"));
      UC.setRequestProperty("Authorization", "Basic ABCD"); // Garbage
      System.out.println("Auth request pro2: "+UC.getRequestProperty
("Authorization"));
      long fileMod = UC.getLastModified();
      System.out.println("Auth request pro3: "+UC.getRequestProperty
("Authorization"));

Result (for user B trying to look at user A's web pages):

Connecting to http://salmon.crc.ricoh.com:8001/barrus/lists/mdates.sorted
Auth request prop: null
Auth request pro2: Basic ABCD
Auth request pro3: Basic bWVubG86YnJ1Y2U=


Notice that even though I have tried to set the request property to make the
URLConnection fail and call the Authenticator, the request property is changed
inside the call to UC.getLastModified() to the most recently used
username:password and the Authenticator is never called. (When my Authenticator
is called, it prints out a line indicating that it has been called and that
didn't happen above.)

I have also tried clearing the password character array as suggested in the
Authentication documentation and that doesn't make any difference.

The only thing that does work is to go to another realm and let the
authenticator fail (return an invalid username:password) and then the
Authenticator asks you again for your password when you return to your own
realm.

How about a routine that clears out the hidden Authentication cache so that the
Authenticator gets called again next time a 401 is returned from a
URLConnection? This would solve my problem.
(Review ID: 99674) 
======================================================================

Comments
Since JDK 9 (JDK-8169495) it is possible to explicitly set an Authenticator on a given HttpURLConnection. This new method should solve the issue.
28-07-2017

WORK AROUND Name: mc57594 Date: 01/08/2000 Create a authentication system which includes a way to login and logout of your kiosk. When a user logs out, set a boolean that is checked by routine which does the URLConnections. Don't make any URLConnections until user B has logged in and deny access for user B to user A's web pages, at least until user B has accessed his own protected web pages (which seems to reset the Authentication cache). This means keeping track of who "belongs" to what URLs or making sure that everyone has at least one file in a specific realm on some web server that can be used for resetting the Authenticator. Another workaround is to stop and restart the JVM - not a good option. ======================================================================
11-06-2004

EVALUATION It is not possible to provide a method that resets the cache for the following reason. The authentication cache is managed by the HTTP URLStreamHandler that is provided with J2SE and loaded dynamically when HTTP URLs are created. The cache is not a required component of the handler and any application could load a different handler that does not implement the cache or implements it in a different way. Therefore, we cannot add a public API to manage functionality that we are not certain will always be there. A possible solution to the underlying requirement could be to use the new authentication framework going into merlin (provided by JAAS). We could store the identity of the user (Subject) who performed the authentication in each cache entry and then only use a particular cache entry when the same user is logged in. This would not require any API change, but it does need some further study to ensure that compatibility is preserved and performance not adversely affected. For this reason, I have to uncommit this RFE from merlin. michael.mcmahon@ireland 2000-10-12
12-10-2000