Skip to content

Commit f3936e2

Browse files
author
Eugen
committed
Merge pull request eugenp#303 from DevendraDesale/master
Adding spring batch intro project.
2 parents c5eb1c5 + b7bbd20 commit f3936e2

File tree

13 files changed

+513
-0
lines changed

13 files changed

+513
-0
lines changed

spring-batch-intro/.classpath

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<classpath>
3+
<classpathentry kind="src" output="target/classes" path="src/main/java">
4+
<attributes>
5+
<attribute name="optional" value="true"/>
6+
<attribute name="maven.pomderived" value="true"/>
7+
</attributes>
8+
</classpathentry>
9+
<classpathentry kind="src" output="target/test-classes" path="src/test/java">
10+
<attributes>
11+
<attribute name="optional" value="true"/>
12+
<attribute name="maven.pomderived" value="true"/>
13+
</attributes>
14+
</classpathentry>
15+
<classpathentry including="**/*.java" kind="src" path="src/main/resources"/>
16+
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/J2SE-1.5">
17+
<attributes>
18+
<attribute name="maven.pomderived" value="true"/>
19+
</attributes>
20+
</classpathentry>
21+
<classpathentry kind="con" path="org.eclipse.m2e.MAVEN2_CLASSPATH_CONTAINER">
22+
<attributes>
23+
<attribute name="maven.pomderived" value="true"/>
24+
</attributes>
25+
</classpathentry>
26+
<classpathentry kind="output" path="target/classes"/>
27+
</classpath>

spring-batch-intro/.project

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<projectDescription>
3+
<name>spring-batch-intro</name>
4+
<comment></comment>
5+
<projects>
6+
</projects>
7+
<buildSpec>
8+
<buildCommand>
9+
<name>org.eclipse.jdt.core.javabuilder</name>
10+
<arguments>
11+
</arguments>
12+
</buildCommand>
13+
<buildCommand>
14+
<name>org.eclipse.m2e.core.maven2Builder</name>
15+
<arguments>
16+
</arguments>
17+
</buildCommand>
18+
</buildSpec>
19+
<natures>
20+
<nature>org.eclipse.jdt.core.javanature</nature>
21+
<nature>org.eclipse.m2e.core.maven2Nature</nature>
22+
</natures>
23+
</projectDescription>

spring-batch-intro/pom.xml

Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
2+
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
3+
<modelVersion>4.0.0</modelVersion>
4+
5+
<groupId>org.baeldung</groupId>
6+
<artifactId>spring-batch-intro</artifactId>
7+
<version>0.1-SNAPSHOT</version>
8+
<packaging>jar</packaging>
9+
10+
<name>spring-batch-intro</name>
11+
<url>http://maven.apache.org</url>
12+
13+
<properties>
14+
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
15+
<spring.version>4.2.0.RELEASE</spring.version>
16+
<spring.batch.version>3.0.5.RELEASE</spring.batch.version>
17+
<sqlite.version>3.8.11.2</sqlite.version>
18+
</properties>
19+
20+
<dependencies>
21+
<!-- SQLite database driver -->
22+
<dependency>
23+
<groupId>org.xerial</groupId>
24+
<artifactId>sqlite-jdbc</artifactId>
25+
<version>${sqlite.version}</version>
26+
</dependency>
27+
<dependency>
28+
<groupId>org.springframework</groupId>
29+
<artifactId>spring-oxm</artifactId>
30+
<version>${spring.version}</version>
31+
</dependency>
32+
<dependency>
33+
<groupId>org.springframework</groupId>
34+
<artifactId>spring-jdbc</artifactId>
35+
<version>${spring.version}</version>
36+
</dependency>
37+
<dependency>
38+
<groupId>org.springframework.batch</groupId>
39+
<artifactId>spring-batch-core</artifactId>
40+
<version>${spring.batch.version}</version>
41+
</dependency>
42+
</dependencies>
43+
44+
</project>
Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
package org.baeldung.spring_batch_intro;
2+
3+
import org.springframework.batch.core.Job;
4+
import org.springframework.batch.core.JobExecution;
5+
import org.springframework.batch.core.JobParameters;
6+
import org.springframework.batch.core.launch.JobLauncher;
7+
import org.springframework.context.ApplicationContext;
8+
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
9+
import org.springframework.context.support.ClassPathXmlApplicationContext;
10+
11+
12+
public class App {
13+
public static void main(String[] args) {
14+
// Spring Java config
15+
AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext();
16+
context.register(SpringConfig.class);
17+
context.register(SpringBatchConfig.class);
18+
context.refresh();
19+
20+
// Spring xml config
21+
// ApplicationContext context = new ClassPathXmlApplicationContext(
22+
// "spring-batch-intro.xml");
23+
24+
JobLauncher jobLauncher = (JobLauncher) context.getBean("jobLauncher");
25+
Job job = (Job) context.getBean("firstBatchJob");
26+
System.out.println("Starting the batch job");
27+
try {
28+
JobExecution execution = jobLauncher.run(job, new JobParameters());
29+
System.out.println("Job Status : " + execution.getStatus());
30+
System.out.println("Job succeeded");
31+
} catch (Exception e) {
32+
e.printStackTrace();
33+
System.out.println("Job failed");
34+
}
35+
}
36+
}
Lines changed: 93 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,93 @@
1+
package org.baeldung.spring_batch_intro;
2+
3+
import java.net.MalformedURLException;
4+
import java.text.ParseException;
5+
6+
import org.baeldung.spring_batch_intro.model.Transaction;
7+
import org.baeldung.spring_batch_intro.service.CustomItemProcessor;
8+
import org.baeldung.spring_batch_intro.service.RecordFieldSetMapper;
9+
import org.springframework.batch.core.Job;
10+
import org.springframework.batch.core.Step;
11+
import org.springframework.batch.core.configuration.annotation.JobBuilderFactory;
12+
import org.springframework.batch.core.configuration.annotation.StepBuilderFactory;
13+
import org.springframework.batch.item.ItemProcessor;
14+
import org.springframework.batch.item.ItemReader;
15+
import org.springframework.batch.item.ItemWriter;
16+
import org.springframework.batch.item.UnexpectedInputException;
17+
import org.springframework.batch.item.file.FlatFileItemReader;
18+
import org.springframework.batch.item.file.mapping.DefaultLineMapper;
19+
import org.springframework.batch.item.file.transform.DelimitedLineTokenizer;
20+
import org.springframework.batch.item.xml.StaxEventItemWriter;
21+
import org.springframework.beans.factory.annotation.Autowired;
22+
import org.springframework.beans.factory.annotation.Qualifier;
23+
import org.springframework.beans.factory.annotation.Value;
24+
import org.springframework.context.annotation.Bean;
25+
import org.springframework.core.io.Resource;
26+
import org.springframework.oxm.Marshaller;
27+
import org.springframework.oxm.jaxb.Jaxb2Marshaller;
28+
29+
public class SpringBatchConfig {
30+
@Autowired
31+
private JobBuilderFactory jobs;
32+
33+
@Autowired
34+
private StepBuilderFactory steps;
35+
36+
@Value("input/record.csv")
37+
private Resource inputCsv;
38+
39+
@Value("file:xml/output.xml")
40+
private Resource outputXml;
41+
42+
@Bean
43+
public ItemReader<Transaction> itemReader()
44+
throws UnexpectedInputException, ParseException {
45+
FlatFileItemReader<Transaction> reader = new FlatFileItemReader<Transaction>();
46+
DelimitedLineTokenizer tokenizer = new DelimitedLineTokenizer();
47+
String[] tokens = { "username", "userid", "transactiondate", "amount" };
48+
tokenizer.setNames(tokens);
49+
reader.setResource(inputCsv);
50+
DefaultLineMapper<Transaction> lineMapper = new DefaultLineMapper<Transaction>();
51+
lineMapper.setLineTokenizer(tokenizer);
52+
lineMapper.setFieldSetMapper(new RecordFieldSetMapper());
53+
reader.setLinesToSkip(1);
54+
reader.setLineMapper(lineMapper);
55+
return reader;
56+
}
57+
58+
@Bean
59+
public ItemProcessor<Transaction, Transaction> itemProcessor() {
60+
return new CustomItemProcessor();
61+
}
62+
63+
@Bean
64+
public ItemWriter<Transaction> itemWriter(Marshaller marshaller)
65+
throws MalformedURLException {
66+
StaxEventItemWriter<Transaction> itemWriter = new StaxEventItemWriter<Transaction>();
67+
itemWriter.setMarshaller(marshaller);
68+
itemWriter.setRootTagName("transactionRecord");
69+
itemWriter.setResource(outputXml);
70+
return itemWriter;
71+
}
72+
73+
@Bean
74+
public Marshaller marshaller() {
75+
Jaxb2Marshaller marshaller = new Jaxb2Marshaller();
76+
marshaller.setClassesToBeBound(new Class[] { Transaction.class });
77+
return marshaller;
78+
}
79+
80+
@Bean
81+
protected Step step1(ItemReader<Transaction> reader,
82+
ItemProcessor<Transaction, Transaction> processor,
83+
ItemWriter<Transaction> writer) {
84+
return steps.get("step1").<Transaction, Transaction> chunk(10)
85+
.reader(reader).processor(processor).writer(writer).build();
86+
}
87+
88+
@Bean(name = "firstBatchJob")
89+
public Job job(@Qualifier("step1") Step step1) {
90+
return jobs.get("firstBatchJob").start(step1).build();
91+
}
92+
93+
}
Lines changed: 79 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,79 @@
1+
package org.baeldung.spring_batch_intro;
2+
3+
import java.net.MalformedURLException;
4+
5+
import javax.sql.DataSource;
6+
7+
import org.springframework.batch.core.configuration.annotation.EnableBatchProcessing;
8+
import org.springframework.batch.core.launch.JobLauncher;
9+
import org.springframework.batch.core.launch.support.SimpleJobLauncher;
10+
import org.springframework.batch.core.repository.JobRepository;
11+
import org.springframework.batch.core.repository.support.JobRepositoryFactoryBean;
12+
import org.springframework.batch.support.transaction.ResourcelessTransactionManager;
13+
import org.springframework.beans.factory.annotation.Value;
14+
import org.springframework.context.annotation.Bean;
15+
import org.springframework.context.annotation.Configuration;
16+
import org.springframework.core.io.Resource;
17+
import org.springframework.jdbc.datasource.DriverManagerDataSource;
18+
import org.springframework.jdbc.datasource.init.DataSourceInitializer;
19+
import org.springframework.jdbc.datasource.init.ResourceDatabasePopulator;
20+
import org.springframework.transaction.PlatformTransactionManager;
21+
22+
@Configuration
23+
@EnableBatchProcessing
24+
public class SpringConfig {
25+
26+
@Value("org/springframework/batch/core/schema-drop-sqlite.sql")
27+
private Resource dropReopsitoryTables;
28+
29+
@Value("org/springframework/batch/core/schema-sqlite.sql")
30+
private Resource dataReopsitorySchema;
31+
32+
@Bean
33+
public DataSource dataSource() {
34+
DriverManagerDataSource dataSource = new DriverManagerDataSource();
35+
dataSource.setDriverClassName("org.sqlite.JDBC");
36+
dataSource.setUrl("jdbc:sqlite:repository.sqlite");
37+
return dataSource;
38+
}
39+
40+
@Bean
41+
public DataSourceInitializer dataSourceInitializer(DataSource dataSource)
42+
throws MalformedURLException {
43+
ResourceDatabasePopulator databasePopulator = new ResourceDatabasePopulator();
44+
45+
databasePopulator.addScript(dropReopsitoryTables);
46+
databasePopulator.addScript(dataReopsitorySchema);
47+
databasePopulator.setIgnoreFailedDrops(true);
48+
49+
DataSourceInitializer initializer = new DataSourceInitializer();
50+
initializer.setDataSource(dataSource);
51+
initializer.setDatabasePopulator(databasePopulator);
52+
53+
return initializer;
54+
}
55+
56+
private JobRepository getJobRepository() throws Exception {
57+
JobRepositoryFactoryBean factory = new JobRepositoryFactoryBean();
58+
factory.setDataSource(dataSource());
59+
factory.setTransactionManager(getTransactionManager());
60+
// JobRepositoryFactoryBean's methods Throws Generic Exception,
61+
// it would have been better to have a specific one
62+
factory.afterPropertiesSet();
63+
return (JobRepository) factory.getObject();
64+
}
65+
66+
private PlatformTransactionManager getTransactionManager() {
67+
return new ResourcelessTransactionManager();
68+
}
69+
70+
public JobLauncher getJobLauncher() throws Exception {
71+
SimpleJobLauncher jobLauncher = new SimpleJobLauncher();
72+
// SimpleJobLauncher's methods Throws Generic Exception,
73+
// it would have been better to have a specific one
74+
jobLauncher.setJobRepository(getJobRepository());
75+
jobLauncher.afterPropertiesSet();
76+
return jobLauncher;
77+
}
78+
79+
}
Lines changed: 56 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,56 @@
1+
package org.baeldung.spring_batch_intro.model;
2+
3+
import java.util.Date;
4+
5+
import javax.xml.bind.annotation.XmlRootElement;
6+
7+
@SuppressWarnings("restriction")
8+
@XmlRootElement(name = "transactionRecord")
9+
public class Transaction {
10+
private String username;
11+
private int userId;
12+
private Date transactionDate;
13+
private double amount;
14+
15+
/* getters and setters for the attributes */
16+
17+
public String getUsername() {
18+
return username;
19+
}
20+
21+
public void setUsername(String username) {
22+
this.username = username;
23+
}
24+
25+
public int getUserId() {
26+
return userId;
27+
}
28+
29+
public void setUserId(int userId) {
30+
this.userId = userId;
31+
}
32+
33+
public Date getTransactionDate() {
34+
return transactionDate;
35+
}
36+
37+
public void setTransactionDate(Date transactionDate) {
38+
this.transactionDate = transactionDate;
39+
}
40+
41+
public double getAmount() {
42+
return amount;
43+
}
44+
45+
public void setAmount(double amount) {
46+
this.amount = amount;
47+
}
48+
49+
@Override
50+
public String toString() {
51+
return "Transaction [username=" + username + ", userId=" + userId
52+
+ ", transactionDate=" + transactionDate + ", amount=" + amount
53+
+ "]";
54+
}
55+
56+
}
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
package org.baeldung.spring_batch_intro.service;
2+
3+
import org.baeldung.spring_batch_intro.model.Transaction;
4+
import org.springframework.batch.item.ItemProcessor;
5+
6+
public class CustomItemProcessor implements
7+
ItemProcessor<Transaction, Transaction> {
8+
9+
public Transaction process(Transaction item) {
10+
System.out.println("Processing..." + item);
11+
return item;
12+
}
13+
}

0 commit comments

Comments
 (0)