关于spring:spring泛型注入

41次阅读

共计 2771 个字符,预计需要花费 7 分钟才能阅读完成。

泛型依赖注入
Spring 4.0 版本中更新了很多新性能,其中比拟重要的一个就是对带泛型的 Bean 进行依赖注入的反对。
泛型依赖注入容许咱们在应用 spring 进行依赖注入的同时,利用泛型的长处对代码进行精简,同时在不减少代码的状况下减少代码的复用性。
Spring 默认依照字段的类进行依赖注入,而 Spring4 的新个性就是把泛型的具体类型也作为类的一种分类办法(Qualifier)。

背景
假如有两个实体类 Student 和 Teacher

@Data
public class Student implements IEntity{

private long id;

}

@Data
public class Teacher implements IEntity{

private long id;

}
实体的存储,是通过仓储操作的,个别所有的实体仓储办法都是统一的,只有具体的实体类型不一样,定义仓储接口

public interface IRepository<TEntity extends IEntity>{

void add(TEntity entity);
List<TEntity> findAll();


}
定义仓储实现的基类,在本例中,应用 List 存储

public abstract class BaseRepository <TEntity extends IEntity> implements IRepository<TEntity>{

List<TEntity> datasource = new ArrayList<>();
@Override
public void add(TEntity entity){this.datasource.add(entity);
}

@Override
public List<TEntity> findAll(){return datasource;}

}
泛型依赖注入的 Bean
BaseRepository 是一个抽象类,不合适注入到 spring 中,定义一个能够注入的 bean

@Repository()
@Scope(“prototype”)
public class DefaultRepository<TEntity extends IEntity> extends BaseRepository<TEntity>{
}
留神 @Scope(“prototype”)注解,示意 DefaultRepository 的 bean 的作用是瞬态的,每次获取 bean 时都会创立一个新的 bean,如果不增加作用域,默认 spring 的 bean 是单例的,这样注入的仓储实例会是同一个实例。
在 test 中依赖注入 @Autowired IRepository<Student> studentRepository; 和 @Autowired IRepository<Teacher> teacherRepository;,
验证这两个仓储的类型都是 DefaultRepository 类型,同时验证操作 student 不会影响到 teacher。

@ExtendWith(SpringExtension.class)
@ContextConfiguration(

    classes = {DemoTests.DemoTestsConfiguration.class})

public class DemoTests {

@Autowired
IRepository<Student> studentRepository;

@Autowired
IRepository<Teacher> teacherRepository;

@Test
public void test(){assertThat(studentIRepository.getClass())
            .isEqualTo(DefaultRepository.class);
    assertThat(teacherIRepository.getClass())
            .isEqualTo(DefaultRepository.class);

    studentIRepository.add(new Student());

    assertThat(studentIRepository.findAll())
            .hasSize(1);

    assertThat(teacherIRepository.findAll())
            .hasSize(0);
}



@ComponentScan({"org.example"})
@Configuration
public static class DemoTestsConfiguration {
}

}

仓储扩大
在上一部分,所有的仓储操作,都定义在了 BaseRepository 中,如果遇到了仓储中未提供的办法,则须要对单个实体的仓储进行扩大。
自定义仓储接口,继承自 IRepository<Student>

public interface IStudentRepository extends IRepository<Student>{

Student findById(long id);

}
实现自定义仓储接口

@Repository
public class StudentRepository extends BaseRepository<Student> implements IStudentRepository {

@Override
public Student findById(long id) {return null;}

}
应用例子如下

@ExtendWith(SpringExtension.class)
@ContextConfiguration(

    classes = {DemoTests.DemoTestsConfiguration.class})

public class DemoTests {

@Autowired
IRepository<Teacher> teacherRepository;

@Autowired
IStudentRepository studentRepository;

@Test
public void repositoryType(){assertThat(studentRepository.getClass())
            .isEqualTo(StudentRepository.class);
    assertThat(teacherRepository.getClass())
            .isEqualTo(DefaultRepository.class);
}



@ComponentScan({"org.example"})
@Configuration
public static class DemoTestsConfiguration {
}

}

总结
应用泛型依赖注入,能够缩小反复代码和类的数目,在本例中,无需对 Student 和 Teacher 两个实体定义仓储接口和实现,应用对立的仓储接口和默认实现即可实现大部分的操作。

正文完
 0