文章目录
- 01-Spring操作数据库(掌握)
- 02-IOC注解说明(了解)
- 03-注解创建对象(掌握)
- 04-注解扫描详解(掌握)
- 05-注解依赖注入之@Autowired(掌握)
- 06-注解依赖注入之@Qualifier(掌握)
- 07-@Autowired的其他细节(掌握)
- 08-注解依赖注入之@Resource(掌握)
- 09-注解依赖注入之@Value(掌握)
- 10-注解整合junit(掌握)
- 11-IOC新注解说明(掌握)
- 12-IOC纯注解开发(掌握)
- 13-IOC注解开发的作用和弊端(掌握)
- 14-AOP 概述(掌握)
- 15-AOP原理环境搭建(掌握)
- 16-动态代理之JDKProxy(掌握)
- 17-动态代理之CGLIB(掌握)
- 18-AOP名词解释(掌握)
- 19-AOP入门案例(掌握)
01-Spring操作数据库(掌握)
-
需求
- 查询用户列表
-
技术体系
- Spring + DbUtils + mysql + druid
-
开发步骤
- ①引入依赖
- ②定义dao接口及其实现子类
- ③编写spring.xml
- ④代码测试
-
①引入依赖
<dependencies> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-core</artifactId> <version>5.3.16</version> </dependency> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-beans</artifactId> <version>5.3.16</version> </dependency> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-context</artifactId> <version>5.3.16</version> </dependency> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-expression</artifactId> <version>5.3.16</version> </dependency> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-jcl</artifactId> <version>5.3.16</version> </dependency> <dependency> <groupId>commons-dbutils</groupId> <artifactId>commons-dbutils</artifactId> <version>1.7</version> </dependency> <dependency> <groupId>com.alibaba</groupId> <artifactId>druid</artifactId> <version>1.2.8</version> </dependency> <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId> <version>5.1.49</version> </dependency> </dependencies> -
②定义dao接口及其实现子类
public class UserDaoImpl implements UserDao { private QueryRunner queryRunner; public void setQueryRunner(QueryRunner queryRunner) { this.queryRunner = queryRunner; } public List<User> selectUserList() throws Exception { return queryRunner.query( "select * from t_user", new BeanListHandler<User>(User.class) ); } } -
③编写spring.xml
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:context="http://www.springframework.org/schema/context" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd"> <bean id="userDao" class="com.panghu.dao.impl.UserDaoImpl"> <property name="queryRunner" ref="queryRunner"></property> </bean> <bean id="queryRunner" class="org.apache.commons.dbutils.QueryRunner"> <constructor-arg name="ds" ref="dataSource"></constructor-arg> </bean> <!--加载jdbc.properties--> <context:property-placeholder location="jdbc.properties"></context:property-placeholder> <bean id="dataSource" class="com.alibaba.druid.pool.DruidDataSource"> <property name="driverClassName" value="${driverClassName}"></property> <property name="url" value="${jdbcUrl}"></property> <property name="username" value="${user}"></property> <property name="password" value="${password}"></property> </bean> </beans> -
④代码测试
public class UserDaoTest { private ApplicationContext applicationContext; @Before public void init(){ applicationContext = new ClassPathXmlApplicationContext("spring.xml"); } @Test public void selectUserList() throws Exception { UserDao userDao = applicationContext.getBean(UserDao.class); List<User> userList = userDao.selectUserList(); System.out.println("userList = " + userList); } }
02-IOC注解说明(了解)
- 概述
- 学习基于注解的 IoC 配置,大家脑海里首先得有一个认知,即注解配置和 xml 配置要实现的功能都 是一样的,都是要降低程序间的耦合。只是配置的形式不一样。
- 关于实际的开发中到底使用xml还是注解,每家公司有着不同的使用习惯。所以这两种配置方式我们 都需要掌 握。
03-注解创建对象(掌握)
-
概述
- @Component , 通用注解,可以作用于任何实体类
- @Controller , 作用于控制层的实体类,本质是@Component
- @Service , 作用于业务层的实体类,本质是@Component
- @Repository , 作用于持久层的实体类,本质是@Component
-
代码实现
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:context="http://www.springframework.org/schema/context" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:cotnext="http://www.springframework.org/schema/context" xsi:schemaLocation=" http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"> <!--扫描注解--> <cotnext:component-scan base-package="com.panghu"></cotnext:component-scan> </beans>@Controller public class UserController { }@Service public class UserServiceImpl implements UserServcie { }@Repository public class UserDaoImpl implements UserDao { }@Component("user1") public class User { private Integer userId; private String userName; private String userPwd; private Double money; private String address; } -
代码测试
public class AnnotationTest { private ApplicationContext applicationContext; @Before public void init(){ applicationContext = new ClassPathXmlApplicationContext("spring.xml"); } /*03-注解创建对象*/ @Test public void test1(){ applicationContext.getBean("user1"); applicationContext.getBean("userController"); applicationContext.getBean("userServiceImpl"); applicationContext.getBean("userDaoImpl"); } }
04-注解扫描详解(掌握)
-
分类
- ①基本扫描
- ②指定要排除的组件
- ③指定要扫描的组件
-
①基本扫描
<cotnext:component-scan base-package="com.panghu"></cotnext:component-scan> -
②指定要排除的组件
<context:component-scan base-package="com.panghu"> <context:exclude-filter type="annotation" expression="org.springframework.stereotype.Controller"/> </context:component-scan> -
③指定要扫描的组件
<context:component-scan base-package="com.panghu" use-default-filters="false"> <context:include-filter type="annotation" expression="org.springframework.stereotype.Controller"/> </context:component-scan>
05-注解依赖注入之@Autowired(掌握)
-
概述
- 使用注解执行依赖注入
-
工作流程
-
代码实现
@Controller public class UserController { @Autowired private UserServcie userService; public void selectUserList() throws Exception { System.out.println("UserController selectUserList"); userService.selectUserList(); } } -
注意事项
- 使用@Autowired执行注入时,不需要提供set方法
06-注解依赖注入之@Qualifier(掌握)
-
概述
- 配置@Autowired注解使用,根据对象名称来执行自动装配
-
代码实现
@Controller public class UserController { @Autowired @Qualifier("userService2") private UserServcie userServcie; public void selectUserList() throws Exception { System.out.println("UserController selectUserList"); userServcie.selectUserList(); } }
07-@Autowired的其他细节(掌握)
-
①标注在构造器
@Component public class UserServiceWrapper { private UserServcie userServcie; @Autowired public UserServiceWrapper(UserServcie userServiceImpl) { this.userServcie = userServiceImpl; } } -
②标注在set方法
@Component public class UserServiceWrapper2 { private UserServcie userServcie; @Autowired @Qualifier("userServiceImpl") public void setUserServcie(UserServcie userServcie) { this.userServcie = userServcie; System.out.println("userServcie = " + userServcie); } } -
③佛系装配 : 有就执行装配,没有就不装配
@Controller public class UserController { @Autowired(required = false) @Qualifier("userServiceImpl3") private UserServcie userServcie; public void selectUserList() throws Exception { System.out.println("UserController selectUserList"); userServcie.selectUserList(); } }
08-注解依赖注入之@Resource(掌握)
- 概述
- JSR-250提供的,它是Java标准,绝大部分框架都支持。
- 总结
- 既指定name,也指定type
- 都要考虑
- 只指定name
- 只考虑name
- 只指定type
- 只考虑type
- 都没有指定
- 先考虑对象名称,再考虑对象类型
- 既指定name,也指定type
09-注解依赖注入之@Value(掌握)
-
概述
- 给简单类型的变量执行自动装配,相当于
-
代码实现
@Component public class Student { @Value("1") private Integer stuId ; @Value("廖虚蕊") private String stuName; }
10-注解整合junit(掌握)
-
开发步骤
- ①引入依赖
- spring-test
- ②编写单元测试类
- ①引入依赖
-
①引入依赖
<dependency> <groupId>org.springframework</groupId> <artifactId>spring-test</artifactId> <version>5.3.16</version> </dependency> -
②编写单元测试类
@RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration(locations = "classpath:spring.xml") public class AnnotationTest2 { @Autowired private UserController userController; @Test public void selectUserList() throws Exception { userController.selectUserList(); } }
11-IOC新注解说明(掌握)
- @Configuration
- 用于指定当前类是一个 spring 配置类;相当于spring.xml
- @ComponentScan
- 用于指定 spring 在初始化容器时要扫描的包;相当于"<cotnext:component-scan base-package=“com.atguigu”>"
- @Bean
- 该注解只能写在方法上,表明使用方法创建一个对象,并且放入 spring 容器;
- 相当于""
- @PropertySource
- 用于加载properties文件;相当于"<context:property-placeholder location=“jdbc.properties”>"
- @Import
- 用于导入其他的配置类;相当于""
12-IOC纯注解开发(掌握)
-
需求
- 将"01-Spring操作数据库"修改为纯注解配置.
-
代码实现
@Import(DataSourceConfiguration.class) @Configuration @ComponentScan("com.panghu") public class SpringConfiguration { }@Configuration @PropertySource("jdbc.properties") public class DataSourceConfiguration { @Value("${driverClassName}") private String driverClassName; @Value("${jdbcUrl}") private String url; @Value("${user}") private String username; @Value("${password}") private String password; @Bean public QueryRunner getQueryRunner(DataSource ds){ return new QueryRunner(ds); } @Bean public DataSource getDataSource(){ DruidDataSource dataSource = new DruidDataSource(); dataSource.setDriverClassName(driverClassName); dataSource.setUrl(url); dataSource.setUsername(username); dataSource.setPassword(password); return dataSource; } }@Repository public class UserDaoImpl implements UserDao { @Autowired private QueryRunner queryRunner; public List<User> selectUserList() throws Exception { return queryRunner.query( "select * from t_user", new BeanListHandler<User>(User.class) ); } }public class UserDaoTest { private ApplicationContext applicationContext; @Before public void init(){ applicationContext = new AnnotationConfigApplicationContext(SpringConfiguration.class); } @Test public void selectUserList() throws Exception { UserDao userDao = applicationContext.getBean(UserDao.class); List<User> userList = userDao.selectUserList(); System.out.println("userList = " + userList); } }
13-IOC注解开发的作用和弊端(掌握)
- 作用
- 总结
- 开发过程中,既有注解,也有xml配置的.
14-AOP 概述(掌握)
- 概述
- 全称是 Aspect Oriented Programming 即: 面向切面编程。
- 核心思想
- AOP关注的是程序中的共性功能,开发时,将共性功能抽取出来制作成独立的功能模块,此时原始功 能中将不具有这些被抽取出的共性功能代码。在被抽取的共性功能的模块运行时候,将共性功能模块 也运行,即可完成原始的功能。
- 作用
- 在程序运行期间,不修改源码对已有方法进行增强。
- 优势
- 减少重复代码 提高开发效率 维护方便
- 实现方式
- 装饰模式
- 动态代理技术
- OOP vs AOP
- OOP : 面向对象
- AOP : 面向共性功能
15-AOP原理环境搭建(掌握)
-
代码实现
public class UserServiceImpl implements UserService { public void addUser() throws Exception { System.out.println("权限校验"); System.out.println("UserServiceImpl addUser"); System.out.println("日志记录"); } public void deleteUser() throws Exception { System.out.println("权限校验"); System.out.println("UserServiceImpl deleteUser"); System.out.println("日志记录"); } public void updateUser() throws Exception { System.out.println("UserServiceImpl updateUser"); } public void selectUser() throws Exception { System.out.println("UserServiceImpl selectUser"); } } -
存在问题
- 主要功能:增加用户,删除用户,修改用户,查询用户 和辅助功能:权限校验,日志记录都写到一块了,不满足单一职责原则,耦合度较高.
16-动态代理之JDKProxy(掌握)
-
工作原理
-
代码实现
public class UserServiceJDKProxy { /** * 获取代理类对象 * * @param userService : 被代理类对象 * @return : 代理类对象 */ public static UserService getUserServiceJDKProxy(final UserService userService) { //ClassLoader loader : 被代理类的类加载器 //Class<?>[] interfaces : 被代理类所实现的所有接口 //InvocationHandler h : 方法增强的处理器 UserService userServiceProxy = (UserService) Proxy.newProxyInstance( userService.getClass().getClassLoader(), userService.getClass().getInterfaces(), new InvocationHandler() { public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { //Object proxy : 代理类对象 //Method method : 被代理类的方法 //Object[] args : 方法的实际参数 Object result = null; if (method.getName().equals("addUser") || method.getName().equals("deleteUser")) { System.out.println("权限校验"); //被代理类对象 调用 被代理类方法 result = method.invoke(userService, args); System.out.println("日志记录"); } else { //selectUser,updateUser , 调用被代理类方法 result = method.invoke(userService, args); } return result; } } ); return userServiceProxy; } }public class UserServiceJDKProxyTest { @Test public void addUser() throws Exception { //被代理类对象 UserService userService = new UserServiceImpl(); //代理类对象 UserService userServiceJDKProxy = UserServiceJDKProxy.getUserServiceJDKProxy(userService); userServiceJDKProxy.addUser(); } @Test public void deleteUser() throws Exception { //被代理类对象 UserService userService = new UserServiceImpl(); //代理类对象 UserService userServiceJDKProxy = UserServiceJDKProxy.getUserServiceJDKProxy(userService); userServiceJDKProxy.deleteUser(); } @Test public void updateUser() throws Exception { //被代理类对象 UserService userService = new UserServiceImpl(); //代理类对象 UserService userServiceJDKProxy = UserServiceJDKProxy.getUserServiceJDKProxy(userService); userServiceJDKProxy.updateUser(); } @Test public void selectUser() throws Exception { //被代理类对象 UserService userService = new UserServiceImpl(); //代理类对象 UserService userServiceJDKProxy = UserServiceJDKProxy.getUserServiceJDKProxy(userService); userServiceJDKProxy.selectUser(); } }
17-动态代理之CGLIB(掌握)
-
工作流程
-
代码实现
public class UserServiceCglibProxy { /** * 获取代理类对象 * * @param clazz : 被代理类字节码对象 * @return */ public static UserService getUserServiceCglibProxy(final Class clazz) { Enhancer enhancer = new Enhancer(); //代理类对象 继承 被代理类对象 enhancer.setSuperclass(clazz); //执行方法增强 enhancer.setCallback(new MethodInterceptor() { public Object intercept(Object o, Method method, Object[] args, MethodProxy methodProxy) throws Throwable { //Object o : 代理类对象 //Method method : 被代理类方法 //Object[] args : 方法实际参数 //MethodProxy methodProxy : 代理类方法 Object result = null; if ("addUser".equals(method.getName()) || "deleteUser".equals(method.getName())) { System.out.println("权限校验"); //执行 被代理类的方法 //method.invoke(o,args);//错误 //method.invoke(clazz,args);//错误 //methodProxy.invoke(o,args);//错误 //由代理类对象 执行代理类方法 , 调用代理类方法的父方法(被代理的方法) result = methodProxy.invokeSuper(o, args); System.out.println("日志记录"); } else { result = methodProxy.invokeSuper(o, args); } return result; } }); Object userServiceCglibProxy = enhancer.create(); return (UserService) userServiceCglibProxy; } }public class UserServiceCglibProxyTest { @Test public void addUser() throws Exception { UserService userServiceCglibProxy = UserServiceCglibProxy.getUserServiceCglibProxy(UserServiceImpl.class); userServiceCglibProxy.addUser(); } @Test public void deleteUser() throws Exception { UserService userServiceCglibProxy = UserServiceCglibProxy.getUserServiceCglibProxy(UserServiceImpl.class); userServiceCglibProxy.deleteUser(); } @Test public void updateUser() throws Exception { UserService userServiceCglibProxy = UserServiceCglibProxy.getUserServiceCglibProxy(UserServiceImpl.class); userServiceCglibProxy.updateUser(); } @Test public void selectUser() throws Exception { UserService userServiceCglibProxy = UserServiceCglibProxy.getUserServiceCglibProxy(UserServiceImpl.class); userServiceCglibProxy.selectUser(); } } -
总结
- 被代理类对象有实现接口,使用JDKProxy动态代理,代理类和被代理类实现同一个接口.
- 被代理类对象没有实现接口,使用CGLIB动态代理,代理类继承被代理类.
18-AOP名词解释(掌握)
- 连接点:join point
- 被代理类中的所有方法
- 切入点: pointcut
- 被代理类中的具有共性功能的方法
- 目标对象类
- 包含切入点方法的类
- 通知: advice
- 将共性功能抽取成独立的方法
- 通知类
- 包含通知方法的类
- 切面:aspect
- 通知和切入点的关系
- 织入 : weave
- 将共性功能(通知)动态放入到原方法(切入点)执行的过程
19-AOP入门案例(掌握)
-
开发步骤
- ①引入依赖
- ②制作目标对象类
- 切入点
- ③制作通知类
- 通知
- ④编写spring.xml
- 配置切面关系
- ⑤代码测试
-
①引入依赖
<dependency> <groupId>org.springframework</groupId> <artifactId>spring-aop</artifactId> <version>5.3.16</version> </dependency> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-aspects</artifactId> <version>5.3.16</version> </dependency> -
②制作目标对象类
@Service public class UserServiceImpl implements UserService { /** * 切入点 * @throws Exception */ public void addUser() throws Exception { System.out.println("UserServiceImpl addUser"); } /** * 切入点 * @throws Exception */ public void deleteUser() throws Exception { System.out.println("UserServiceImpl deleteUser"); } public void updateUser() throws Exception { System.out.println("UserServiceImpl updateUser"); } public void selectUser() throws Exception { System.out.println("UserServiceImpl selectUser"); } } -
③制作通知类
@Component public class MyAdvice1 { /** * 通知 */ public void checkPermission(){ System.out.println("权限校验"); } /** * 通知 */ public void printLog(){ System.out.println("日志记录"); } } -
④编写spring.xml
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context" xmlns:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/aop https://www.springframework.org/schema/aop/spring-aop.xsd"> <context:component-scan base-package="com.atguigu"></context:component-scan> <!--配置切面--> <aop:config> <!--通知和切入点的关系--> <aop:aspect ref="myAdvice1"> <aop:before method="checkPermission" pointcut="execution(public void com.atguigu.service.impl.UserServiceImpl.addUser())"></aop:before> <aop:after method="printLog" pointcut="execution(public void com.atguigu.service.impl.UserServiceImpl.addUser())"></aop:after> </aop:aspect> </aop:config> </beans> -
⑤代码测试
@RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration(locations = "classpath:spring.xml") public class AOPTest { @Autowired private UserService userService; @Test public void addUser() throws Exception { userService.addUser(); } @Test public void selectUser() throws Exception { userService.selectUser(); } }
本文详细介绍了如何使用Spring框架操作数据库,包括引入依赖、定义DAO接口及其实现、配置Spring XML文件以及进行代码测试。接着探讨了IoC注解,如@Component、@Autowired、@Qualifier等,解释了它们的工作原理和应用场景。同时,讲解了基于注解的Spring配置,如@Configuration、@ComponentScan和@Bean。最后,提到了AOP的概念、动态代理(JDKProxy和CGLIB)以及AOP在Spring中的应用,包括通知、切入点和织入过程。





846

被折叠的 条评论
为什么被折叠?



