以下の3パターンのアプリケーション実装方法の例を示します。
入出力にCSVファイルを使用するBatchアプリケーションの開発
入出力にデータベースを使用するBatchアプリケーションの開発
条件分岐するBatchアプリケーションの開発
ポイント
Interstage Studio上におけるSpring Batchアプリケーション開発用プロジェクトの作成方法については、“4.9.6 Spring IDEによるSpring Batchアプリケーションの作成”を参照してください。
入出力データにCSVファイルを使用するBatchアプリケーションの開発手順を説明します
以下の手順は、Spring Batchで入出力データにcsvファイルを使用するために必要な手順です。
JobRepository定義の作成
JobLauncher定義の作成
Job定義の作成
Step定義の作成
ItemReader定義の作成
ItemWriter定義の作成
チャンクモデル定義の作成
プロパティファイルに接続先情報を定義します。
データソースの接続先情報(batch.properties):
datasource.driver= org.postgresql.Driver |
JobRepositoryにて使用するデータソースとトランザクションを定義し、JobRepository定義を作成します。データソース定義にはプロパティファイルの値を使用してください。
設定ファイル(context.xml):
<context:property-placeholder location="batch.properties" /> <bean id="jobRepository_DataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource"> <property name="driverClassName" value="${datasource.driver}" /> <property name="url" value="${datasource.url}" /> <property name="username" value="${datasource.username}" /> <property name="password" value="${datasource.password}" /> </bean> <bean id="jdbcTransactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager"> <property name="dataSource" ref="jobRepository_DataSource" /> </bean> <batch:job-repository id="testJobRepository" transaction-manager="jdbcTransactionManager" data-source="jobRepository_DataSource" /> |
JobLauncher定義を作成します。JobLauncher定義には、使用するJobRepositoryを定義してください。
設定ファイル(context.xml):
<bean id="jobLauncher" class="org.springframework.batch.core.launch.support.SimpleJobLauncher"> <property name="jobRepository" ref="testJobRepository" /> </bean> |
Job定義を作成します。
Job定義ファイル(job.xml):
<batch:job id="testJob" job-repository="testJobRepository"> |
Step実行時に使用するトランザクションを定義し、手順3で作成したJob定義内にStep定義を追加します。
Job定義ファイル(job.xml):
<bean id="resourcelessTransactionManager" class="org.springframework.batch.support.transaction.ResourcelessTransactionManager" /> <batch:job id="testJob"> <batch:step id="step1"> <batch:tasklet transaction-manager="resourcelessTransactionManager"> </batch:tasklet> </batch:step> </batch:job> |
入力データとして複数のcsvファイルを使用するItemReader定義を作成します。
Job定義ファイル(job.xml):
<bean id="multiResourceItemReader" class=" org.springframework.batch.item.file.MultiResourceItemReader"> <property name="resources" value="file:/csv/input/test*.csv" /> <property name="delegate" ref="flatFileItemReader" /> </bean> <bean id="flatFileItemReader" class="org.springframework.batch.item.file.FlatFileItemReader"> <property name="lineMapper"> <bean class="org.springframework.batch.item.file.mapping.PassThroughLineMapper" /> </property> </bean> |
複数のcsvファイルにデータを出力するItemReader定義を作成します。本例では、MultiResourceItemWriterを使用して複数ファイル出力を行うため、SuffixCreatorクラスを作成します。
SuffixCreatorクラス(OutputFileSuffixCreator.java):
… public class OutputFileSuffixCreator implements ResourceSuffixCreator { public String getSuffix(int arg0) { return arg0 + ".csv"; } } |
Job定義ファイル(job.xml):
<bean id="outputSuffixCreator" class="example.OutputFileSuffixCreator" /> <bean id="multiResourceItemWriter" class="org.springframework.batch.item.file.MultiResourceItemWriter"> <property name="resource" value="file:/csv/output/test" /> <property name="resourceSuffixCreator" ref="outputSuffixCreator" /> <property name="itemCountLimitPerResource" value="1000" /> <property name="delegate" ref="flatFileItemWriter" /> </bean> <bean id="flatFileItemWriter" class="org.springframework.batch.item.file.FlatFileItemWriter"> <property name="lineAggregator"> <bean class="org.springframework.batch.item.file.transform.PassThroughLineAggregator" /> </property> </bean> |
手順4にて作成したStep定義内に、チャンクモデル定義を追加します。
Job定義ファイル(job.xml):
<bean id="transactionManager" class="org.springframework.batch.support.transaction.ResourcelessTransactionManager" /> <batch:job id="testJob"> <batch:step id="step1"> <batch:tasklet transaction-manager="transactionManager"> <batch:chunk reader="multiResourceItemReader" writer="multiResourceItemWriter" commit-interval="10000" /> </batch:tasklet> </batch:step> </batch:job> |
ポイント
MyBatisを使用したデータベースにアクセスするアプリケーションの作成については、“5.4.5.2 MyBatisを使用するSpring Frameworkのアプリケーションの作成”を参照してください。
ブラウザ経由でMyBatis上のデータを処理するJobを実行するアプリケーションを作成します。
以下の手順1-7は、Spring Batchとして必要な手順です。手順8-10はWebアプリケーションとして必要な手順です。
JobRepository定義の作成
JobLauncher定義の作成
Job定義の作成
Step定義の作成
ItemReader定義の作成
ItemWriter定義の作成
チャンクモデル定義の作成
コントローラの作成
JSP画面の作成
Webアプリケーション設定ファイルの作成
JobRepositoryに使用するデータベースはJNDIに登録したものを使用してください。JobRepository定義を作成します。
設定ファイル(context.xml):
<!-- JNDIリソースの参照 --> <jee:jndi-lookup id="jobRepository_DataSource" jndi-name="postgreDB" /> <!-- トランザクションマネージャ定義 --> <bean id="jdbcTransactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager"> <property name="dataSource" ref="jobRepository_DataSource" /> </bean> <!-- JobRepository定義 --> <batch:job-repository id="testJobRepository" transaction-manager="jdbcTransactionManager" data-source="jobRepository_DataSource" /> |
JobLauncher定義を作成します。JobLauncher定義には、使用するJobRepositoryを定義してください。
Job定義ファイル(job.xml):
<bean id="jobLauncher" class="org.springframework.batch.core.launch.support.SimpleJobLauncher"> <property name="jobRepository" ref="testJobRepository" /> </bean> |
Job定義を作成します。
Job定義ファイル(job.xml):
<batch:job id="testJob" job-repository="testJobRepository"> |
Step実行時に使用するトランザクションを定義し、手順3で作成したJob定義内にStep定義を追加します。本例ではstep1、step2、step3の順に実行するStep定義を作成します。
Job定義ファイル(job.xml):
<!-- JNDIリソースの参照 --> <jee:jndi-lookup id="itemDataSource" jndi-name="itemDB" /> <!-- トランザクションマネージャ定義 --> <bean id="jdbcTransactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager"> <property name="dataSource" ref="itemDataSource" /> </bean> <!-- Job定義 --> <batch:job id="testJob" job-repository="testJobRepository"> <batch:step id="step1" next="step2"> <batch:tasklet transaction-manager="jdbcTransactionManager"> </batch:tasklet> </batch:step> <batch:step id="step2" next="step3"> <batch:tasklet transaction-manager="jdbcTransactionManager"> </batch:tasklet> </batch:step> <batch:step id="step3"> <batch:tasklet transaction-manager="jdbcTransactionManager"> </batch:tasklet> </batch:step> </batch:job> |
ItemReader定義を作成します。データベースからMyBatisを用いて入力データを取得するためには、Mapperクラスが必要です。Mapperクラスで使用するDAOクラスが必要です。
DAOクラス(UserModel.java):
public class UserModel { private int id; private String name; public int getId() { return id; } public void setId(int id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; } } |
Mapperクラス(SQLMapper.java):
public interface SQLMapper { // step1にて使用するSelect文 @Select("SELECT * FROM SELECT_TABLE1 ORDER BY id ASC LIMIT #{_pagesize} OFFSET #{_skiprows} ") UserModel selectUser1(); // step2にて使用するSelect文 @Select("SELECT * FROM SELECT_TABLE2 ORDER BY id ASC LIMIT #{_pagesize} OFFSET #{_skiprows} ") UserModel selectUser2(); // step3にて使用するSelect文 @Select("SELECT * FROM SELECT_TABLE3 ORDER BY id ASC LIMIT #{_pagesize} OFFSET #{_skiprows} ") UserModel selectUser3(); } |
Job定義ファイル(job.xml):
<!-- セッションファクトリ定義 --> <bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean"> <property name="dataSource" ref="itemDataSource" /> </bean> <!-- step1のItemReader定義 --> <bean id="myBatisPagingItemReader1" class="org.mybatis.spring.batch.MyBatisPagingItemReader"> <property name="sqlSessionFactory" ref="sqlSessionFactory" /> <property name="queryId" value="example.mapper.SQLMapper.selectUser1" /> </bean> <!-- step2のItemReader定義 --> <bean id="myBatisPagingItemReader2" class="org.mybatis.spring.batch.MyBatisPagingItemReader"> <property name="sqlSessionFactory" ref="sqlSessionFactory" /> <property name="queryId" value="example.mapper.SQLMapper.selectUser2" /> </bean> <!-- step3のItemReader定義 --> <bean id="myBatisPagingItemReader3" class="org.mybatis.spring.batch.MyBatisPagingItemReader"> <property name="sqlSessionFactory" ref="sqlSessionFactory" /> <property name="queryId" value="example.mapper.SQLMapper.selectUser3" /> </bean> |
ItemWriter定義を作成します。データベースからMyBatisを用いてデータを出力するためには、手順5で作成したMapperクラスにInsert定義を追加します。
Mapperクラス(SQLMapper.java):
public interface SQLMapper { // step1にて使用するSelect文 @Select("SELECT * FROM SELECT_TABLE1 ORDER BY id ASC LIMIT #{_pagesize} OFFSET #{_skiprows} ") UserModel selectUser1(); // step2にて使用するSelect文 @Select("SELECT * FROM SELECT_TABLE2 ORDER BY id ASC LIMIT #{_pagesize} OFFSET #{_skiprows} ") UserModel selectUser2(); // step3にて使用するSelect文 @Select("SELECT * FROM SELECT_TABLE3 ORDER BY id ASC LIMIT #{_pagesize} OFFSET #{_skiprows} ") UserModel selectUser3(); // step1にて使用するInsert文 @Insert("insert into INSERT_TABLE1(NAME,ID) values (#{name}, #{id})") void insertUser1(UserModel usermodel); // step2にて使用するInsert文 @Insert("insert into INSERT_TABLE2(NAME,ID) values (#{name}, #{id})") void insertUser2(UserModel usermodel); // step3にて使用するInsert文 @Insert("insert into INSERT_TABLE3(NAME,ID) values (#{name}, #{id})") void insertUser3(UserModel usermodel); } |
Job定義ファイル(job.xml):
<!-- step1のItemWriter定義 --> <bean id="myBatisBatchItemWriter1" class="org.mybatis.spring.batch.MyBatisBatchItemWriter"> <property name="sqlSessionFactory" ref="sqlSessionFactory" /> <property name="statementId" value="example.mapper.SQLMapper.insertUser1" /> </bean> <!-- step2のItemWriter定義 --> <bean id="myBatisBatchItemWriter2" class="org.mybatis.spring.batch.MyBatisBatchItemWriter"> <property name="sqlSessionFactory" ref="sqlSessionFactory" /> <property name="statementId" value="example.mapper.SQLMapper.insertUser2" /> </bean> <!-- step3のItemWriter定義 --> <bean id="myBatisBatchItemWriter3" class="org.mybatis.spring.batch.MyBatisBatchItemWriter"> <property name="sqlSessionFactory" ref="sqlSessionFactory" /> <property name="statementId" value="example.mapper.SQLMapper.insertUser3" /> </bean> |
手順4にて作成したStep定義内に、チャンクモデル定義を追加します。
Job定義ファイル(job.xml):
<batch:job id="testJob" job-repository="testJobRepository"> <batch:step id="step1" next="step2> <batch:tasklet transaction-manager="jdbcTransactionManager"> <!-- step1のチャンク定義 --> <batch:chunk reader="myBatisPagingItemReader1" writer="myBatisBatchItemWriter1" commit-interval="10000" /> </batch:tasklet> </batch:step> <batch:step id="step2" next="step3"> <batch:tasklet transaction-manager="jdbcTransactionManager"> <!-- step2のチャンク定義 --> <batch:chunk reader="myBatisPagingItemReader2" writer="myBatisBatchItemWriter2" commit-interval="10000" /> </batch:tasklet> </batch:step> <batch:step id="step3"> <batch:tasklet transaction-manager="jdbcTransactionManager"> <!-- step3のチャンク定義 --> <batch:chunk reader="myBatisPagingItemReader3" writer="myBatisBatchItemWriter3" commit-interval="10000" /> </batch:tasklet> </batch:step> </batch:job> |
コントローラを作成します。
コントローラ(JobController.java):
public class JobController { @Autowired JobLauncher jobLauncher; @Autowired Job job; @RequestMapping(value="/job", method=RequestMethod.GET) public String Job1Run() throws Exception { jobLauncher.run(job, JobParameters()); return "end"; } private static JobParameters JobParameters() { Map<String, JobParameter> map = new HashMap<>(); Date date = new Date(); map.put("date", new JobParameter(date.toString())); JobParameters jobParameters = new JobParameters(map); return jobParameters; } } |
JSP画面を作成します。本例では、Jobを実行するための画面とJob実行完了画面の2つを作成します。
Job実行画面(index.jsp):
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%> <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd"> <html> <head> <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"> <title>index</title> </head> <body> <form action="job" method="GET"> Job:<input value="実行" type="submit" /> </form> </body> </html> |
完了画面(end.jsp):
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%> <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd"> <html> <head> <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"> <title>End</title> </head> <body> <H3> <% out.println("End"); %> </H3> </body> </html> |
Webアプリケーション設定ファイルを作成します。
Webアプリケーション設定ファイルは、以下のファイル設定が必要です。
Bean定義ファイル
Interstage deployment descriptor(glassfish-web.xml)
Web application deployment descriptor(web.xml)
Bean定義ファイルを作成します。
Bean定義ファイル(test-servlet.xml):
<?xml version="1.0" encoding="UTF-8"?> … <!-- コンテキストファイルの指定 --> <import resource="classpath:context.xml" /> <!-- Job定義ファイルの指定 --> <import resource="classpath:job.xml" /> <!-- Spring Framework用の定義 --> <context:component-scan base-package="example" /> <!-- MyBatis用の定義 --> <mybatis-spring:scan base-package="example.mapper" /> </beans> |
Interstage deployment descriptorを作成します。Interstage deployment descriptorは、クラスパスの設定を行います。クラスパスの設定については、“4.9.3 アプリケーションのクラスパスの設定(Webアプリケーション)”を参照してください。
Interstage deployment descriptor(glassfish-web.xml):
<!DOCTYPE glassfish-web-app PUBLIC "-//GlassFish.org//DTD GlassFish Application Server 3.1 Servlet 3.0//EN" "http://glassfish.org/dtds/glassfish-web-app_3_0-1.dtd"> <glassfish-web-app> <context-root>/Sample2</context-root> <class-loader delegate="false" extra-class-path="/opt/FJSVibs/lib/classpathhelper/spring43-web-cph.FUJITSU.jar:/opt/FJSVibs/lib/classpathhelper/logback-cph.FUJITSU.jar:/opt/FJSVibs/lib/classpathhelper/spring-batch30-cph.FUJITSU.jar:/opt/FJSVibs/lib/classpathhelper/spring43-orm-mybatis-cph.FUJITSU.jar" /> </glassfish-web-app> |
Web application deployment descriptorを作成します。
Web application deployment descriptor(web.xml):
<?xml version="1.0" encoding="UTF-8"?> <web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" id="WebApp_ID" version="2.5"> <display-name>Sample</display-name> <context-param> <param-name>contextConfigLocation</param-name> <param-value>classpath:test-servlet.xml</param-value> </context-param> <servlet> <servlet-name>test</servlet-name> <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class> <load-on-startup>1</load-on-startup> </servlet> <servlet-mapping> <servlet-name>test</servlet-name> <url-pattern>/</url-pattern> </servlet-mapping> </web-app> |
ポイント
“4.9.4.2 入出力にデータベースを使用するBatchアプリケーションの開発”のアプリケーションを条件分岐するアプリケーションに改修する方法を説明します。
条件分岐するBatchアプリケーションの開発手順を説明します
以下の手順1-7は、Spring Batchとして必要な手順です。手順8-10はWebアプリケーションとして必要な手順です。
JobRepository定義の作成
JobLauncher定義の作成
Job定義の作成
条件分岐するStep定義の作成
ItemReader定義の作成
ItemWriter定義の作成
チャンクモデル定義の作成
コントローラの作成
JSP画面の作成
Webアプリケーション設定ファイルの作成
手順1~3までの各種定義の作成手順は、“4.9.4.2 入出力にデータベースを使用するBatchアプリケーションの開発”と同じものを使用します。
Step実行時に使用するトランザクションを定義し、手順3で作成したJob定義内にStep定義を追加します。本例ではstep1、step2、step3の順に実行し、エラーが発生しても条件分岐して必ずstep3を実行するStep定義を作成します。
Job定義ファイル(job.xml):
<batch:job id="job" job-repository="testJobRepository"> <batch:step id="step1"> <batch:tasklet transaction-manager="jdbcTransactionManager"> </batch:tasklet> <batch:next on="COMPLETED" to="step2" /> <batch:next on="*" to="step3" /> </batch:step> <batch:step id="step2"> <batch:tasklet transaction-manager="jdbcTransactionManager"> </batch:tasklet> <batch:next on="*" to="step3" /> </batch:step> <batch:step id="step3"> <batch:tasklet transaction-manager="jdbcTransactionManager"> </batch:tasklet> </batch:step> </batch:job> |
手順5~6までの各種定義の作成手順は、“4.9.4.2 入出力にデータベースを使用するBatchアプリケーションの開発”と同じものを使用します。
手順4にて作成したStep定義内に、チャンクモデル定義を追加します。
Job定義ファイル(job.xml):
<batch:job id="job" job-repository="testJobRepository"> <batch:step id="step1"> <batch:tasklet transaction-manager="jdbcTransactionManager"> <!-- step1のチャンク定義 --> <batch:chunk reader="myBatisPagingItemReader1" writer="myBatisBatchItemWriter1" commit-interval="10000" /> </batch:tasklet> <batch:next on="COMPLETED" to="step2" /> <batch:next on="*" to="step3" /> </batch:step> <batch:step id="step2"> <batch:tasklet transaction-manager="jdbcTransactionManager"> <!-- step2のチャンク定義 --> <batch:chunk reader="myBatisPagingItemReader2" writer="myBatisBatchItemWriter2" commit-interval="10000" /> </batch:tasklet> <batch:next on="*" to="step3" /> </batch:step> <batch:step id="step3"> <batch:tasklet transaction-manager="jdbcTransactionManager"> <!-- step3のチャンク定義 --> <batch:chunk reader="myBatisPagingItemReader3" writer="myBatisBatchItemWriter3" commit-interval="10000" /> </batch:tasklet> </batch:step> </batch:job> |
手順8~10までの各種定義の作成手順は、“4.9.4.2 入出力にデータベースを使用するBatchアプリケーションの開発”と同じものを使用します。