なぜあなたが書いたブロッキングはJava beanに注入できないのですか?


一、遮断器の実現方法
Spring Bootプロジェクトでは、ブロッキングはログイン検証、ログ記録などの操作によく使用されます.インターセプターはSpringが提供しているので、インターセプターをbeanにしてIOC容器で管理することができます.ブロッキングを実現する方法は簡単で、主に以下の2つのステップから構成されています.
  • カスタムブロッキングクラス実装HandlerInterceptorインタフェース
  • カスタムWebMvc構成クラスWebMvcConfigurerインタフェースを実現し、カスタムブロッキングクラス
  • を追加する.
    簡単な実装コードは次のとおりです.
    カスタムブロッキングLoginInterceptor:
    public class LoginInterceptor implements HandlerInterceptor {
    
        @Override
        public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
    
            String token = request.getHeader("token");
            if(StringUtils.isEmpty(token)){
                 ...
                return false;
            }
            return true;
        }
    }

    カスタムブロッキングの設定:
    @Configuration
    public class WebConfiguration implements WebMvcConfigurer {
    
        @Override
        public void addInterceptors(InterceptorRegistry registry) {
            registry.addInterceptor(new LoginInterceptor())
                    //      
                    .addPathPatterns("/**")
                    //        
                    .excludePathPatterns("/login");
        }
    }

    このブロッカーの主な役割は、すべてのアクセス要求をブロックし、帯域tokenが有効であるかどうかを検証することです.tokenの検証に成功した後、ビジネスインタフェースにアクセスできます.この場合、tokenの有効性を検証するインタフェースを提供する必要があり、tokenをブロッカーで検証する必要がある.ブロッカーはSpringが提供するので、@Component注釈を使用してブロッカーをbeanに注入することは容易に考えられる.次いで、@Autowired注釈を使用して、検証tokenのクラスをブロッカーに注入して検証する.
    改造されたコードは以下の通りです.
    tokenインタフェースクラスの検証:
    @Component
    public class TokenUtil {
        /**
         *   token     
         */
        public boolean checkToken(String token){
            ...
        }
    }

    改造されたブロッキングコードは以下の通りです.
    @Component
    public class LoginInterceptor implements HandlerInterceptor {
    
        @Autowired
        private TokenUtil tokenUtil;
    
        @Override
        public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
            if(!tokenUtil.checkToken(token)){
                ...
                return false;
            }
            return true;
        }
    }

    インタフェースを呼び出すと、TokenUtilは注入されていません!コードは大丈夫なのに、なぜTokenUtilを正常に注入できないのですか?
    カスタマイズされたコンフィギュレーションクラスWebConfigurationをよく観察すると、ブロッキングを追加するときに使用されるのはnew LoginInterceptor()で、ブロッキングを有効にするには、WebMvcのコンフィギュレーションクラスにブロッキングを構成する必要があります.これは、カスタマイズされたWebConfigurationクラスです.現在、インターセプターを追加したのはnewのインターセプターで、つまりインターセプターをIOCコンテナに預けていないのでSpringのbeanオブジェクトを導入することはできません.
    二、インターセプターをIOC容器に預ける方法
    問題解決の構想も簡単で、インターセプターもIOC容器に預け、容器内の対象を互いに注入することができる.これらの問題を処理するには、以下の3つの方法があります.
    2.1 WebConfigurationにブロッカーを注入する
    ブロッキングコードは変更されず、ブロッキングに@Componentを使用し、WebConfiguration@Autowired注釈を使用してブロッキングを注入する.
    ブロッキングコード:
    @Component
    public class LoginInterceptor implements HandlerInterceptor {
    }

    クラスコードの構成:
    @Configuration
    public class WebConfiguration implements WebMvcConfigurer {
    
        @Autowired
        private LoginInterceptor loginInterceptor;
    
        @Override
        public void addInterceptors(InterceptorRegistry registry) {
            registry.addInterceptor(loginInterceptor);
        }
    }

    2.2遮断器をWebConfigurationでbeanに注ぐ
    ブロッキングは、@Component注釈を追加する必要はなく、WebConfigurationクラスにおいて@Bean注釈を使用してブロッキングをbeanに注釈する.
    ブロッキングコード:
    public class LoginInterceptor implements HandlerInterceptor {
    }

    クラスコードの構成:
    @Configuration
    public class WebConfiguration implements WebMvcConfigurer {
    
        @Bean
        public LoginInterceptor loginInterceptor(){
            return new LoginInterceptor();
        }
    
        @Override
        public void addInterceptors(InterceptorRegistry registry) {
            registry.addInterceptor( loginInterceptor());
        }
    }

    2.3コンストラクタ処理によるWebConfigurationクラスに必要な検証tokenのビジネスクラスを注入し、ブロッキングを初期化するときにコンストラクタを介してブロッキングにビジネスクラスを持ち込むことで、ブロッキングをSpring Beanオブジェクトに注ぐ必要がなくなります.
    ブロッキングコード:
    public class LoginInterceptor implements HandlerInterceptor {
    
        private TokenUtil tokenUtil;
    
        public LoginInterceptor(TokenUtil tokenUtil) {
            this.tokenUtil = tokenUtil;
        }
    }

    クラスコードの構成:
    @Configuration
    public class WebConfiguration implements WebMvcConfigurer {
    
        @Autowired
        private TokenUtil tokenUtil;
    
        @Override
        public void addInterceptors(InterceptorRegistry registry) {
            registry.addInterceptor(new LoginInterceptor(tokenUtil));
        }
    }

    三、まとめ
    ネット上のブロッキングに関するコードは基本的にnewの1つのブロッキングで構成されており、この場合他のbeanを注入できない場合があります.多くの人は当然、遮断器に@Componentを加えてbeanオブジェクトになるように注釈したいと思っています.これは間違ったやり方だ.WebMvc構成クラスに追加されたブロッカーがSpringのbeanオブジェクトであることを保証する必要があります.つまり、ブロッカーをbeanに注ぎ込み、このbeanが追加されたWebMvc構成クラスに追加する必要があります.
    四、注意して、道に迷わない
    もし文章がいいと思ったら、注目して、ほめて、コレクションを歓迎して、あなた达の支持は私の創作の動力で、みんなに感謝します.
    もし文章に問題があれば、文章を惜しまないでください.伝言を歓迎します.私はすぐにチェックして修正します.
    他にも見たいものがあれば、微信で「Java旅」を検索して注目することができます.「Java旅路」は現在、各種ミドルウェアの使用チュートリアルや各種Java関連の面接問題を整理している.