/*
   * (non-Javadoc)
   *
   * @see org.deegree.security.AbstractAuthentication#authenticate(java.util.Map)
   */
  public User authenticate(Map<String, String> params) throws WrongCredentialsException {

    String tmp = initParams.get(INIT_PARAM_PATTERN);
    List<String> patterns = StringTools.toList(tmp, ",;", true);

    String ipAddress = params.get(AUTH_PARAM_IPADDRESS);
    if (ipAddress != null) {
      for (String p : patterns) {
        if (ipAddress.matches(p)) {
          User usr = null;
          try {
            SecurityAccessManager sam = SecurityAccessManager.getInstance();
            // use matching pattern as username and password
            usr = sam.getUserByName(p);
            usr.authenticate(null);
          } catch (Exception e) {
            LOG.logError(e.getMessage());
            String msg = Messages.getMessage("OWSPROXY_USER_AUTH_ERROR", ipAddress);
            throw new WrongCredentialsException(msg);
          }
          return usr;
        }
      }
      throw new WrongCredentialsException(
          Messages.getMessage("OWSPROXY_USER_AUTH_ERROR", ipAddress));
    }
    return null;
  }
  /**
   * Loads the deegree SecurityAccesManager if no instance is present jet.
   *
   * @throws GeneralSecurityException if the no instance of the deegree securitymanager could be
   *     touched.
   */
  private void initializeSecurityAccessManager() throws GeneralSecurityException {

    if (databaseInfo == null) {
      LOG.logError(Messages.getMessage("WASS_ERROR_SECURITYACCESSMANAGER_NO_DBINFO"));
      return;
    }
    Properties properties = new Properties();
    properties.setProperty("driver", databaseInfo.getDriver());
    properties.setProperty("url", databaseInfo.getURL());
    properties.setProperty("user", databaseInfo.getUser());
    properties.setProperty("password", databaseInfo.getPassword());
    try {
      securityAccessManager = SecurityAccessManager.getInstance();
    } catch (GeneralSecurityException gse) {
      try {
        SecurityAccessManager.initialize(
            "org.deegree.security.drm.SQLRegistry", properties, 60 * 1000);
        securityAccessManager = SecurityAccessManager.getInstance();
      } catch (GeneralSecurityException gse2) {
        LOG.logError(Messages.getMessage("WASS_ERROR_SECURITYACCESSMANAGER"));
        LOG.logError(gse2.getLocalizedMessage(), gse2);
        throw new GeneralSecurityException(getMessage("WASS_ERROR_SECURITYACCESSMANAGER"));
      }
    }
  }
  /*
   * (non-Javadoc)
   *
   * @see org.deegree.security.AbstractAuthentication#authenticate(java.util.Map,
   * javax.servlet.http.HttpServletRequest)
   */
  public User authenticate(Map<String, String> params, HttpServletRequest request)
      throws WrongCredentialsException {
    String sessionID = params.get(AUTH_PARAM_SESSIONID);
    User usr = null;
    if (sessionID != null) {
      String[] user = new String[3];
      String urlStr = initParams.get(INIT_PARAM_WAS);
      urlStr = urlStr.replaceFirst("\\[SESSIONID\\]", sessionID);
      LOG.logDebug("request WAS for user information: " + urlStr);
      Document doc = null;
      try {
        URL url = new URL(urlStr);
        XMLFragment xml = new XMLFragment(url);
        doc = xml.getRootElement().getOwnerDocument();
        user[0] = XMLTools.getNodeAsString(doc, "/User/UserName", nsContext, null);
        user[1] = XMLTools.getNodeAsString(doc, "/User/Password", nsContext, null);
      } catch (Exception e) {
        LOG.logError(e.getMessage(), e);
        throw new WrongCredentialsException(Messages.getMessage("OWSProxyServletFilter.WASACCESS"));
      }

      if (user[0] != null) {
        try {
          SecurityAccessManager sam = SecurityAccessManager.getInstance();
          usr = sam.getUserByName(user[0]);
          usr.authenticate(user[1]);
        } catch (Exception e) {
          throw new WrongCredentialsException(
              Messages.getMessage("OWSPROXY_USER_AUTH_ERROR", user[0]));
        }
      } else {
        String msg = "undefined error";
        try {
          msg = XMLTools.getNodeAsString(doc, "//ServiceException", nsContext, "general error");
        } catch (Exception e) {
          // should never happen
        }
        throw new WrongCredentialsException(msg);
      }
    }

    return usr;
  }
  @Override
  public void actionPerformed(FormEvent event) {

    // the Role for which the rights are to be set
    int roleId = -1;
    // array of ints, ids of Layers (SecuredObjects) for which
    // the Role has access rights
    int[] layers = null;
    // corresponding maps of key (PropertyName) / value-pairs that
    // constitute access constraints
    Map<String, Object>[] layerConstraints = null;

    SecurityAccessManager manager = null;
    SecurityTransaction transaction = null;

    try {
      RPCWebEvent ev = (RPCWebEvent) event;
      RPCMethodCall rpcCall = ev.getRPCMethodCall();
      RPCParameter[] params = rpcCall.getParameters();

      // validates the incomming method call and extracts the roleID
      roleId = validate(params);

      RPCParameter[] layerParams = (RPCParameter[]) params[1].getValue();
      layers = new int[layerParams.length];
      layerConstraints = new Map[layerParams.length];
      extractLayerValues(layers, layerConstraints, layerParams);

      // extract FeatureType rights
      if (!(params[2].getValue() instanceof RPCParameter[])) {
        throw new RPCException(Messages.getMessage("IGEO_STD_STORERIGHTS_THIRD_PARAM"));
      }

      // array of ints, ids of FeatureTypes (SecuredObjects) for which
      // the Role has access rights
      FeatureTypeRight[] featureTypes = extractFeatureTypeValues(params);

      transaction = SecurityHelper.acquireTransaction(this);
      SecurityHelper.checkForAdminRole(transaction);

      manager = SecurityAccessManager.getInstance();
      User user = transaction.getUser();
      Role role = transaction.getRoleById(roleId);

      // perform access check
      if (!user.hasRight(transaction, "update", role)) {
        getRequest().setAttribute("SOURCE", this.getClass().getName());
        String s = Messages.getMessage("IGEO_STD_STORERIGHTS_MISSING_RIGHTS", role.getName());
        getRequest().setAttribute("MESSAGE", s);
        setNextPage("error.jsp");
        return;
      }

      // set/delete access rights for Layers
      SecuredObject[] presentLayers = transaction.getAllSecuredObjects(ClientHelper.TYPE_LAYER);
      setAccessRightsForLayers(layers, layerConstraints, transaction, role, presentLayers);

      // set/delete access rights for FeatureTypes
      SecuredObject[] presentFeatureTypes =
          transaction.getAllSecuredObjects(ClientHelper.TYPE_FEATURETYPE);
      setAccessRightsForFeatureTypes(featureTypes, transaction, role, presentFeatureTypes);

      manager.commitTransaction(transaction);
      transaction = null;
      String s = Messages.getMessage("IGEO_STD_STORERIGHTS_SUCCESS", role.getID());
      getRequest().setAttribute("MESSAGE", s);
    } catch (RPCException e) {
      getRequest().setAttribute("SOURCE", this.getClass().getName());
      String s = Messages.getMessage("IGEO_STD_STORERIGHTS_INVALID_REQ", e.getMessage());
      getRequest().setAttribute("MESSAGE", s);
      setNextPage("error.jsp");
      LOG.logDebug(e.getMessage(), e);
    } catch (GeneralSecurityException e) {
      getRequest().setAttribute("SOURCE", this.getClass().getName());
      String s = Messages.getMessage("IGEO_STD_STORERIGHTS_ERROR", e.getMessage());
      getRequest().setAttribute("MESSAGE", s);
      setNextPage("error.jsp");
      LOG.logDebug(e.getMessage(), e);
    } finally {
      if (manager != null && transaction != null) {
        try {
          manager.abortTransaction(transaction);
        } catch (GeneralSecurityException e) {
          LOG.logDebug(e.getMessage(), e);
        }
      }
    }
  }