/**
   * Do a refresh in the user's session. This method will update the last visit time for the current
   * user, as well checking for authentication if the session is new or the SSO user has changed
   */
  public void refreshSession() {

    LOG.trace("refreshSession");
    UserSession userSession = SessionFacade.getUserSession();
    RequestContext request = JForumExecutionContext.getRequest();

    if (userSession == null) {
      userSession = new UserSession();
      userSession.registerBasicInfo();
      userSession.setSessionId(request.getSessionContext().getId());
      userSession.setIp(request.getRemoteAddr());
      SessionFacade.makeUnlogged();

      if (!JForumExecutionContext.getForumContext().isBot()) {
        // Non-SSO authentications can use auto login
        if (!ConfigKeys.TYPE_SSO.equals(SystemGlobals.getValue(ConfigKeys.AUTHENTICATION_TYPE))) {
          if (SystemGlobals.getBoolValue(ConfigKeys.AUTO_LOGIN_ENABLED)) {
            this.checkAutoLogin(userSession);
          } else {
            userSession.makeAnonymous();
          }
        } else {
          this.checkSSO(userSession);
        }
      }

      SessionFacade.add(userSession);
    } else if (ConfigKeys.TYPE_SSO.equals(SystemGlobals.getValue(ConfigKeys.AUTHENTICATION_TYPE))) {
      SSO sso;

      try {
        sso =
            (SSO)
                Class.forName(SystemGlobals.getValue(ConfigKeys.SSO_IMPLEMENTATION)).newInstance();
      } catch (Exception e) {
        throw new ForumException(e);
      }

      // If SSO, then check if the session is valid
      if (!sso.isSessionValid(userSession, request)) {
        SessionFacade.remove(userSession.getSessionId());
        refreshSession();
      }
    } else {
      SessionFacade.getUserSession().updateSessionTime();
    }
  }
  /**
   * Checks for user authentication using some SSO implementation
   *
   * @param userSession UserSession
   */
  protected void checkSSO(UserSession userSession) {

    LOG.trace("checkSSO");
    try {
      SSO sso =
          (SSO) Class.forName(SystemGlobals.getValue(ConfigKeys.SSO_IMPLEMENTATION)).newInstance();
      String username = sso.authenticateUser(JForumExecutionContext.getRequest());

      if (username == null || username.trim().equals("")) {
        userSession.makeAnonymous();
      } else {
        SSOUtils utils = new SSOUtils();

        if (!utils.userExists(username)) {
          SessionContext session = JForumExecutionContext.getRequest().getSessionContext();

          String email =
              (String) session.getAttribute(SystemGlobals.getValue(ConfigKeys.SSO_EMAIL_ATTRIBUTE));
          String password =
              (String)
                  session.getAttribute(SystemGlobals.getValue(ConfigKeys.SSO_PASSWORD_ATTRIBUTE));

          if (email == null) {
            email = SystemGlobals.getValue(ConfigKeys.SSO_DEFAULT_EMAIL);
          }

          if (password == null) {
            password = SystemGlobals.getValue(ConfigKeys.SSO_DEFAULT_PASSWORD);
          }

          utils.register(password, email);
        }

        this.configureUserSession(userSession, utils.getUser());
      }
    } catch (Exception e) {
      e.printStackTrace();
      throw new ForumException("Error while executing SSO actions: " + e);
    }
  }