Package org.tamacat.httpd.auth

Source Code of org.tamacat.httpd.auth.WSSEAuthProcessor

/*
* Copyright (c) 2009, TamaCat.org
* All rights reserved.
*/
package org.tamacat.httpd.auth;

import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.LinkedHashMap;
import java.util.Map;

import org.apache.commons.codec.binary.Base64;
import org.apache.http.Header;
import org.apache.http.HttpRequest;
import org.apache.http.HttpResponse;
import org.apache.http.HttpStatus;
import org.apache.http.protocol.HttpContext;
import org.tamacat.httpd.exception.UnauthorizedException;
import org.tamacat.util.StringUtils;
import org.tamacat.util.UniqueCodeGenerator;

/**
* Implements of WS-Security Extenstion (WSSE) authentication.
*/
public class WSSEAuthProcessor extends AbstractAuthProcessor {
 
  static final String AUTHORIZATION = "Authorization";
  static final String WWW_AUTHENTICATE = "WWW-Authenticate";

  static final String X_WSSE_HEADER = "X-WSSE";
 
  @Override
  public void doFilter(HttpRequest request, HttpResponse response,
      HttpContext context) {
        try {
        String remoteUser = checkUser(request, context);
        context.setAttribute(remoteUserKey, remoteUser);
        } catch (UnauthorizedException e) {
          response.setStatusCode(HttpStatus.SC_UNAUTHORIZED);
          setWWWAuthenticateHeader(response);
          throw e;
        }
  }
 
  /**
   * Login check with AuthComponent.
   * @param request
   * @param context
   * @return login username in request parameter.
   * @throws UnauthorizedException
   */
  protected String checkUser(HttpRequest request, HttpContext context)
      throws UnauthorizedException {
      Header wsseAuthLine = request.getFirstHeader(X_WSSE_HEADER);
    if (wsseAuthLine != null && StringUtils.isNotEmpty(wsseAuthLine.getValue())) {
        String line = wsseAuthLine.getValue().replaceFirst("UsernameToken ", "");
          WSSE wsse = new WSSE(line);

        if (authComponent != null) {
        AuthUser user = authComponent.getAuthUser(wsse.getUsername(), context);
        String username = wsse.getUsername();
        String password = wsse.getPasswordDigest();
        String passwordDigest = getPasswordDigest(wsse, user);
        if (username != null && password != null
            && username.equals(user.getAuthUsername())
            && password.equals(passwordDigest)) {
          return user.getAuthUsername();
        }
      }
    }
      throw new UnauthorizedException();
  }
 
  /**
   * Get the password digest.
   * @param wsse
   * @param user
   * @return password digest
   */
  protected String getPasswordDigest(WSSE wsse, AuthUser user) {
    String password = user.getAuthPassword();
    if (password == null
        || wsse.getNonce() == null
        || wsse.getCreated() == null) {
      throw new UnauthorizedException();
    }
    byte[] nonce = new Base64().decode(wsse.getNonce().getBytes());
    byte[] created = wsse.getCreated().getBytes();
    byte[] pb = password.getBytes();
    byte[] digest = new byte[nonce.length + created.length + pb.length];
      System.arraycopy(nonce, 0, digest, 0, nonce.length);
      System.arraycopy(created, 0, digest, nonce.length, created.length);
      System.arraycopy(pb, 0, digest, nonce.length + created.length, pb.length);
      return new String(new Base64().encode(getSHA1(digest))).replace("\r","").replace("\n","");
  }
 
  /**
   * Set the "WWW-Authenticate" response header of WSSE authenticate realm.
   * @param response
   */
  protected void setWWWAuthenticateHeader(HttpResponse response) {
      response.addHeader(WWW_AUTHENTICATE, "WSSE profile=\"UsernameToken\"");
  }
 
  /**
   * Get the nonce.
   * @return nonce
   */
  protected String getNonce() {
    String nonce = UniqueCodeGenerator.generate();
    return new String(new Base64().encode(nonce.getBytes()));
  }
 
  /**
   * Get the SHA1 digest.
   * @param digest
   * @return bytes of digest.
   */
  protected byte[] getSHA1(byte[] digest) {
    try {
      MessageDigest md = MessageDigest.getInstance("SHA1");
      return md.digest(digest);
    } catch (NoSuchAlgorithmException e) {
      return null;
    }
  }
 
  /**
   * Bean class for WSSE attributes.
   */
  static class WSSE {
    private Map<String,String> params = new LinkedHashMap<String,String>();

    WSSE(String line) {
          String[] params = line.split(",");
        for (String keyValue : params) {
             String[] param = keyValue.trim().split("=");
             if (param != null && param.length >= 2) {
               String key = param[0].trim();
               StringBuilder value = new StringBuilder(param[1]);
               if (param.length > 2) {
                 for (int i=2; i<param.length; i++) {
                   value.append("=" + param[i]);
                 }
               }
               setParam(key,
                 value.toString().replaceFirst("^\"", "")
                 .replaceFirst("\"$", ""));
             }
        }
    }
    public void setParam(String key, String value) {
      this.params.put(key, value);
    }
   
    public Map<String, String> getParams() {
      return params;
    }
   
    public String getUsername() {
      return params.get("Username");
    }
   
    public String getPasswordDigest() {
      return params.get("PasswordDigest");
    }
   
    public String getNonce() {
      return params.get("Nonce");
    }
   
    public String getCreated() {
      return params.get("Created");
    }
  }
}
TOP

Related Classes of org.tamacat.httpd.auth.WSSEAuthProcessor

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.