Heim  >  Artikel  >  Java  >  Wie SpringBoot das Abfangen von Anmeldungen über ThreadLocal implementiert

Wie SpringBoot das Abfangen von Anmeldungen über ThreadLocal implementiert

WBOY
WBOYnach vorne
2023-05-22 12:04:421390Durchsuche

    1 Vorwort

    Registrierung und Anmeldung sind die häufigsten Dinge in der täglichen Entwicklung, im Allgemeinen jedoch nach der Eingabe Das Unternehmen hat solche Funktionen schon vor langer Zeit entwickelt, es sei denn, es handelt sich um ein neues Projekt. In den letzten zwei Tagen hatte ich zufällig die Notwendigkeit, die Registrierungs- und Anmeldefunktion auf der PC-Seite abzuschließen.

    Es gibt viele Möglichkeiten, eine solche Anforderung zu erfüllen: wie

    1) HandlerInterceptor+WebMvcConfigurer+ThreadLocal

    2) Filter filter

    3) Sicherheits-Framework Shiro (leichtes Framework)

    4) Sicherheits-Framework Spring Securety (schweres Framework)

    Und ich verwende das erste, Spring HandlerInterceptor+WebMvcConfigurer+ ThreadLocal-Technologie ist implementiert.

    2 Konkrete Klasse

    2.1HandlerInterceptor

    HandlerInterceptor ist die Schnittstelle, die für Interceptoren in SpringMVC bereitgestellt wird, ähnlich dem Filter Filter in der Servlet-Entwicklung und Nachbearbeitung durch den Prozessor müssen drei Methoden neu geschrieben werden.

    preHandle:

    Aufrufzeit: vor Verarbeitung der Controller-Methode

    Ausführungsreihenfolge: Bei verketteten Interceptern werden die Intercepter nacheinander ausgeführt in der Reihenfolge der Deklaration.

    Wenn false zurückgegeben wird, wird die Ausführung unterbrochen. Hinweis: Es wird nicht nach Abschluss eingegeben.

    postHandle:

    Aufrufvoraussetzung: preHandle gibt true zurück

    Aufrufzeit: Nach der Verarbeitung der Controller-Methode, bevor DispatcherServlet die Ansicht rendert, d. h. ModelAndView kann in dieser Methode betrieben werden

    Ausführungsreihenfolge: Im Fall eines verketteten Interceptors folgt der Intercepter der Deklaration der sequentiellen Ausführung

    Bemerkungen: Obwohl postHandle mit post beginnt, können Post-Anfragen und Get-Anfragen

    afterCompletion verarbeitet werden :

    Aufrufvoraussetzung: preHandle Return true

    Aufrufzeit: nachdem DispatcherServlet die Ansicht gerendert hat

    Wird hauptsächlich zum Bereinigen von Ressourcen verwendet

    # 🎜🎜#2.2WebMvcConfigurer

    WebMvcConfigurer Die Konfigurationsklasse ist eigentlich die

    Schnittstelle;

    Spring内部的一种配置方式,采用JavaBean的形式来代替传统的xml配置文件形式进行针对框架个性化定制,可以自定义一些Handler,Interceptor,ViewResolver,MessageConverter。基于java-based方式的spring mvc配置,需要创建一个配置类并实现WebMvcConfigurer In Spring Boot Version 1.5 wird die Methode zum Umschreiben von WebMvcConfigurerAdapter verwendet, um benutzerdefinierte hinzuzufügen Abfangjäger, Nachrichtenkonverter usw. Nach der SpringBoot-Version 2.0 wurde diese Klasse als @Deprecated (veraltet) markiert. Die offizielle Empfehlung besteht darin, WebMvcConfigurer direkt zu implementieren oder WebMvcConfigurationSupport direkt zu erben. Methode eins implementiert die WebMvcConfiguration-Schnittstelle (empfohlen) und Methode zwei erbt die WebMvcConfigurationSupport-Klasse

    3 Codepraxis

    1 ) Schreiben Sie den Interceptor HeadTokenInterceptor, um ihn zu verwenden. Er erbt HandlerInterceptor

    package com.liubujun.config;
    import com.liubujun.moudle.UserToken;
    import com.liubujun.util.SecurityContextUtil;
    import lombok.extern.slf4j.Slf4j;
    import org.springframework.http.HttpStatus;
    import org.springframework.stereotype.Component;
    import org.springframework.util.StringUtils;
    import org.springframework.web.servlet.HandlerInterceptor;
    import org.springframework.web.servlet.ModelAndView;
    import javax.servlet.http.HttpServletRequest;
    import javax.servlet.http.HttpServletResponse;
    import javax.xml.ws.handler.Handler;
    import java.io.IOException;
    /**
     * @Author: liubujun
     * @Date: 2022/5/21 16:12
     */
    @Component
    @Slf4j
    public class HeadTokenInterceptor implements HandlerInterceptor {
        @Override
        public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
            String authorization = request.getHeader("Authorization");
            if (authorization == null ) {
                unauthorized(response);
                return false;
            }
            //这里一般都会解析出userToken的值,这里为了方便就直接new了
            UserToken userToken  = new UserToken();
            SecurityContextUtil.addUser(userToken);
            return false;
        }
        @Override
        public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
        }
        @Override
        public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
            SecurityContextUtil.removeUser();
        }
        private void unauthorized(HttpServletResponse response) {
            response.setStatus(HttpStatus.UNAUTHORIZED.value());
            try {
                response.getWriter().append(HttpStatus.UNAUTHORIZED.getReasonPhrase());
            } catch (IOException e) {
                log.error("HttpServletResponse writer error.msg",HttpStatus.UNAUTHORIZED.getReasonPhrase());
                log.error(e.getMessage(),e);
            }
        }
    }

    2) Schreiben Sie MyWebMvcConfigurer, um WebMvcConfigurationSupport

    package com.liubujun.config;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.context.annotation.Configuration;
    import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
    import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry;
    import org.springframework.web.servlet.config.annotation.WebMvcConfigurationSupport;
    import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
    import java.util.ArrayList;
    /**
     * @Author: liubujun
     * @Date: 2022/5/21 16:40
     */
    @Configuration
    public class MyWebMvcConfigurer extends WebMvcConfigurationSupport {
        @Autowired
        private HeadTokenInterceptor headTokenInterceptor;
        /**
         * 类似于白名单,在这边添加的请求不会走拦截器
         * @param registry
         */
        @Override
        public void addInterceptors(InterceptorRegistry registry) {
            ArrayList<String> pattres = new ArrayList<>();
            pattres.add("/login/login");
            registry.addInterceptor(headTokenInterceptor).excludePathPatterns(pattres).addPathPatterns("/**");
            super.addInterceptors(registry);
        }
        /**
         * 添加静态资源
         * @param registry
         */
        @Override
        public void addResourceHandlers(ResourceHandlerRegistry registry) {
            registry.addResourceHandler("xxx.html")
                    .addResourceLocations("classpath:/META-INF/resources");
            super.addResourceHandlers(registry);
        }
    }

    3) Schreiben Sie die ThreadLocal-Klasse, um Benutzerinformationen zu speichern ee

    4) Schreiben Sie einen Testcontroller

    package com.liubujun.util;
    import com.liubujun.moudle.UserToken;
    import org.springframework.core.NamedThreadLocal;
    /**
     * @Author: liubujun
     * @Date: 2022/5/23 9:41
     */
    public class SecurityContextUtil {
        private static ThreadLocal<UserToken> threadLocal = new NamedThreadLocal<>("user");
        public static void addUser(UserToken user){
            threadLocal.set(user);
        }
        public static UserToken getUser(){
            return threadLocal.get();
        }
        public static void removeUser(){
            threadLocal.remove();
        }
        public static String getPhoneNumber(){
            return threadLocal.get().getPhoneNumber();
        }
        public static Integer getId(){
            return threadLocal.get().getId();
        }
        public static String getUserText(){
            return threadLocal.get().getUserText();
        }
    }

    5) Testen Sie

    Testen Sie die Anmeldeschnittstelle (geben Sie sie direkt frei, ohne das Token zu übergeben)

    #🎜 🎜#

    #🎜 🎜#Testen Sie andere Schnittstellen. Wenn das Token nicht übertragen wird, wird es abgefangen

    Wie SpringBoot das Abfangen von Anmeldungen über ThreadLocal implementiert

    Das obige ist der detaillierte Inhalt vonWie SpringBoot das Abfangen von Anmeldungen über ThreadLocal implementiert. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!

    Stellungnahme:
    Dieser Artikel ist reproduziert unter:yisu.com. Bei Verstößen wenden Sie sich bitte an admin@php.cn löschen