由于可扩展可抛出

发布于 2025-02-07 18:14:20 字数 5889 浏览 1 评论 0原文

当用户尝试访问安全资源时,我在尝试记录端点的URI时会有问题。

我已经创建了一个AccessDeniedHandler的实例:

public class CustomAccessDeniedHandler implements AccessDeniedHandler {

      private final static Logger logger = Logger.getLogger(CustomAccessDeniedHandler.class);
    
      @Override
      public void handle(
          HttpServletRequest request,
          HttpServletResponse response,
          AccessDeniedException exc) throws IOException, ServletException {
    
        Authentication auth = SecurityContextHolder.getContext().getAuthentication();
        if (auth != null) {
          logger.warn("User: " + auth.getName()
              + " attempted to access the protected URL: "
              + request.getRequestURI());
        }
    
      }
    }

但是从未触发处理程序,我不明白为什么。在项目中,我们有此类,我想它在我的AccessDeniedHandler之前捕获了例外,但是我不知道O可以处理。

@Provider
public class ExceptionMH extends Throwable implements ExceptionMapper<Exception> {

  private static final long serialVersionUID = 1L;
  private static final Logger logger = Logger.getLogger(ExceptionMH.class);

  private void exceptionWarning(Exception e) {
    logger.warn("[ExceptionMH] Warn: ", e);
  }

  private void exceptionError(Exception e) {
    logger.error("[ExceptionMH] Error: ", e);
  }

  @Override
  public Response toResponse(Exception exception) {
    if (exception.getClass() == HttpRequestMethodNotSupportedException.class || exception.getClass() == NotFoundException.class) {
      this.exceptionWarning(exception);
      return Response.status(404).build();
    } else if (exception.getClass() == CardException.class) {
      this.exceptionWarning(exception);
      return Response.status(200).build();
    } else if (exception.getClass() == APIException.class) {
      String msg = ((APIException) exception).getRawResponse();
      logger.error("Facebook API exception: " + msg, exception);
      return Response.status(500).entity(msg).build();
    } else if (exception.getClass() == AccessDeniedException.class) {
      this.exceptionError(exception);
      return Response.status(401).entity("{ \"error\": \"" + exception.getMessage() + "\" }").build();
    } else {
      this.exceptionError(exception);
      return Response.status(500).build();
    }
  }
}

我该怎么做才能触发AccessDendiedHandler?

编辑:这是我的配置。宣布并添加了AccessDeniedhandler bean。

<b:beans xmlns="http://www.springframework.org/schema/security"
         xmlns:b="http://www.springframework.org/schema/beans"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xmlns:util="http://www.springframework.org/schema/util"
         xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd
                http://www.springframework.org/schema/security https://www.springframework.org/schema/security/spring-security.xsd
        http://www.springframework.org/schema/util
        http://www.springframework.org/schema/util/spring-util.xsd">

  <global-method-security pre-post-annotations="enabled" proxy-target-class="true"/>

  <http entry-point-ref="authEntryPoint" create-session="never" >
    <cors configuration-source-ref="corsSource"/>
    <csrf disabled="true"/>
    <custom-filter ref="authFilter" before="PRE_AUTH_FILTER"/>
    <access-denied-handler ref="customAccessDeniedHandler"/>
  </http>

  <authentication-manager alias="authenticationManager">
    <authentication-provider ref="daoAuthenticationProvider"/>
  </authentication-manager>

  <b:bean name="customAccessDeniedHandler"
        class="io.markethero.security.CustomAccessDeniedHandler" />

  <b:bean id="daoAuthenticationProvider" class="org.springframework.security.authentication.dao.DaoAuthenticationProvider">
    <b:property name="userDetailsService"  ref="userLoginService"/>
    <b:property name="passwordEncoder" ref="customizePasswordEncoder"/>
  </b:bean>

  <b:bean id="customizePasswordEncoder" class="io.markethero.security.CustomizePasswordEncoder"/>

  <b:bean id="authFilter" class="io.markethero.security.AuthFilter"/>

  <b:bean id="authEntryPoint" class="io.markethero.security.AuthEntryPoint"/>

  <b:bean id="corsSource" class="org.springframework.web.cors.UrlBasedCorsConfigurationSource">
    <b:property name="corsConfigurations">
      <util:map>
        <b:entry key="/**">
          <b:bean class="org.springframework.web.cors.CorsConfiguration">
            <b:property name="allowCredentials" value="true"/>
            <b:property name="allowedHeaders">
              <util:list>
                <b:value>Authorization</b:value>
                <b:value>Content-Type</b:value>
              </util:list>
            </b:property>
            <b:property name="exposedHeaders">
              <b:list>
                <b:value>Account-Locked</b:value>
                <b:value>Account-Disabled</b:value>
                <b:value>Bad-Credentials</b:value>
              </b:list>
            </b:property>
            <b:property name="allowedMethods">
              <util:list>
                <b:value>POST</b:value>
                <b:value>GET</b:value>
                <b:value>PUT</b:value>
                <b:value>DELETE</b:value>
                <b:value>OPTIONS</b:value>
              </util:list>
            </b:property>
            <b:property name="allowedOrigins" value="*"/>
          </b:bean>
        </b:entry>
      </util:map>
    </b:property>
  </b:bean>


</b:beans>

I have an issue when trying to logging URI of endpoint when a user try to access a secured Resource.

I've created an instance of AccessDeniedHandler :

public class CustomAccessDeniedHandler implements AccessDeniedHandler {

      private final static Logger logger = Logger.getLogger(CustomAccessDeniedHandler.class);
    
      @Override
      public void handle(
          HttpServletRequest request,
          HttpServletResponse response,
          AccessDeniedException exc) throws IOException, ServletException {
    
        Authentication auth = SecurityContextHolder.getContext().getAuthentication();
        if (auth != null) {
          logger.warn("User: " + auth.getName()
              + " attempted to access the protected URL: "
              + request.getRequestURI());
        }
    
      }
    }

But the handleMethod is never triggered and I don't understand why. In the project we have this class, and I suppose that it catch the exception before my AccessDeniedHandler, but I don't know o to deal with that.

@Provider
public class ExceptionMH extends Throwable implements ExceptionMapper<Exception> {

  private static final long serialVersionUID = 1L;
  private static final Logger logger = Logger.getLogger(ExceptionMH.class);

  private void exceptionWarning(Exception e) {
    logger.warn("[ExceptionMH] Warn: ", e);
  }

  private void exceptionError(Exception e) {
    logger.error("[ExceptionMH] Error: ", e);
  }

  @Override
  public Response toResponse(Exception exception) {
    if (exception.getClass() == HttpRequestMethodNotSupportedException.class || exception.getClass() == NotFoundException.class) {
      this.exceptionWarning(exception);
      return Response.status(404).build();
    } else if (exception.getClass() == CardException.class) {
      this.exceptionWarning(exception);
      return Response.status(200).build();
    } else if (exception.getClass() == APIException.class) {
      String msg = ((APIException) exception).getRawResponse();
      logger.error("Facebook API exception: " + msg, exception);
      return Response.status(500).entity(msg).build();
    } else if (exception.getClass() == AccessDeniedException.class) {
      this.exceptionError(exception);
      return Response.status(401).entity("{ \"error\": \"" + exception.getMessage() + "\" }").build();
    } else {
      this.exceptionError(exception);
      return Response.status(500).build();
    }
  }
}

What should I do to make AccessDeniedHandler triggered?

EDIT: Here's my configuration. The AccessDeniedHandler bean is declared and well added.

<b:beans xmlns="http://www.springframework.org/schema/security"
         xmlns:b="http://www.springframework.org/schema/beans"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xmlns:util="http://www.springframework.org/schema/util"
         xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd
                http://www.springframework.org/schema/security https://www.springframework.org/schema/security/spring-security.xsd
        http://www.springframework.org/schema/util
        http://www.springframework.org/schema/util/spring-util.xsd">

  <global-method-security pre-post-annotations="enabled" proxy-target-class="true"/>

  <http entry-point-ref="authEntryPoint" create-session="never" >
    <cors configuration-source-ref="corsSource"/>
    <csrf disabled="true"/>
    <custom-filter ref="authFilter" before="PRE_AUTH_FILTER"/>
    <access-denied-handler ref="customAccessDeniedHandler"/>
  </http>

  <authentication-manager alias="authenticationManager">
    <authentication-provider ref="daoAuthenticationProvider"/>
  </authentication-manager>

  <b:bean name="customAccessDeniedHandler"
        class="io.markethero.security.CustomAccessDeniedHandler" />

  <b:bean id="daoAuthenticationProvider" class="org.springframework.security.authentication.dao.DaoAuthenticationProvider">
    <b:property name="userDetailsService"  ref="userLoginService"/>
    <b:property name="passwordEncoder" ref="customizePasswordEncoder"/>
  </b:bean>

  <b:bean id="customizePasswordEncoder" class="io.markethero.security.CustomizePasswordEncoder"/>

  <b:bean id="authFilter" class="io.markethero.security.AuthFilter"/>

  <b:bean id="authEntryPoint" class="io.markethero.security.AuthEntryPoint"/>

  <b:bean id="corsSource" class="org.springframework.web.cors.UrlBasedCorsConfigurationSource">
    <b:property name="corsConfigurations">
      <util:map>
        <b:entry key="/**">
          <b:bean class="org.springframework.web.cors.CorsConfiguration">
            <b:property name="allowCredentials" value="true"/>
            <b:property name="allowedHeaders">
              <util:list>
                <b:value>Authorization</b:value>
                <b:value>Content-Type</b:value>
              </util:list>
            </b:property>
            <b:property name="exposedHeaders">
              <b:list>
                <b:value>Account-Locked</b:value>
                <b:value>Account-Disabled</b:value>
                <b:value>Bad-Credentials</b:value>
              </b:list>
            </b:property>
            <b:property name="allowedMethods">
              <util:list>
                <b:value>POST</b:value>
                <b:value>GET</b:value>
                <b:value>PUT</b:value>
                <b:value>DELETE</b:value>
                <b:value>OPTIONS</b:value>
              </util:list>
            </b:property>
            <b:property name="allowedOrigins" value="*"/>
          </b:bean>
        </b:entry>
      </util:map>
    </b:property>
  </b:bean>


</b:beans>

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

玩世 2025-02-14 18:14:20

在不看到安全配置的情况下,很难确切回答,但我怀疑您尚未注册处理程序吗?假设CustomAccessDeniedHandler是一种称为customAccessDeniedHandler的BEAN,这应该启用它。

@Configuration
public class WebSecurityConfig {

  @Bean
  public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
    // all HttpSecurity configurations here

    // add this
    http.exceptionHandling().accessDeniedHandler(customAccessDeniedHandler);
    return http.build();
  }
}

It's hard to answer exactly without seeing your security configuration, but I suspect that you haven't registered the handler? Assuming that CustomAccessDeniedHandler is a bean called customAccessDeniedHandler, this should enable it.

@Configuration
public class WebSecurityConfig {

  @Bean
  public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
    // all HttpSecurity configurations here

    // add this
    http.exceptionHandling().accessDeniedHandler(customAccessDeniedHandler);
    return http.build();
  }
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文