+

Search Tips   |   Advanced Search

Create SPNEGO tokens for J2EE, .NET, Java, web service clients for HTTP requests

We can create a Simple and Protected GSS-API Negotiation (SPNEGO) token for the applications and insert this token into the HTTP headers to authenticate to the WAS.

  1. Create a client GSS credential. Choose one of the following 4 options:

    1. Create a GSS credential for the Kerberos credential cache. For example:
              System.setProperty("javax.security.auth.useSubjectCredsOnly", "false");
              Oid krb5MechOid    = new Oid("1.2.840.113554.1.2.2");
              Oid spnegoMechOid  = new Oid("1.3.6.1.5.5.2"); 
      
              GSSManager manager = GSSManager.getInstance();
              GSSName gssUserName = manager.createName(userName, GSSName.NT_USER_NAME, krb5MechOid);
              clientGssCreds = manager.createCredential(gssUserName.canonicalize(krb5MechOid), 
                                                            GSSCredential.INDEFINITE_LIFETIME, 
                                                            krb5MechOid, 
                                                            GSSCredential.INITIATE_ONLY);
              clientGssCreds.add (gssUserName, GSSCredential.INDEFINITE_LIFETIME, 
                                  GSSCredential.INDEFINITE_LIFETIME, 
                                  spnegoMechOid, 
                                  GSSCredential.INITIATE_ONLY);

    2. Create a GSS credential from a subject that has Kerberos tickets. For example:
             Oid krb5MechOid    = new Oid("1.2.840.113554.1.2.2");
             Oid spnegoMechOid  = new Oid("1.3.6.1.5.5.2"); 
      
             GSSManager manager = GSSManager.getInstance();
             clientGssCreds = (GSSCredential) Subject.doAs(subject, new PrivilegedExceptionAction() 
             {
                 public Object run() throws GSSException, Exception  
                 {
                     try {
                         gssName = manager.createName( userName, GSSName.NT_USER_NAME, getKrb5MechOid());
                         GSSCredential gssCred = manager.createCredential(
                                                         gssName.canonicalize(krb5MechOid), GSSCredential.DEFAULT_LIFETIME, krb5MechOid, GSSCredential.INITIATE_ONLY);
                         gssCred.add (gssUserName, GSSCredential.INDEFINITE_LIFETIME, 
                                      GSSCredential.INDEFINITE_LIFETIME, 
                                      spnegoMechOid, 
                                      GSSCredential.INITIATE_ONLY);
      
                         return gssCred;
                     } catch (GSSException gsse) {
                     } catch (Exception e) {
                     }
      
                     return null;
                 }
             });

    3. Create a GSS credential after calling the WSKRB5Login login module. For example:
             Oid krb5MechOid    = new Oid("1.2.840.113554.1.2.2");
             Oid spnegoMechOid  = new Oid("1.3.6.1.5.5.2"); 
      
             System.setProperty("javax.security.auth.useSubjectCredsOnly", "true");
             GSSManager manager = GSSManager.getInstance();
             GSSName gssUserName = manager.createName(userName, GSSName.NT_USER_NAME, krb5MechOid);
             clientGssCreds = manager.createCredential(gssUserName.canonicalize(krb5MechOid), 
                                                       GSSCredential.INDEFINITE_LIFETIME, 
                                                       krb5MechOid, 
                                                       GSSCredential.INITIATE_ONLY);
             clientGssCreds.add (gssUserName, GSSCredential.INDEFINITE_LIFETIME, 
                                 GSSCredential.INDEFINITE_LIFETIME, 
                                 spnegoMechOid, 
                                 GSSCredential.INITIATE_ONLY);

    4. Create a GSS credential using the Microsoft native Kerberos credential cache. For example:
             Oid krb5MechOid    = new Oid("1.2.840.113554.1.2.2");
             Oid spnegoMechOid  = new Oid("1.3.6.1.5.5.2"); 
      
             System.setProperty("javax.security.auth.useSubjectCredsOnly", "false");
             GSSManager manager = GSSManager.getInstance();
             
             clientGssCreds = manager.createCredential(null, GSSCredential.INDEFINITE_LIFETIME, krb5MechOid, GSSCredential.INITIATE_ONLY);
      
             clientGssCreds.add(null, GSSCredential.INDEFINITE_LIFETIME, 
                                GSSCredential.INDEFINITE_LIFETIME, 
                                spnegoMechOid, GSSCredential.INITIATE_ONLY);

      The MSLSA: credential cache relies on the ability to extract the entire Kerberos ticket, including the session key from the Kerberos LSA.&nbsp. In an attempt to increase security, Microsoft has begun to implement a feature by which they no longer export the session keys for Ticket Getting Tickets, which can cause them to be useless to the IBM JGSS when attempts are made to request additional service tickets. This new feature has been seen in Windows 2003 Server and Windows XP SP2 Beta. Microsoft has provided the following registry key to disable this new feature:

      HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Lsa\Kerberos\Parameters
      AllowTGTSessionKey = 0x01 (DWORD)

      On Windows XP SP2 Beta 1 the key is specified as:

      HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Lsa\Kerberos
      AllowTGTSessionKey = 0x01 (DWORD)

  2. After we have created a client GSS credential, we can now create the SPNEGO token and insert it in the HTTP header as in the following example:
           // create target server SPN
           GSSName gssServerName = manager.createName(targetServerSpn, GSSName.NT_USER_NAME);
    
           GSSContext clientContext = manager.createContext(gssServerName.canonicalize(spnegoMechOid), spnegoMechOid, clientGssCreds, GSSContext.DEFAULT_LIFETIME);
           // optional enable GSS credential delegation        clientContext.requestCredDeleg(true);
    
           byte[] spnegoToken = new byte[0];
    
           // create a SPNEGO token for the target server        spnegoToken = clientContext.initSecContext(spnegoToken, 0, spnegoToken.length);
    
           URL url = new URL(targetUrl);
           HttpURLConnection con= (HttpURLConnection) url.openConnection();
    
           try {
               // insert SPNEGO token in the HTTP header
               con.setRequestProperty("Authorization", "Negotiate " + Base64.encode(spnegoToken));
               con.getResponseCode();          
           } catch (IOException e) {
           } catch (Exception ex) {
           }


Results

Your application might need a Kerberos configuration file (krb5.ini or krb5.conf). Read about (dist) Create a Kerberos configuration file for more information.


Related tasks

  • Create a single sign-on for HTTP requests using SPNEGO Web authentication
  • Create a Kerberos service principal (SPN) and keytab file on the Microsoft domain controller machine
  • Configure Kerberos as the authentication mechanism using the administrative console
  • Create a Kerberos service principal name and keytab file
  • Add SPNEGO web authentication filters using the administrative console

  • CSIv2 inbound communications settings
  • CSIv2 outbound communications settings
  • SPNEGO web authentication configuration commands
  • SPNEGO web authentication filter commands
  • SPNEGO web authentication enablement
  • SPNEGO web authentication filter values
    IBM Java Generic Security Service API (JGSS) 6.0 Application Developer's Guide