From 49861f4ad5deca289e414f23dde206b898625e63 Mon Sep 17 00:00:00 2001 From: Eric Zhao Date: Mon, 2 Dec 2019 17:04:06 +0800 Subject: [PATCH] dashboard: Improve authentication and authorization filter Signed-off-by: Eric Zhao --- .../sentinel/dashboard/auth/AuthAction.java | 15 ++++++- ...tor.java => AuthorizationInterceptor.java} | 8 +++- .../LoginAuthenticationFilter.java} | 39 +++++++++++-------- .../sentinel/dashboard/config/WebConfig.java | 30 +++++++++++--- .../gateway/GatewayApiControllerTest.java | 4 +- .../GatewayFlowRuleControllerTest.java | 4 +- 6 files changed, 72 insertions(+), 28 deletions(-) rename sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/auth/{AuthInterceptor.java => AuthorizationInterceptor.java} (93%) rename sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/{filter/AuthFilter.java => auth/LoginAuthenticationFilter.java} (78%) diff --git a/sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/auth/AuthAction.java b/sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/auth/AuthAction.java index 74f9c877..f521c04d 100644 --- a/sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/auth/AuthAction.java +++ b/sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/auth/AuthAction.java @@ -21,14 +21,27 @@ import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; +/** + * @author lkxiaolou + * @since 1.7.1 + */ @Retention(RetentionPolicy.RUNTIME) @Documented @Target({ElementType.METHOD}) public @interface AuthAction { + /** + * @return the privilege type + */ AuthService.PrivilegeType value(); + /** + * @return the target name to control + */ String targetName() default "app"; - String message() default "No privilege"; + /** + * @return the message when permission is denied + */ + String message() default "Permission denied"; } diff --git a/sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/auth/AuthInterceptor.java b/sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/auth/AuthorizationInterceptor.java similarity index 93% rename from sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/auth/AuthInterceptor.java rename to sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/auth/AuthorizationInterceptor.java index 5cfcb706..19472521 100644 --- a/sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/auth/AuthInterceptor.java +++ b/sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/auth/AuthorizationInterceptor.java @@ -27,8 +27,14 @@ import javax.servlet.http.HttpServletResponse; import java.io.IOException; import java.lang.reflect.Method; +/** + * The web interceptor for privilege-based authorization. + * + * @author lkxiaolou + * @since 1.7.1 + */ @Component -public class AuthInterceptor implements HandlerInterceptor { +public class AuthorizationInterceptor implements HandlerInterceptor { @Autowired private AuthService authService; diff --git a/sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/filter/AuthFilter.java b/sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/auth/LoginAuthenticationFilter.java similarity index 78% rename from sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/filter/AuthFilter.java rename to sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/auth/LoginAuthenticationFilter.java index 6a809b9a..f489b48e 100644 --- a/sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/filter/AuthFilter.java +++ b/sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/auth/LoginAuthenticationFilter.java @@ -13,9 +13,8 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -package com.alibaba.csp.sentinel.dashboard.filter; +package com.alibaba.csp.sentinel.dashboard.auth; -import com.alibaba.csp.sentinel.dashboard.auth.AuthService; import org.apache.commons.lang.StringUtils; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Value; @@ -30,39 +29,46 @@ import javax.servlet.ServletRequest; import javax.servlet.ServletResponse; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; + import java.io.IOException; import java.util.List; /** - * Servlet Filter that authenticate requests. - * - * Note: - * Some urls are excluded as they needn't auth, such as: + *

The Servlet filter for authentication.

* - * Index url: / - * Authentication request url: /login,logout - * Used for client: /registry/machine - * Static resources: htm,html,js and so on. + *

Note: some urls are excluded as they needn't auth, such as:

+ *
    + *
  • index url: {@code /}
  • + *
  • authentication request url: {@code /login}, {@code /logout}
  • + *
  • machine registry: {@code /registry/machine}
  • + *
  • static resources
  • + *
* - * The excluded urls and urlSuffixes are configured in application.properties + * The excluded urls and urlSuffixes could be configured in {@code application.properties} file. * * @author cdfive * @since 1.6.0 */ @Component -public class AuthFilter implements Filter { +public class LoginAuthenticationFilter implements Filter { private static final String URL_SUFFIX_DOT = "."; - /**Some urls which needn't auth, such as /auth/login,/registry/machine and so on*/ + /** + * Some urls which needn't auth, such as /auth/login, /registry/machine and so on. + */ @Value("#{'${auth.filter.exclude-urls}'.split(',')}") private List authFilterExcludeUrls; - /**Some urls with suffixes which needn't auth, such as htm,html,js and so on*/ + /** + * Some urls with suffixes which needn't auth, such as htm, html, js and so on. + */ @Value("#{'${auth.filter.exclude-url-suffixes}'.split(',')}") private List authFilterExcludeUrlSuffixes; - /**Authentication using AuthService interface*/ + /** + * Authentication using AuthService interface. + */ @Autowired private AuthService authService; @@ -72,7 +78,8 @@ public class AuthFilter implements Filter { } @Override - public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException { + public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) + throws IOException, ServletException { HttpServletRequest httpRequest = (HttpServletRequest) request; String servletPath = httpRequest.getServletPath(); diff --git a/sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/config/WebConfig.java b/sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/config/WebConfig.java index cd9194c9..f0183430 100755 --- a/sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/config/WebConfig.java +++ b/sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/config/WebConfig.java @@ -16,8 +16,11 @@ package com.alibaba.csp.sentinel.dashboard.config; import com.alibaba.csp.sentinel.adapter.servlet.CommonFilter; -import com.alibaba.csp.sentinel.dashboard.auth.AuthInterceptor; -import com.alibaba.csp.sentinel.dashboard.filter.AuthFilter; +import com.alibaba.csp.sentinel.adapter.servlet.callback.WebCallbackManager; +import com.alibaba.csp.sentinel.dashboard.auth.AuthorizationInterceptor; +import com.alibaba.csp.sentinel.dashboard.auth.LoginAuthenticationFilter; +import com.alibaba.csp.sentinel.util.StringUtil; + import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.beans.factory.annotation.Autowired; @@ -29,6 +32,7 @@ import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry import org.springframework.web.servlet.config.annotation.ViewControllerRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; +import javax.annotation.PostConstruct; import javax.servlet.Filter; /** @@ -40,14 +44,14 @@ public class WebConfig implements WebMvcConfigurer { private final Logger logger = LoggerFactory.getLogger(WebConfig.class); @Autowired - private AuthFilter authFilter; + private LoginAuthenticationFilter loginAuthenticationFilter; @Autowired - private AuthInterceptor authInterceptor; + private AuthorizationInterceptor authorizationInterceptor; @Override public void addInterceptors(InterceptorRegistry registry) { - registry.addInterceptor(authInterceptor).addPathPatterns("/**"); + registry.addInterceptor(authorizationInterceptor).addPathPatterns("/**"); } @Override @@ -77,10 +81,24 @@ public class WebConfig implements WebMvcConfigurer { return registration; } + @PostConstruct + public void doInit() { + // Example: register a UrlCleaner to exclude URLs of common static resources. + WebCallbackManager.setUrlCleaner(url -> { + if (StringUtil.isEmpty(url)) { + return url; + } + if (url.endsWith(".js") || url.endsWith(".css") || url.endsWith("html")) { + return null; + } + return url; + }); + } + @Bean public FilterRegistrationBean authenticationFilterRegistration() { FilterRegistrationBean registration = new FilterRegistrationBean<>(); - registration.setFilter(authFilter); + registration.setFilter(loginAuthenticationFilter); registration.addUrlPatterns("/*"); registration.setName("authenticationFilter"); registration.setOrder(0); diff --git a/sentinel-dashboard/src/test/java/com/alibaba/csp/sentinel/dashboard/controller/gateway/GatewayApiControllerTest.java b/sentinel-dashboard/src/test/java/com/alibaba/csp/sentinel/dashboard/controller/gateway/GatewayApiControllerTest.java index c4d2cb17..9751c831 100644 --- a/sentinel-dashboard/src/test/java/com/alibaba/csp/sentinel/dashboard/controller/gateway/GatewayApiControllerTest.java +++ b/sentinel-dashboard/src/test/java/com/alibaba/csp/sentinel/dashboard/controller/gateway/GatewayApiControllerTest.java @@ -15,7 +15,7 @@ */ package com.alibaba.csp.sentinel.dashboard.controller.gateway; -import com.alibaba.csp.sentinel.dashboard.auth.AuthInterceptor; +import com.alibaba.csp.sentinel.dashboard.auth.AuthorizationInterceptor; import com.alibaba.csp.sentinel.dashboard.auth.FakeAuthServiceImpl; import com.alibaba.csp.sentinel.dashboard.client.SentinelApiClient; import com.alibaba.csp.sentinel.dashboard.datasource.entity.gateway.ApiDefinitionEntity; @@ -61,7 +61,7 @@ import static org.mockito.BDDMockito.*; */ @RunWith(SpringRunner.class) @WebMvcTest(GatewayApiController.class) -@Import({FakeAuthServiceImpl.class, InMemApiDefinitionStore.class, AppManagement.class, SimpleMachineDiscovery.class, AuthInterceptor.class}) +@Import({FakeAuthServiceImpl.class, InMemApiDefinitionStore.class, AppManagement.class, SimpleMachineDiscovery.class, AuthorizationInterceptor.class}) public class GatewayApiControllerTest { private static final String TEST_APP = "test_app"; diff --git a/sentinel-dashboard/src/test/java/com/alibaba/csp/sentinel/dashboard/controller/gateway/GatewayFlowRuleControllerTest.java b/sentinel-dashboard/src/test/java/com/alibaba/csp/sentinel/dashboard/controller/gateway/GatewayFlowRuleControllerTest.java index b3ffce83..b9c2353e 100644 --- a/sentinel-dashboard/src/test/java/com/alibaba/csp/sentinel/dashboard/controller/gateway/GatewayFlowRuleControllerTest.java +++ b/sentinel-dashboard/src/test/java/com/alibaba/csp/sentinel/dashboard/controller/gateway/GatewayFlowRuleControllerTest.java @@ -15,7 +15,7 @@ */ package com.alibaba.csp.sentinel.dashboard.controller.gateway; -import com.alibaba.csp.sentinel.dashboard.auth.AuthInterceptor; +import com.alibaba.csp.sentinel.dashboard.auth.AuthorizationInterceptor; import com.alibaba.csp.sentinel.dashboard.auth.FakeAuthServiceImpl; import com.alibaba.csp.sentinel.dashboard.client.SentinelApiClient; import com.alibaba.csp.sentinel.dashboard.datasource.entity.gateway.GatewayFlowRuleEntity; @@ -65,7 +65,7 @@ import static org.mockito.BDDMockito.*; @RunWith(SpringRunner.class) @WebMvcTest(GatewayFlowRuleController.class) @Import({FakeAuthServiceImpl.class, InMemGatewayFlowRuleStore.class, AppManagement.class, SimpleMachineDiscovery.class, - AuthInterceptor.class }) + AuthorizationInterceptor.class }) public class GatewayFlowRuleControllerTest { private static final String TEST_APP = "test_app";