spring整合dbutils+c3p0实现数据的增删改查

前面两篇文章和大家分享了spring的IOC和DI工作原理。今天我们利用spring+dbutils+mysql来做一个简单的demo。这个demo的功能主要是银行账户的一些信息,实现基本的增删查改操作。

  • 采用XML形式实现demo
  • 采用XML和注解形式实现demo
  • 采用注解形式实现demo

首先,我们创建一个maven工程,搭建spring的开发环境。
项目结构如下:
在这里插入图片描述
读者暂且不用管config包面的东西了。这个就是我们正常的三层架构模式。
pom文件如下:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>com.tff.demo</groupId>
    <artifactId>spring_demo</artifactId>
    <version>1.0-SNAPSHOT</version>
    <packaging>jar</packaging>
    <dependencies>
    
        <!-- spring 开发环境 -->
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-context</artifactId>
            <version>5.0.5.RELEASE</version>
        </dependency>
        
        <!-- dbutils数据操作工具类 -->
        <dependency>
            <groupId>commons-dbutils</groupId>
            <artifactId>commons-dbutils</artifactId>
            <version>1.4</version>
        </dependency>
        
        <!--   mysql数据库驱动类 -->
        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <version>5.1.37</version>
        </dependency>
        
        <!-- junit测试单元 -->
        <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
            <version>4.11</version>
        </dependency>
        
        <!-- c3p0数据库连接池 -->
        <dependency>
            <groupId>c3p0</groupId>
            <artifactId>c3p0</artifactId>
            <version>0.9.1.2</version>
        </dependency>
    </dependencies>

</project>

数据库文件


//创建表文件
create table account1(
	id int PRIMARY key auto_increment,
	name varchar(40) COMMENT '账户名',
	money float COMMENT '账户余额'
);
//插入数据
insert into account1(name,money) values('张三',4545);
insert into account1(name,money) values('zyy',4545);
insert into account1(name,money) values('gxr',454545);
insert into account1(name,money) values('lyc',78787);
insert into account1(name,money) values('zyt',78787);
insert into account1(name,money) values('tff',99999999999.999);
insert into account1(name,money) values('weilai',8888888888.888);

实体类:

package com.tff.demo.entity;

import com.sun.org.apache.xml.internal.serialize.Serializer;
import java.io.Serializable;

public class Account implements Serializable {
    private Integer id;
    private String name;
    private Float money;

    public Integer getId() {
        return id;
    }

    public void setId(Integer id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public Float getMoney() {
        return money;
    }

    public void setMoney(Float money) {
        this.money = money;
    }

    @Override
    public String toString() {
        return "Account{" +
                "id=" + id +
                ", name='" + name + '\'' +
                ", money=" + money +
                '}';
    }
}

基于XML形式来实现demo

dao层
package com.tff.demo.dao;

import com.tff.demo.entity.Account;
import java.util.List;
public interface AccountDao {
    //查询所有的账户信息
    List<Account> getAccountAll();
    //按照条件来查询
    Account getAccount(Integer id);
    //增加一个账户信息
    int saveAccount(Account account);
    //修改账户信息
    int updateAccount(Account account);
    //删除账户信息
    int deleteAccount(Integer id);
}

package com.tff.demo.dao.impl;

import com.tff.demo.dao.AccountDao;
import com.tff.demo.entity.Account;
import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanHandler;
import org.apache.commons.dbutils.handlers.BeanListHandler;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;
import java.util.List;

public class AccountImpl implements AccountDao {
	//这个是dbutils工具类中的属性,用来完成对数据的增删改查
    private QueryRunner runner;
	
	//因为我们使用set方式注入数据,所以提供必要的set方法和默认构造函数
    public void setRunner(QueryRunner runner) {
        this.runner = runner;
    }

	//查询所有的用户账户信息
    public List<Account> getAccountAll() {
        try{
            return runner.query("select * from account1",new BeanListHandler<Account>(Account.class));
        }catch (Exception e){
           throw new RuntimeException(e);
        }
    }
	//按照id来查询个人的账户信息
    public Account getAccount(Integer id) {
        try{
            return runner.query("select * from account1 where id = ?",new BeanHandler<Account>(Account.class));
        }catch (Exception e){
            throw new RuntimeException(e);
        }
    }
	//注册一个账户信息
    public int saveAccount(Account account) {
        try{
            return runner.update("insert into account1(name,money)values(?,?)",account.getName(),account.getMoney());
        }catch (Exception e){
            throw new RuntimeException(e);
        }
    }
	//修改一个账户信息
    public int updateAccount(Account account) {
        try{
            return runner.update("update account1 set name = ?,money = ? where id = ?",account.getName(),account.getMoney(),account.getId());
        }catch (Exception e){
            throw new RuntimeException(e);
        }
    }
	//删除一个账户信息
    public int deleteAccount(Integer id) {
        try{
            return runner.update("delete from account1 where id = ?",id);
        }catch (Exception e){
            throw new RuntimeException(e);
        }
    }
}

service层
package com.tff.demo.service;

import com.tff.demo.entity.Account;
import java.util.List;

public interface AccountService {
    //查询所有的账户信息
    List<Account> getAccountAll();
    //按照条件来查询
    Account getAccount(Integer id);
    //增加一个账户信息
    int saveAccount(Account account);
    //修改账户信息
    int updateAccount(Account account);
    //删除账户信息
    int deleteAccount(Integer id);
}

package com.tff.demo.service.impl;

import com.tff.demo.dao.AccountDao;
import com.tff.demo.entity.Account;
import com.tff.demo.service.AccountService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.util.List;

public class AccountServiceImpl implements AccountService {

 	//dao层属性,用来访问dao层的方法
    private AccountDao accountDao;
	//使用set方式注入,提供标准的set方法和默认构造函数
    public void setAccountDao(AccountDao accountDao) {
        this.accountDao = accountDao;
    }
//一下都是调用dao层的方法,实现对数据库的访问。对于初学者,可能觉得这一层没有必要,是的,因为我们现在还没有实现业务逻辑的控制,就只是简单的调用dao层方法而已。
    public List<Account> getAccountAll() {
        return accountDao.getAccountAll();
    }

    public Account getAccount(Integer id) {
        return accountDao.getAccount(id);
    }

    public int saveAccount(Account account) {
        return accountDao.saveAccount(account);
    }

    public int updateAccount(Account account) {
        return accountDao.updateAccount(account);
    }

    public int deleteAccount(Integer id) {
        return accountDao.deleteAccount(id);
    }
}
spring配置文件
<?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
        http://www.springframework.org/schema/context/spring-context.xsd
        http://www.springframework.org/schema/aop
        http://www.springframework.org/schema/aop/spring-aop.xsd
        http://www.springframework.org/schema/tx">

<!-- 配置service层 -->
    <bean id="accountService" class="com.tff.demo.service.impl.AccountServiceImpl">
        <!-- 注入数据 -->
        <property name="accountDao" ref="dao"></property>
    </bean>

    <!--  配置dao层-->
    <bean id="dao" class="com.tff.demo.dao.impl.AccountImpl">
        <!-- 注入数据 -->
        <property name="runner" ref="queryRunner"></property>
    </bean>
    <context:component-scan base-package="com.tff.demo"></context:component-scan>

    <!--   配置queryRunner,它提供了一个有参构造器来进行注入 -->
    <bean id="queryRunner" class="org.apache.commons.dbutils.QueryRunner">
        <!-- 注入数据源 -->
        <constructor-arg name="ds" ref="dataSource"></constructor-arg>
    </bean>
    <!--  配置数据源  -->
    <bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
        <!-- 连接数据库的必备信息 -->
        <property name="driverClass" value="com.mysql.jdbc.Driver"></property>
        <property name="jdbcUrl" value="jdbc:mysql://10.10.6.45:3396/TEST"></property>
        <property name="user" value="root"></property>
        <property name="password" value="Az.123456"></property>
    </bean>
</beans>

简单说明一下:
我们先注入的是service层的数据,在service层我们引用了dao层的属性,所以,要使用ref标签来进行注入。那ref标签注入的bean类型必须是要在springIOC容器中出现过的对象。所以,我们还要配置dao层,这样,dao层这个bean类型就存在于springIOC容器中了。我们又发现,在dao层我们要使用dbutils工具实现对数据库的访问,我们也要对他进行类似上面的操作。同理,数据源也是一样。
大家对dbutils和C3P0数据库连接池不了解的没关系,我们这次的重点不在这里。有兴趣的可以自己去查阅资料。
接下来我们看一下测试类:

import com.tff.demo.config.SpringConfiguration;
import com.tff.demo.entity.Account;
import com.tff.demo.service.AccountService;
import org.apache.commons.dbutils.QueryRunner;
import org.junit.Test;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import java.util.List;
//利用Junit测试单元进行测试
public class AccountServiceTest {
    @Test
    public void testFindAll(){
        ApplicationContext ac = new ClassPathXmlApplicationContext("bean.xml");
        AccountService  accountService = ac.getBean("accountService",AccountService.class);
        List<Account> list = accountService.getAccountAll();
        for (Account acc: list) {
            System.out.println(acc.toString());
        }
    }

    @Test
    public void testDelete(){
    	 ApplicationContext ac = new ClassPathXmlApplicationContext("bean.xml");
        AccountService  accountService = ac.getBean("accountService",AccountService.class);
        int k = accountService.deleteAccount(2);
       	System.out.println(k);
    }
    @Test
    public void updateAccount(){
        ApplicationContext ac = new ClassPathXmlApplicationContext("bean.xml");
        AccountService  accountService = ac.getBean("accountService",AccountService.class);
        Account account = new Account();
        account.setId(2);
        account.setName("zyy2");
        account.setMoney(454545454545.789F);
        int up = accountService.updateAccount(account);
        System.out.println(up);
    }
    @Test
    public void insertAccount(){
        ApplicationContext ac = new ClassPathXmlApplicationContext("bean.xml");
        AccountService  accountService = ac.getBean("accountService",AccountService.class);
        Account account = new Account();
        account.setName("dt");
        account.setMoney(454545545.789F);
        accountService.saveAccount(account);
    }
}

运行结果:
在这里插入图片描述
如果大家在看的过程中,对spring的IOC和注入方式又不理解的,建议大家先看上两篇文章。里面详细解说了spring的IOC机制和DI机制。

基于XML和注解形式来实现demo

dao层
package com.tff.demo.dao;
import com.tff.demo.entity.Account;
import java.util.List;

public interface AccountDao {
    //查询所有的账户信息
    List<Account> getAccountAll();
    //按照条件来查询
    Account getAccount(Integer id);
    //增加一个账户信息
    int saveAccount(Account account);
    //修改账户信息
    int updateAccount(Account account);
    //删除账户信息
    int deleteAccount(Integer id);

}

package com.tff.demo.dao.impl;

import com.tff.demo.dao.AccountDao;
import com.tff.demo.entity.Account;
import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanHandler;
import org.apache.commons.dbutils.handlers.BeanListHandler;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;
import java.util.List;

//这个注解已经讲过了
@Repository
public class AccountImpl implements AccountDao {

	//自动化装配
    @Autowired
    private QueryRunner runner;
    
    public List<Account> getAccountAll() {
        try{
            return runner.query("select * from account1",new BeanListHandler<Account>(Account.class));
        }catch (Exception e){
           throw new RuntimeException(e);
        }
    }

    public Account getAccount(Integer id) {
        try{
            return runner.query("select * from account1 where id = ?",new BeanHandler<Account>(Account.class));
        }catch (Exception e){
            throw new RuntimeException(e);
        }
    }

    public int saveAccount(Account account) {
        try{
            return runner.update("insert into account1(name,money)values(?,?)",account.getName(),account.getMoney());
        }catch (Exception e){
            throw new RuntimeException(e);
        }
    }

    public int updateAccount(Account account) {
        try{
            return runner.update("update account1 set name = ?,money = ? where id = ?",account.getName(),account.getMoney(),account.getId());
        }catch (Exception e){
            throw new RuntimeException(e);
        }
    }

    public int deleteAccount(Integer id) {
        try{
            return runner.update("delete from account1 where id = ?",id);
        }catch (Exception e){
            throw new RuntimeException(e);
        }
    }
}
service层
package com.tff.demo.service;
import com.tff.demo.entity.Account;
import java.util.List;

public interface AccountService {
    //查询所有的账户信息
    List<Account> getAccountAll();
    //按照条件来查询
    Account getAccount(Integer id);
    //增加一个账户信息
    int saveAccount(Account account);
    //修改账户信息
    int updateAccount(Account account);
    //删除账户信息
    int deleteAccount(Integer id);
}
package com.tff.demo.service.impl;

import com.tff.demo.dao.AccountDao;
import com.tff.demo.entity.Account;
import com.tff.demo.service.AccountService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.List;

@Service
public class AccountServiceImpl implements AccountService {
	//按照类型自动装配
    @Autowired
    //@Resource(name = "id的属性值")  这个注解也是可以的
    private AccountDao accountDao;
    
    public List<Account> getAccountAll() {
        return accountDao.getAccountAll();
    }

    public Account getAccount(Integer id) {
        return accountDao.getAccount(id);
    }

    public int saveAccount(Account account) {
        return accountDao.saveAccount(account);
    }

    public int updateAccount(Account account) {
        return accountDao.updateAccount(account);
    }

    public int deleteAccount(Integer id) {
        return accountDao.deleteAccount(id);
    }
}

spring配置文件

<?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
        http://www.springframework.org/schema/context/spring-context.xsd
        http://www.springframework.org/schema/aop
        http://www.springframework.org/schema/aop/spring-aop.xsd
        http://www.springframework.org/schema/tx">
	<!--  告诉spring去那些包下面扫描要交给spring实例化的对象 -->
    <context:component-scan base-package="com.tff.demo"></context:component-scan>

    <!--   配置queryRunner,它提供了一个有参构造器来进行注入 -->
    <bean id="queryRunner" class="org.apache.commons.dbutils.QueryRunner">
        <!-- 注入数据源 -->
        <constructor-arg name="ds" ref="dataSource"></constructor-arg>
    </bean>
    <!--  配置数据源  -->
    <bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
        <!-- 连接数据库的必备信息 -->
        <property name="driverClass" value="com.mysql.jdbc.Driver"></property>
        <property name="jdbcUrl" value="jdbc:mysql://10.10.6.45:3396/TEST"></property>
        <property name="user" value="root"></property>
        <property name="password" value="Az.123456"></property>
    </bean>
</beans>

测试类:

import com.tff.demo.config.SpringConfiguration;
import com.tff.demo.entity.Account;
import com.tff.demo.service.AccountService;
import org.apache.commons.dbutils.QueryRunner;
import org.junit.Test;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import java.util.List;

public class AccountServiceTest {
    @Test
    public void testFindAll(){
        ApplicationContext ac = new ClassPathXmlApplicationContext("bean.xml");
        
        //这里需要注意一下,为什么这里是accountServiceImpl而不是上一次的accountService,因为我们在Service层的实现类的Service注解后面省略了value属性,所以,默认就是当前类名(类名首字母小写),如果需要指定,可以这样Server(value="名字")
        AccountService  accountService = ac.getBean("accountServiceImpl",AccountService.class);
        List<Account> list = accountService.getAccountAll();
        for (Account acc: list) {
            System.out.println(acc.toString());
        }
    }

    @Test
    public void testDelete(){
       ApplicationContext ac = new ClassPathXmlApplicationContext("bean.xml");
        AccountService  accountService = ac.getBean("accountServiceImpl",AccountService.class);
        int k = accountService.deleteAccount(2);
        System.out.println(k);
       
    }
    @Test
    public void updateAccount(){
        ApplicationContext ac = new ClassPathXmlApplicationContext("bean.xml");
        AccountService  accountService = ac.getBean("accountServiceImpl",AccountService.class);
        Account account = new Account();
        account.setId(2);
        account.setName("zyy2");
        account.setMoney(454545454545.789F);
        int up = accountService.updateAccount(account);
        System.out.println(up);
    }
    @Test
    public void insertAccount(){
        ApplicationContext ac = new ClassPathXmlApplicationContext("bean.xml");
        AccountService  accountService = ac.getBean("accountServiceImpl",AccountService.class);
        Account account = new Account();
        account.setName("dt");
        account.setMoney(454545545.789F);
        accountService.saveAccount(account);
    }
}

测试结果:
在这里插入图片描述
小结一下:跟完全XML形式配置哪里不一样呢?好像也差不多。就是spring的配置文件中我们要告诉spring去哪个包下面扫面要交给spring容器帮我们实例化的bean 对象。

基于全注解形式来实现demo

dao层
package com.tff.demo.dao;
import com.tff.demo.entity.Account;
import java.util.List;

public interface AccountDao {
    //查询所有的账户信息
    List<Account> getAccountAll();
    //按照条件来查询
    Account getAccount(Integer id);
    //增加一个账户信息
    int saveAccount(Account account);
    //修改账户信息
    int updateAccount(Account account);
    //删除账户信息
    int deleteAccount(Integer id);

}
package com.tff.demo.dao.impl;

import com.tff.demo.dao.AccountDao;
import com.tff.demo.entity.Account;
import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanHandler;
import org.apache.commons.dbutils.handlers.BeanListHandler;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;

import java.util.List;

@Repository
public class AccountImpl implements AccountDao {

    @Autowired
    private QueryRunner runner;
    
    public List<Account> getAccountAll() {
        try{
            return runner.query("select * from account1",new BeanListHandler<Account>(Account.class));
        }catch (Exception e){
           throw new RuntimeException(e);
        }
    }

    public Account getAccount(Integer id) {
        try{
            return runner.query("select * from account1 where id = ?",new BeanHandler<Account>(Account.class));
        }catch (Exception e){
            throw new RuntimeException(e);
        }
    }

    public int saveAccount(Account account) {
        try{
            return runner.update("insert into account1(name,money)values(?,?)",account.getName(),account.getMoney());
        }catch (Exception e){
            throw new RuntimeException(e);
        }
    }

    public int updateAccount(Account account) {
        try{
            return runner.update("update account1 set name = ?,money = ? where id = ?",account.getName(),account.getMoney(),account.getId());
        }catch (Exception e){
            throw new RuntimeException(e);
        }
    }

    public int deleteAccount(Integer id) {
        try{
            return runner.update("delete from account1 where id = ?",id);
        }catch (Exception e){
            throw new RuntimeException(e);
        }
    }
}

service层
package com.tff.demo.service;
import com.tff.demo.entity.Account;
import java.util.List;

public interface AccountService {
    //查询所有的账户信息
    List<Account> getAccountAll();
    //按照条件来查询
    Account getAccount(Integer id);
    //增加一个账户信息
    int saveAccount(Account account);
    //修改账户信息
    int updateAccount(Account account);
    //删除账户信息
    int deleteAccount(Integer id);
}
package com.tff.demo.service.impl;

import com.tff.demo.dao.AccountDao;
import com.tff.demo.entity.Account;
import com.tff.demo.service.AccountService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import javax.annotation.Resource;
import java.util.List;

@Service
public class AccountServiceImpl implements AccountService {

    @Autowired
    private AccountDao accountDao;

    public List<Account> getAccountAll() {
        return accountDao.getAccountAll();
    }

    public Account getAccount(Integer id) {
        return accountDao.getAccount(id);
    }

    public int saveAccount(Account account) {
        return accountDao.saveAccount(account);
    }

    public int updateAccount(Account account) {
        return accountDao.updateAccount(account);
    }

    public int deleteAccount(Integer id) {
        return accountDao.deleteAccount(id);
    }
}

到这里,我们发现是不是跟基于注解和XML来实现的demo的方式一样,是的,至少在dao层和service层是一样的,还记得第三种的实现方式叫“全注解实现”,什嘛意思,就是这次肯定不会再有XML文件出现了,当然,程序运行的时候不会再去加载spring的配置文件。(哦买噶,XML是不是已经悄悄的留下了伤心的泪水,太伤人家的心了。)
怎么会,出来混迟早是要还的。只不过是换了一种存在方式而已(哈哈哈哈哈……)。他就是我们前面说的config包下面的东东,一起来看一下:
在这里插入图片描述
目录结构就是这样的(包名和类名自己随便起,只要符合java的命名规则就OK)

SpringConfiguration配置类代码
package com.tff.demo.config;
import com.mchange.v2.c3p0.ComboPooledDataSource;
import org.apache.commons.dbutils.QueryRunner;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Scope;
import javax.sql.DataSource;

@Configuration
@ComponentScan(basePackages = {"com.tff.demo"})
public class SpringConfiguration {
	
	//把当前方法的返回值作为bean的对象存入spring的IOC容器中,如果省略name值,他的id为方法名
    @Bean(name = "runner")
    @Scope("prototype")  //bean 对象的作用范围
    public QueryRunner getNewQueryRunner(DataSource dataSource){
        return new QueryRunner(dataSource);
    }

    @Bean(name = "dataSource")
    public DataSource getDataSource(){
        ComboPooledDataSource cs = new ComboPooledDataSource();
        try{
            cs.setDriverClass("com.mysql.jdbc.Driver");
            cs.setJdbcUrl("jdbc:mysql://10.10.6.45:3396/TEST");
            cs.setUser("root");
            cs.setPassword("Az.123456");
            return cs;
        }catch (Exception e){
            throw new RuntimeException(e);
        }
    }
}

稍后我们来看那些不认识的注解
测试类:

import com.tff.demo.config.SpringConfiguration;
import com.tff.demo.entity.Account;
import com.tff.demo.service.AccountService;
import org.apache.commons.dbutils.QueryRunner;
import org.junit.Test;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import java.util.List;

public class AccountServiceTest {
    @Test
    public void testFindAll(){
        ApplicationContext ac = new AnnotationConfigApplicationContext(SpringConfiguration.class);
        AccountService  accountService = ac.getBean("accountServiceImpl",AccountService.class);
        List<Account> list = accountService.getAccountAll();
        for (Account acc: list) {
            System.out.println(acc.toString());
        }
    }

    @Test
    public void testDelete(){
      ApplicationContext ac = new AnnotationConfigApplicationContext(SpringConfiguration.class);
        AccountService  accountService = ac.getBean("accountServiceImpl",AccountService.class);
        int k = accountService.deleteAccount(2);
       System.out.println(k);
    }
    
    @Test
    public void updateAccount(){
        ApplicationContext ac = new AnnotationConfigApplicationContext(SpringConfiguration.class);
        AccountService  accountService = ac.getBean("accountServiceImpl",AccountService.class);
        Account account = new Account();
        account.setId(2);
        account.setName("zyy2");
        account.setMoney(454545454545.789F);
        int up = accountService.updateAccount(account);
        System.out.println(up);
    }
    @Test
    public void insertAccount(){
        ApplicationContext ac = new AnnotationConfigApplicationContext(SpringConfiguration.class);
        AccountService  accountService = ac.getBean("accountService",AccountService.class);
        Account account = new Account();
        account.setName("dt");
        account.setMoney(454545545.789F);
        accountService.saveAccount(account);
    }
}

运行结果:
在这里插入图片描述
另外,需要大家注意的是,在测试类中我们不在是加载类路径下面的spring配置文件,而是使用注解的方式类实现:
ApplicationContext ac = new AnnotationConfigApplicationContext(SpringConfiguration.class);
希望大家仔细恳看清这一点。
配置类的作用:
其实就和bean.xml是一样的
现在我来解释一下配置类的一些注解,也是spring中一些新的注解:
Configuration:
作用:指定当前类是一个配置类
ComponentScan:
作用:用于通过注解指定spring在创建容器时要扫描的包
属性:他有两个属性,分别是value和basePackages,作用是一样的。都是用于指定创建容器时要扫描的包。等同于XML中配置:
<context:component-scan base-package=“com.tff.demo”></context:component-scan>

Bean:
作用:用于把当前方法的返回值作为bean对象存入spring的IOC容器中。
属性:
name:用于指定bean的id,当不写时,默认值是当前方法的名称,而不是当前类的名称。

备注:有一个问题,不知道大家有没有发现,就是我们去掉配置类上面的@Configuration注解,也能正常运行处结果。这是为什么?
说明一下:就是如果这个配置类只是作为注解构造函数里面的一个参数时,我们可以不写Configuration这个注解。如果,我们需要配置的东西,需要用到ComponentScan去扫描的时候,这个时候还不写Configuration注解的时候,他不会去扫描的。因为他不是一个配置类。
demo中刚好作为一个参数传入,所以不写也是可以的。如果有多个配置类,不想写Configuration注解,就把他作为参数穿进去就可以了。
ApplicationContext ac = new AnnotationConfigApplicationContext(SpringConfiguration.class);
加粗部分就是作为这个类的一个参数传递进去,如果有多个,写在后面,逗号隔开。
所以,@Configuration这个注解什么时候能去掉,什么时候不能去掉,希望大家也搞清楚。
这个demo就跟大家分享完了。也不知道会不会理解了。还是来总结一下:
总结:
spring的配置方式和spring的注入方式是两个概念。请不要混淆这两个概念。配置方式更多的是spring帮我们实例化bean 对象。而注入方式更多的是给bean对象的成员属性赋值的。
spring的配置方式就目前而言只有XML和注解方式
spring的注入方式有基于构造函数、set方法和注解三种方式。

今天人生中第23个感恩节,虽然是一个西方的节日,不是我们中国的传统节日。但是,我们仍然要心怀感恩。感恩曾经给过你帮助的人,感恩那些伤害过你的人。感恩父母,感恩祖国。感恩这世间的一花一草。正式因为有他们的存在,我们的世界才变得精彩、变得美好。

  • 2
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
好的,以下是使用QueryRunner和c3p0进行增删改查操作的示例代码: ```java import java.sql.SQLException; import java.util.List; import org.apache.commons.dbutils.QueryRunner; import org.apache.commons.dbutils.handlers.BeanListHandler; import com.mchange.v2.c3p0.ComboPooledDataSource; public class C3p0Demo { private static ComboPooledDataSource dataSource; static { dataSource = new ComboPooledDataSource(); dataSource.setJdbcUrl("jdbc:mysql://localhost:3306/test"); dataSource.setUser("root"); dataSource.setPassword("123456"); dataSource.setDriverClass("com.mysql.jdbc.Driver"); } public static void main(String[] args) throws SQLException { QueryRunner queryRunner = new QueryRunner(dataSource); // 查询 List<User> userList = queryRunner.query("SELECT * FROM user", new BeanListHandler<User>(User.class)); System.out.println(userList); // 新增 queryRunner.update("INSERT INTO user (name, age) VALUES (?, ?)", "张三", 20); // 修改 queryRunner.update("UPDATE user SET age = ? WHERE name = ?", 21, "张三"); // 删除 queryRunner.update("DELETE FROM user WHERE name = ?", "张三"); } public static class User { private String name; private int age; public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } @Override public String toString() { return "User [name=" + name + ", age=" + age + "]"; } } } ``` 这里使用了c3p0的ComboPooledDataSource来获取数据库连接,并使用QueryRunner来进行数据库操作。以上代码中的User类仅作为示例,你可以根据自己的需求修改。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值