spring+batch+multiple+reader+hibernate+writer
Click here to download eclipse supported ZIP file
This is Main.java file having the source code to execute business logic.
package com.cv.springbatch;
import org.apache.log4j.Logger;
import org.springframework.batch.core.Job;
import org.springframework.batch.core.JobExecution;
import org.springframework.batch.core.JobExecutionException;
import org.springframework.batch.core.JobParameters;
import org.springframework.batch.core.launch.JobLauncher;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
/**
* @author Chandra Vardhan
*/
public class Main {
private static final Logger LOGGER = Logger.getLogger(Main.class);
@SuppressWarnings("resource")
public static void main(String args[]) {
LOGGER.info("Entered into Main.main()");
ApplicationContext context = new ClassPathXmlApplicationContext(
"spring-batch-context.xml");
JobLauncher jobLauncher = (JobLauncher) context.getBean("jobLauncher");
Job job = (Job) context.getBean("resultJob");
try {
JobExecution execution = jobLauncher.run(job, new JobParameters());
LOGGER.info("Job Exit Status : " + execution.getStatus());
} catch (JobExecutionException e) {
LOGGER.info("Job ExamResult failed");
e.printStackTrace();
}
LOGGER.info("Exiting from Main.main()");
}
} |
This is Result.java file having the source code to execute business logic.
package com.cv.springbatch.model;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;
import org.hibernate.annotations.Type;
import org.joda.time.LocalDate;
@Entity
@Table(name = "RESULT")
public class Result {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private long id;
@Column(name = "STUDENT_NAME", nullable = false)
private String studentName;
@Column(name = "DOB", nullable = false)
@Type(type="org.jadira.usertype.dateandtime.joda.PersistentLocalDate")
private LocalDate dob;
@Column(name = "PERCENTAGE", nullable = false)
private double percentage;
public long getId() {
return id;
}
public void setId(long id) {
this.id = id;
}
public String getStudentName() {
return studentName;
}
public void setStudentName(String studentName) {
this.studentName = studentName;
}
public LocalDate getDob() {
return dob;
}
public void setDob(LocalDate dob) {
this.dob = dob;
}
public double getPercentage() {
return percentage;
}
public void setPercentage(double percentage) {
this.percentage = percentage;
}
@Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + (int) (id ^ (id >>> 32));
return result;
}
@Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (!(obj instanceof Result))
return false;
Result other = (Result) obj;
if (id != other.id)
return false;
return true;
}
@Override
public String toString() {
return "Result [id=" + id + ", studentName=" + studentName
+ ", dob=" + dob + ", percentage=" + percentage + "]";
}
} |
This is ResultFieldSetMapper.java file having the source code to execute business logic.
package com.cv.springbatch;
import org.joda.time.LocalDate;
import org.springframework.batch.item.file.mapping.FieldSetMapper;
import org.springframework.batch.item.file.transform.FieldSet;
import org.springframework.validation.BindException;
import com.cv.springbatch.model.Result;
public class ResultFieldSetMapper implements FieldSetMapper<Result>{
public Result mapFieldSet(FieldSet fieldSet) throws BindException {
Result result = new Result();
result.setStudentName(fieldSet.readString(0));
result.setDob(new LocalDate(fieldSet.readDate(1,"dd/MM/yyyy")));
result.setPercentage(fieldSet.readDouble(2));
return result;
}
} |
This is ResultItemProcessor.java file having the source code to execute business logic.
package com.cv.springbatch;
import org.apache.log4j.Logger;
import org.springframework.batch.item.ItemProcessor;
import com.cv.springbatch.model.Result;
public class ResultItemProcessor implements ItemProcessor<Result, Result> {
private static final Logger LOGGER = Logger.getLogger(ResultItemProcessor.class);
public Result process(Result result) throws Exception {
LOGGER.info("Processing result :"+result);
/*
* Only return results which are more than 60%
*
*/
if(result.getPercentage() < 60){
return null;
}
return result;
}
} |
This is ResultJobListener.java file having the source code to execute business logic.
package com.cv.springbatch;
import java.util.List;
import org.apache.log4j.Logger;
import org.joda.time.DateTime;
import org.springframework.batch.core.BatchStatus;
import org.springframework.batch.core.JobExecution;
import org.springframework.batch.core.JobExecutionListener;
public class ResultJobListener implements JobExecutionListener{
private static final Logger LOGGER = Logger.getLogger(ResultJobListener.class);
private DateTime startTime, stopTime;
public void beforeJob(JobExecution jobExecution) {
startTime = new DateTime();
LOGGER.info("Result Job starts at :"+startTime);
}
public void afterJob(JobExecution jobExecution) {
stopTime = new DateTime();
LOGGER.info("Result Job stops at :"+stopTime);
LOGGER.info("Total time take in millis :"+getTimeInMillis(startTime , stopTime));
if(jobExecution.getStatus() == BatchStatus.COMPLETED){
LOGGER.info("Result job completed successfully");
//Here you can perform some other business logic like cleanup
}else if(jobExecution.getStatus() == BatchStatus.FAILED){
LOGGER.info("Result job failed with following exceptions ");
List<Throwable> exceptionList = jobExecution.getAllFailureExceptions();
for(Throwable th : exceptionList){
System.err.println("exception :" +th.getLocalizedMessage());
}
}
}
private long getTimeInMillis(DateTime start, DateTime stop){
return stop.getMillis() - start.getMillis();
}
} |
This is pom.xml file having the entries of dependency jars and information to build the application .
| <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.cv.springbatch</groupId>
<artifactId>SpringBatchMultiReaderHibernateWriter</artifactId>
<version>1.0.0</version>
<packaging>jar</packaging>
<name>SpringBatchMultiReaderHibernateWriter</name>
<properties>
<springframework.version>4.2.0.RELEASE</springframework.version>
3.0.1.RELEASE
<hibernate.version>4.3.6.Final</hibernate.version>
3.18.1-GA
<mysql.version>5.1.31</mysql.version>
<joda-time.version>2.3</joda-time.version>
0.9.5-pre8
</properties>
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
<version>${springframework.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-tx</artifactId>
<version>${springframework.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-orm</artifactId>
<version>${springframework.version}</version>
</dependency>
<dependency>
<groupId>org.springframework.batch</groupId>
<artifactId>spring-batch-core</artifactId>
<version>${springbatch.version}</version>
</dependency>
<dependency>
<groupId>org.springframework.batch</groupId>
<artifactId>spring-batch-infrastructure</artifactId>
<version>${springbatch.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>${springframework.version}</version>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-core</artifactId>
<version>${hibernate.version}</version>
</dependency>
<dependency>
<groupId>org.javassist</groupId>
<artifactId>javassist</artifactId>
<version>${javassist.version}</version>
</dependency>
<dependency>
<groupId>joda-time</groupId>
<artifactId>joda-time</artifactId>
<version>${joda-time.version}</version>
</dependency>
<dependency>
<groupId>org.jadira.usertype</groupId>
<artifactId>usertype.core</artifactId>
<version>3.0.0.CR1</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>${mysql.version}</version>
</dependency>
<dependency>
<groupId>com.mchange</groupId>
<artifactId>c3p0</artifactId>
<version>${c3p0.version}</version>
</dependency>
<dependency>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
<version>1.2.16</version>
</dependency>
</dependencies>
</project> |
This is context-datasource.xml spring configuration file and these entries are used in the application.
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:batch="http://www.springframework.org/schema/batch" 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-4.0.xsd"> <bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource" destroy-method="close"> <property name="driverClass" value="com.mysql.jdbc.Driver" /> <property name="jdbcUrl" value="jdbc:mysql://localhost:3306/hibernate" /> <property name="user" value="root" /> <property name="password" value="root" /> </bean> </beans>
|
This is context-model.xml spring configuration file and these entries are used in the application.
<?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:tx="http://www.springframework.org/schema/tx" xmlns:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.0.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.0.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-4.0.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-4.0.xsd" default-autowire="byName" default-init-method="init"> <import resource="classpath:context-datasource.xml"/> <bean id="sessionFactory" class="org.springframework.orm.hibernate4.LocalSessionFactoryBean" > <property name="dataSource" ref="dataSource"/> <property name="packagesToScan"> <list> <value>com.cv.springbatch.model</value> </list> </property> <property name="hibernateProperties"> <props> <prop key="hibernate.dialect">org.hibernate.dialect.MySQLDialect</prop> <prop key="hibernate.show_sql">true</prop> <prop key="hibernate.format_sql">true</prop> <prop key="hibernate.hbm2ddl.auto">update</prop> </props> </property> </bean> <bean id="transactionManager" class="org.springframework.orm.hibernate4.HibernateTransactionManager" /> <tx:annotation-driven transaction-manager="transactionManager"/> </beans>
|
This is spring-batch-context.xml spring configuration file and these entries are used in the application.
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:batch="http://www.springframework.org/schema/batch" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/batch http://www.springframework.org/schema/batch/spring-batch-3.0.xsd http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.0.xsd"> <import resource="classpath:context-model.xml"/>
<!-- JobRepository and JobLauncher are configuration/setup classes --> <bean id="jobRepository" class="org.springframework.batch.core.repository.support.MapJobRepositoryFactoryBean" /> <bean id="jobLauncher" class="org.springframework.batch.core.launch.support.SimpleJobLauncher"> <property name="jobRepository" ref="jobRepository" /> </bean>
<bean id="multiResourceItemReader" class="org.springframework.batch.item.file.MultiResourceItemReader"> <property name="resources" value="classpath:csv/Result*.txt" /> <property name="delegate" ref="flatFileItemReader" /> </bean> <!-- ItemReader reads a complete line one by one from input file --> <bean id="flatFileItemReader" class="org.springframework.batch.item.file.FlatFileItemReader" scope="step"> <property name="lineMapper"> <bean class="org.springframework.batch.item.file.mapping.DefaultLineMapper"> <property name="fieldSetMapper"> <!-- Mapper which maps each individual items in a record to properties in POJO --> <bean class="com.cv.springbatch.ResultFieldSetMapper" /> </property> <property name="lineTokenizer"> <!-- A tokenizer class to be used when items in input record are separated by specific characters --> <bean class="org.springframework.batch.item.file.transform.DelimitedLineTokenizer"> <property name="delimiter" value="|" /> </bean> </property> </bean> </property> </bean>
<!-- ItemWriter which writes data to database --> <bean id="databaseItemWriter" class="org.springframework.batch.item.database.HibernateItemWriter"> <property name="sessionFactory" ref="sessionFactory" /> </bean>
<!-- Optional ItemProcessor to perform business logic/filtering on the input records --> <bean id="itemProcessor" class="com.cv.springbatch.ResultItemProcessor" /> <!-- Optional JobExecutionListener to perform business logic before and after the job --> <bean id="jobListener" class="com.cv.springbatch.ResultJobListener" />
<!-- Actual Job --> <batch:job id="resultJob"> <batch:step id="step1"> <batch:tasklet transaction-manager="transactionManager"> <batch:chunk reader="multiResourceItemReader" writer="databaseItemWriter" processor="itemProcessor" commit-interval="10" /> </batch:tasklet> </batch:step> <batch:listeners> <batch:listener ref="jobListener" /> </batch:listeners> </batch:job> </beans>
|
This is log4j.properties file having the entries for logging the information into the console/file.
#By default enabling Console appender # Root logger option log4j.rootLogger=INFO, stdout
# Redirect log messages to console log4j.appender.stdout=org.apache.log4j.ConsoleAppender log4j.appender.stdout.Target=System.out log4j.appender.stdout.layout=org.apache.log4j.PatternLayout log4j.appender.stdout.layout.ConversionPattern=%-5p [%c]:%L -->> %m%n
# Redirect log messages to a log file #log4j.appender.file=org.apache.log4j.RollingFileAppender #log4j.appender.file.File=C:\servlet-application.log #log4j.appender.file.MaxFileSize=5MB #log4j.appender.file.MaxBackupIndex=10 #log4j.appender.file.layout=org.apache.log4j.PatternLayout #log4j.appender.file.layout.ConversionPattern=%d{yyyy-MM-dd HH:mm:ss} %-5p %c{1}:%L - %m%n
|
No comments:
Post a Comment