Spring04_IOC and DI in action

For the source code of this tutorial, please visit: tutorial_demo

Before learning this tutorial, you need to know (use it if you want) the following:

  • Database connection pool c3p0;
  • Apache Commons DbUtils.

Learning without practicing is false. Next, we use the knowledge of IOC and DI learned before to combine Apache Commons DbUtils to implement CRUD operation of single table.

1, Requirements and technical requirements

1.1 demand

Implement CRUD of single table

1.2 technical requirements

  1. Using Spring's IOC to manage objects;
  2. Using Spring's DI to implement attribute injection;
  3. Use Apache Commons DbUtils for persistence layer operation;
  4. Use c3p0 database connection pool.

2, Implementation process

2.1. Building database and table

DROP DATABASE IF EXISTS springlearn;
CREATE DATABASE springlearn;
USE springlearn;


DROP TABLE IF EXISTS account;
CREATE TABLE account (
  id int(11) NOT NULL AUTO_INCREMENT,
  name varchar(40) DEFAULT NULL,
  money float DEFAULT NULL,
  PRIMARY KEY (id)
) ENGINE=InnoDB AUTO_INCREMENT=8 DEFAULT CHARSET=utf8mb4;

INSERT INTO account VALUES ('1', 'aaa', '1000');
INSERT INTO account VALUES ('2', 'bbb', '1000');
INSERT INTO account VALUES ('3', 'ccc', '1000');
INSERT INTO account VALUES ('5', 'cc', '10000');
INSERT INTO account VALUES ('6', 'abc', '10000');
INSERT INTO account VALUES ('7', 'abc', '10000');

2.2 create Maven project and add relevant coordinates

<?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>org.codeaction</groupId>
    <artifactId>account</artifactId>
    <version>1.0-SNAPSHOT</version>
    <packaging>jar</packaging>

    <dependencies>
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-context</artifactId>
            <version>5.2.6.RELEASE</version>
        </dependency>
        <dependency>
            <groupId>commons-dbutils</groupId>
            <artifactId>commons-dbutils</artifactId>
            <version>1.4</version>
        </dependency>
        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <version>5.1.47</version>
        </dependency>
        <dependency>
            <groupId>c3p0</groupId>
            <artifactId>c3p0</artifactId>
            <version>0.9.1.2</version>
        </dependency>
        <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
            <version>4.13</version>
            <scope>test</scope>
        </dependency>
    </dependencies>
</project>

2.3. Write Account entity class

package org.codeaction.domain;

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 +
                '}';
    }
}

2.4. Write IAccountDao

package org.codeaction.dao;

import org.codeaction.domain.Account;

import java.util.List;

public interface IAccountDao {
    List<Account> findAll();
    Account findById(Integer id);
    void save(Account account);
    void update(Account account);
    void delete(Integer id);
}

2.5 write a persistence layer implementation class IAccountDaoImpl

package org.codeaction.dao.impl;

import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanHandler;
import org.apache.commons.dbutils.handlers.BeanListHandler;
import org.codeaction.dao.IAccountDao;
import org.codeaction.domain.Account;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;

import java.sql.SQLException;
import java.util.List;

public class AccountDaoImpl implements IAccountDao {
    private QueryRunner queryRunner;

    public void setQueryRunner(QueryRunner queryRunner) {
        this.queryRunner = queryRunner;
    }

    @Override
    public List<Account> findAll() {
        List<Account> list = null;
        try {
            list = queryRunner.query("select * from account", new BeanListHandler<Account>(Account.class));
        } catch (SQLException e) {
            e.printStackTrace();
        }
        return list;
    }

    @Override
    public Account findById(Integer id) {
        Account account = null;
        try {
            account = queryRunner.query("select * from account where id = ?",
                    new BeanHandler<Account>(Account.class), id);
        } catch (SQLException e) {
            e.printStackTrace();
        }
        return account;
    }

    @Override
    public void save(Account account) {
        Object[] params = {account.getName(), account.getMoney()};
        try {
            queryRunner.update("insert into account(name, money) values(?, ?)", params);
        } catch (SQLException e) {
            e.printStackTrace();
        }
    }

    @Override
    public void update(Account account) {
        Object[] params = {account.getName(), account.getMoney(), account.getId()};
        try {
            queryRunner.update("update account set name=?, money=? where id=?", params);
        } catch (SQLException e) {
            e.printStackTrace();
        }
    }

    @Override
    public void delete(Integer id) {
        Object[] params = {id};
        try {
            queryRunner.update("delete from account where id=?", id);
        } catch (SQLException e) {
            e.printStackTrace();
        }
    }
}

2.6. Write business layer interface IAccountService

package org.codeaction.service;

import org.codeaction.domain.Account;

import java.util.List;

public interface IAccountService {
    List<Account> findAll();
    Account findById(Integer id);
    void save(Account account);
    void update(Account account);
    void delete(Integer id);
}

2.7 write the business layer implementation class IAccountServiceImpl

package org.codeaction.service.impl;

import org.codeaction.dao.IAccountDao;
import org.codeaction.domain.Account;
import org.codeaction.service.IAccountService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.List;

public class AccountServiceImpl implements IAccountService {
    private IAccountDao accountDao;

    public void setAccountDao(IAccountDao accountDao) {
        this.accountDao = accountDao;
    }

    @Override
    public List<Account> findAll() {
        return accountDao.findAll();
    }

    @Override
    public Account findById(Integer id) {
        return accountDao.findById(id);
    }

    @Override
    public void save(Account account) {
        accountDao.save(account);
    }

    @Override
    public void update(Account account) {
        accountDao.update(account);
    }

    @Override
    public void delete(Integer id) {
        accountDao.delete(id);
    }
}

2.8 write XML configuration file (key)

The XML configuration file is in the resource directory

<?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"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
        https://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/context
        https://www.springframework.org/schema/context/spring-context.xsd">
    <!-- to configure service -->
    <bean id="accountService" class="org.codeaction.service.impl.AccountServiceImpl">
        <!-- adopt set Method injection dao Object of implementation class -->
        <property name="accountDao" ref="accountDao"></property>
    </bean>
    <!-- to configure dao -->
    <bean id="accountDao" class="org.codeaction.dao.impl.AccountDaoImpl">
        <!-- adopt set Method injection queryRunner Object of implementation class -->
        <property name="queryRunner" ref="queryRunner"></property>
    </bean>
    <!-- to configure queryRunner -->
    <bean id="queryRunner" class="org.apache.commons.dbutils.QueryRunner" scope="prototype">
        <!-- Inject connection pool by construction method -->
        <constructor-arg name="ds" ref="dataSource"></constructor-arg>
    </bean>
    <!-- Configure connection pool -->
    <bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
        <!-- adopt set Four parameters of method injection -->
        <property name="driverClass" value="com.mysql.jdbc.Driver"></property>
        <property name="jdbcUrl" value="jdbc:mysql://localhost:3306/springlearn"></property>
        <property name="user" value="root"></property>
        <property name="password" value="123456"></property>
    </bean>
</beans>

Spring configuration file is the core of this project, and it is also used to realize IOC and DI through the configuration of this configuration file. Combined with the previous Java code, the bean configuration is managed by the spring container through IOC, and the properties are injected by the spring container through DI.

2.9 write test class

package org.codeaction.test;

import org.codeaction.domain.Account;
import org.codeaction.service.IAccountService;
import org.codeaction.service.impl.AccountServiceImpl;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

import java.util.List;

public class MyTest {
    private IAccountService accountService;
    @Before
    public void init() {
        ApplicationContext context = new ClassPathXmlApplicationContext("beans.xml");
        accountService = context.getBean("accountService", AccountServiceImpl.class);
    }

    @Test
    public void testFindAll() {
        List<Account> accounts = accountService.findAll();
        for (Account account : accounts) {
            System.out.println(account);
        }
    }

    @Test
    public void testFindById() {
        Account account = accountService.findById(3);
        System.out.println(account);
    }

    @Test
    public void testSave() {
        Account account = new Account();
        account.setName("abc");
        account.setMoney(10000F);

        accountService.save(account);

        System.out.println(account);
    }

    @Test
    public void testDelete() {
        accountService.delete(4);
    }

    @Test
    public void testUpdate() {
        Account account = new Account();
        account.setId(5);
        account.setName("ab111111111c111");
        account.setMoney(10000F);
        accountService.update(account);
    }
}

Run the test methods separately.

Tags: Java Apache Spring Database

Posted on Mon, 25 May 2020 08:51:45 -0700 by squiblo