11 Spring 高级注解编程二

11 Spring 高级注解编程

一,使用注解开发AOP

1.AOP开发的基本要素

根据之前的总结,动态代理开发有以下要素

  • 原始对象
  • 额外功能
  • 切入点

那么在注解开发中,其中额外功能和切入点整合为了一个类

对注解开发AOP的总体描述:提供原始对象和切面类之后由配置Bean整合使用

2.开发步骤

1.提供原始对象

​ 需要提供@Component及其衍生注解来创建出这个类提供给切面类

    @Service
    public class UserServiceImpl implements UserService {
        @Override
        public void register() {
            System.out.println("UserServiceImpl.register");
        }

        @Override
        public void login(String name, String password) {
            System.out.println("UserServiceImpl.login");
        }
    }

2.切面类开发

​ 要提供@Aspect注解指明这是切面类

​ 同样需要提供@Component创建代理类

​ 使用 @Around提供切入点表达式

​ 其余实现和之前的一致

    @org.aspectj.lang.annotation.Aspect
    @Component
    public class Aspect {
        @Around("execution(* *(..))")
        public Object Arround(ProceedingJoinPoint proceedingJoinPoint) throws Throwable {
            System.out.println("Aspect.Arround");
            Object ret=proceedingJoinPoint.proceed();
            return  ret;
        }
    }

3.配置Bean的开发

​ 必须指明了切面类和原始对象所在的地方然后才能被配置Bean创建出来

​ @EnableAspectJAutoProxy指明自动扫描代理,等同于配置文件的<aop:aspectj-autoproxy />

    @Configuration
    @ComponentScan(basePackages = "org.AnnotationProgramming.AOP")
    @EnableAspectJAutoProxy
    public class Appconfig_Aop {

    }

4.运行

​ 获取配置Bean的信息即可

    @Test
    //测试注解开发AOP
    public void test14() {
        ApplicationContext context = new AnnotationConfigApplicationContext(Appconfig_Aop.class);
        UserService userService= (UserService) context.getBean("userServiceImpl");
        userService.register();
        userService.login("SY","123");
    }

效果:

    Aspect.Arround
    UserServiceImpl.register
    Aspect.Arround
    UserServiceImpl.login

注意:不需要再次在配置Bean中编写创建原始对象的方法了

二,使用注解整合Mybatis

和之前的整合流程一致,只不过是变换成了注解

整合代码如下:

使用配置文件解决了耦合

@Configuration
@ComponentScan(basePackages = "")
@MapperScan(basePackages = "")
public class MyBatisAutoConfiguration {

    @Autowired
    private MybatisProperties mybatisProperties;
	//连接池
    @Bean
    public DataSource dataSource() {
        DruidDataSource dataSource = new DruidDataSource();
        dataSource.setDriverClassName(mybatisProperties.getDriverClassName());
        dataSource.setUrl(mybatisProperties.getUrl());
        dataSource.setUsername(mybatisProperties.getUsername());
        dataSource.setPassword(mybatisProperties.getPassword());
        return dataSource;
    }
	//sqlsession的创建
    @Bean
    public SqlSessionFactoryBean sqlSessionFactoryBean(DataSource dataSource) {
        SqlSessionFactoryBean sqlSessionFactoryBean = new SqlSessionFactoryBean();
        sqlSessionFactoryBean.setDataSource(dataSource);
        //一组Mapper文件
        sqlSessionFactoryBean.setTypeAliasesPackage(mybatisProperties.getTypeAliasesPackages());
        //一个Mapper文件
        //sqlSessionFactoryBean.setMapperLocations(new ClassPathResource("UserDAOMapper.xml"));
        try {
            ResourcePatternResolver resolver = new PathMatchingResourcePatternResolver();
            Resource[] resources = resolver.getResources(mybatisProperties.getMapperLocations());
            sqlSessionFactoryBean.setMapperLocations(resources);
        } catch (IOException e) {
            e.printStackTrace();
        }

        return sqlSessionFactoryBean;
    }
}

注意点:MapperLocations编码时通配的写法

​ 依然可以使用/*Mapper.xml表示一个文件夹下面的所有Mapper文件

mybatisProperties代码如下(省略了SET/GET方法):


@Component
@PropertySource("classpath:mybatis.properties")
public class MybatisProperties {
    @Value("${mybatis.driverClassName}")
    private String driverClassName;
    @Value("${mybatis.url}")
    private String url;
    @Value("${mybatis.username}")
    private String username;
    @Value("${mybatis.password}")
    private String password;
    @Value("${mybatis.typeAliasesPackages}")
    private String typeAliasesPackages;
    @Value("${mybatis.mapperLocations}")
    private String mapperLocations;
}

三,使用注解开发事务

事务开发时使用aop开发的所以需要:

  • 原始对象

    并标注上@Transactional注解

    ​ 事务属性就在这里指定

    @Service
    @Transactional
    public class UserServiceImpl implements UserService {
    
        @Autowired
        private UserDAO userDAO;
    
        public UserDAO getUserDAO() {
            return userDAO;
        }
    
        public void setUserDAO(UserDAO userDAO) {
            this.userDAO = userDAO;
        }
    
        @Override
        public void register(User user) {
            userDAO.save(user);
        }
    }
    
  • 事务额外功能

    需要加上@EnableTransactionManagement

@Configuration
@EnableTransactionManagement
public class TransactionAutoConfiguration {
    @Autowired
    private DataSource dataSource;
    //此处只是作为演示不必看内容
    @Bean
    public DataSourceTransactionManager dataSourceTransactionManager() {
        DataSourceTransactionManager dataSourceTransactionManager = new DataSourceTransactionManager();
        dataSourceTransactionManager.setDataSource(dataSource);
        return dataSourceTransactionManager;
    }
}

四,Spring5中YML的使用

1.YML是什么

​ YAML不是一种标记语言,通常以.yml,.yaml为后缀的文件,是一种直观的能够被电脑识别的数据序列化格式,并且容易被人类阅读,容易和脚本语言交互的,可以被支持YAML库的不同的编程语言程序导入,一种专门用来写配置文件的语言。

2.YML语法

  • 大小写敏感
  • 松散表示,java中对于驼峰命名法,可用原名或使用-代替驼峰,如java中的lastName属性,在yml中使用lastName或 last-name都可正确映射。
1.基本语法
	k: v 表示键值对关系,冒号之后有一个空格
	例如:
	id: 32
	name: SY
	password: 123456
2.对象语法,或者是Map语法
	使用空格的缩进表示层级关系,只要是左对齐的一列数据,都是同一个对象的
	缩进时不允许使用Tab键,只允许使用空格
	例如:
	Info:
	 id: 32
	 name: SY
	 password: 123456
	表示为一行为(元素依然带有空格):
	Info: {id: 32,name: SY,password: 123456}
3.数组,集合,list,set
	用- 值表示数组中的一个元素
	例如:
	Info:
	 -32
	 -SY
	 -123456
	 表示为一行为
	 Info:[32,SY,123456]
4.数组对象,list对象,set对象
	Info:
	 - id: 32
	   name: SY
	   password: 123456
	 - id: 0
       name: SYS
       password: 123
     - {id: 32,name: SY,password: 123456}

3.Java中使用

1.处理集合问题

YML内容如下:

	Arrays:  'A,B,C'

java处理如下:

​ 使用#而不是处理properties的$,使用split分割

 	@Value("#{'${arrays}'.split(',')}")
    private String[] arrays;

2.处理普通的注入

YML内容如下:

id: 1

java处理如下:

 @Value("#{'${id}')
 private Integerid;

4.Spring和YML的整合

1.配置MAVEN

版本需要在1.18以上

<!-- https://mvnrepository.com/artifact/org.yaml/snakeyaml -->
<dependency>
    <groupId>org.yaml</groupId>
    <artifactId>snakeyaml</artifactId>
    <version>1.29</version>
</dependency>

2.配置读取YML的工具

​ 由于Spring无法直接读取YML所以需要把YML变为properties形式

@Bean
public PropertySourcesPlaceholderConfigurer configurer(){
    //配置yamlPropertiesFactoryBean读取YML文件
    YamlPropertiesFactoryBean yamlPropertiesFactoryBean=new YamlPropertiesFactoryBean();
    yamlPropertiesFactoryBean.setResources(new ClassPathResource("init.yml"));
    //使得Properties对象拿到转变的YML文件
    Properties properties =yamlPropertiesFactoryBean.getObject();
    //读取Properties文件
    PropertySourcesPlaceholderConfigurer configurer =new PropertySourcesPlaceholderConfigurer();
    configurer.setProperties( properties);
    return  configurer;
}

3.使用:

1.基本使用

​ 和之前使用Properties一样,同样的方法注入(省略了SET和GET方法)

@Service
public class Info
{
    @Value("${id}")
    private String id;
    @Value("${name}")
    private String name;
}

使用的YML内容为:

id: 32
name: SY
2.配置形式为对象

使用的YML内容为:

Info:
 id: 32
 name: SY

注入值得时候得跟着改变,加上了对象

@Service
public class Info
{
    @Value("${Info.id}")
    private String id;
    @Value("${Info.name}")
    private String name;
}

3.配置形式为集合

使用的YML内容为:

Info:
 id: 32
 name: SY
lists: A,B,C

由于Properties不可以解析集合类型得数据,所以就使用EL表达式

@Service
public class Info
{
    @Value("${Info.id}")
    private String id;
    @Value("${Info.name}")
    private String name;
    @Value("#{'${lists}'.split(',')}")
    private List<String> list;
}
posted on 2021-07-23 16:35  NathenJames  阅读(53)  评论(0编辑  收藏  举报