RedisTemplate 无法注入的几种场景,以及解决方法;

场景一 : 拦截器中

原因: 
 

Spring框架中的拦截器是在容器启动时就进行实例化的;

在Spring框架中,拦截器的实例化和配置是通过拦截器配置类(Interceptor Configuration Class)完成的。拦截器配置类是一个专门用于配置拦截器的类,通常使用@Configuration注解进行标记。

在拦截器配置类中,可以使用@Bean注解来创建拦截器的实例,并进行配置。这样一来,拦截器就成为了Spring容器中的一个Bean,可以由Spring管理。

当容器启动时,会读取拦截器配置类,并实例化其中的拦截器Bean。这意味着拦截器可以在容器启动之后的任何时候被使用,而不需要等待Bean实例化。

因此,通过在拦截器配置类中实例化拦截器,并将其纳入Spring容器的管理,可以确保在需要时拦截器可以被正确地使用,并且可以进行依赖注入等操作。

解决方法:

@Configuration
public class WebMvcConfig implements WebMvcConfigurer {

    /**实例化拦截器  创建拦截器的实例*/

    @Bean
    public UserLoginInterceptor getUserLoginInterceptor() {
        return new UserLoginInterceptor();
    }

    /**
     * 注册自定义拦截器
     * @param registry ·
     */

    String[] strs =  new String[]{
            "/error",
            "/IM/login/**"

    };

    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(getUserLoginInterceptor())
                .addPathPatterns("/**") // 拦截地址
                .excludePathPatterns(strs);// 开放登录路径
    }

}

场景二: 在非Spring管理的类中获取Spring容器中的Bean

比如再Netty中,以及一些工具类中

原因:

在非Spring管理的类中获取Spring容器中的Bean

解决方法:

1. 先创建一个SpringUtils的类; 通过这个类拿到Spring中的bean;

@Repository
public class SpringUtils implements BeanFactoryPostProcessor {
 
    //Spring应用上下文环境
    private static ConfigurableListableBeanFactory beanFactory;
 
    @Override
    public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException {
        SpringUtils.beanFactory = beanFactory;
    }
 
    public static ConfigurableListableBeanFactory getBeanFactory() {
        return beanFactory;
    }
 
    /**
     * 获取对象
     *
     * @param name
     * @return Object 一个以所给名字注册的bean的实例
     * @throws org.springframework.beans.BeansException
     *
     */
    @SuppressWarnings("unchecked")
    public static <T> T getBean(String name) throws BeansException {
        return (T) getBeanFactory().getBean(name);
    }
 
    /**
     * 获取类型为requiredType的对象
     *
     * @param clz
     * @return
     * @throws org.springframework.beans.BeansException
     *
     */
    public static <T> T getBean(Class<T> clz) throws BeansException {
        T result = (T) getBeanFactory().getBean(clz);
        return result;
    }
 
    /**
     * 如果BeanFactory包含一个与所给名称匹配的bean定义,则返回true
     *
     * @param name
     * @return boolean
     */
    public static boolean containsBean(String name) {
        return getBeanFactory().containsBean(name);
    }
 
    /**
     * 判断以给定名字注册的bean定义是一个singleton还是一个prototype。 如果与给定名字相应的bean定义没有被找到,将会抛出一个异常(NoSuchBeanDefinitionException)
     *
     * @param name
     * @return boolean
     * @throws org.springframework.beans.factory.NoSuchBeanDefinitionException
     *
     */
    public static boolean isSingleton(String name) throws NoSuchBeanDefinitionException {
        return getBeanFactory().isSingleton(name);
    }
 
    /**
     * @param name
     * @return Class 注册对象的类型
     * @throws org.springframework.beans.factory.NoSuchBeanDefinitionException
     *
     */
    public static Class<?> getType(String name) throws NoSuchBeanDefinitionException {
        return getBeanFactory().getType(name);
    }
 
    /**
     * 如果给定的bean名字在bean定义中有别名,则返回这些别名
     *
     * @param name
     * @return
     * @throws org.springframework.beans.factory.NoSuchBeanDefinitionException
     *
     */
    public static String[] getAliases(String name) throws NoSuchBeanDefinitionException {
        return getBeanFactory().getAliases(name);
    }
}

2. 在非Spring类中这样注入:

private StringRedisTemplate stringRedisTemplate = SpringUtils.getBean(StringRedisTemplate.class);

原理:

SpringUtils实现了BeanFactoryPostProcessor接口,这是Spring框架提供的一个扩展点接口。通过实现该接口,SpringUtils可以在Spring容器加载Bean定义后,在Bean实例化之前对BeanFactory进行后置处理。

这个类的主要目的是提供一些静态方法,用于方便地访问和操作Spring容器中的BeanFactory。下面是一些主要方法的解释:

  • postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory): 这个方法是BeanFactoryPostProcessor接口的实现方法。在Spring容器加载Bean的定义后,会调用该方法,并传入beanFactory作为参数。SpringUtils将这个beanFactory赋值给自己的静态变量beanFactory,以便后续的静态方法可以使用它。

  • getBeanFactory(): 这个静态方法返回beanFactory,即Spring容器中的BeanFactory实例。其他静态方法可以通过调用这个方法来获取BeanFactory实例。

  • getBean(String name): 这个静态方法用于根据给定的名称获取对应的Bean实例。它通过调用getBeanFactory().getBean(name)来实现,在Spring容器中查找并返回匹配名称的Bean实例。

  • getBean(Class<T> clz): 这个静态方法用于根据给定的类型获取对应的Bean实例。它通过调用getBeanFactory().getBean(clz)来实现,在Spring容器中查找并返回匹配类型的Bean实例。

  • 其他方法,如containsBean(String name)isSingleton(String name)getType(String name)getAliases(String name),提供了一些额外的功能,用于判断Bean是否存在、获取Bean的类型和别名等。

通过使用SpringUtils类,可以在任何需要访问Spring容器中的Bean的地方,方便地获取和操作Bean实例。

  • 22
    点赞
  • 11
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
您好!对于Spring Boot中的RedisTemplate无法注入的问题,有几个常见的原因和解决方法可以尝试: 1. 确保Redis依赖已添加:在`pom.xml`文件中,确保已经添加了Redis相关的依赖,例如`spring-boot-starter-data-redis`。 2. 检查配置:在应用的配置文件(如`application.properties`或`application.yml`)中,确保已正确配置了Redis连接信息,包括主机名、端口号、密码等。例如: ``` spring.redis.host=localhost spring.redis.port=6379 spring.redis.password=your_password ``` 3. 检查注入方式:确保您正在使用`@Autowired`注解将RedisTemplate注入到您的类中。例如: ```java @Autowired private RedisTemplate<String, Object> redisTemplate; ``` 4. 确认RedisTemplate泛型参数:如果您在配置RedisTemplate时指定了泛型参数,请确保与实际使用的数据类型匹配。例如,如果您要使用字符串作为键,对象作为值,则可以这样配置: ```java @Bean public RedisTemplate<String, Object> redisTemplate(RedisConnectionFactory redisConnectionFactory) { RedisTemplate<String, Object> redisTemplate = new RedisTemplate<>(); redisTemplate.setConnectionFactory(redisConnectionFactory); redisTemplate.setKeySerializer(new StringRedisSerializer()); redisTemplate.setValueSerializer(new Jackson2JsonRedisSerializer<>(Object.class)); return redisTemplate; } ``` 这些是常见的解决方法,您可以根据具体情况进行尝试。如果问题仍然存在,请提供更多的详细信息,例如错误日志或代码片段,以便更好地帮助您解决问题。
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值