When I started learning Spring, I noticed something about many of the tutorials I found.

They often showed how to use a feature, but not always why it worked or how the different pieces fitted together in a real application.

I learn best by building things and documenting what I discover, so I started a project called spring-by-example.

The idea is simple: instead of building one large application, I’m creating a collection of small, focused examples where each example explores a specific Spring concept with clear explanations, tests, and documentation.

I’m happy to say that I’ve now completed Module 07 - Spring Batch. 🎉

This module took me from the fundamentals of batch processing to more advanced topics such as job execution metadata, restartability, fault tolerance, and testing.

The module covers:

  • Jobs and Steps
  • Job Parameters
  • Item Readers
  • Item Processors
  • Item Writers
  • Chunk-Oriented Processing
  • Tasklet Processing
  • Job Execution and Metadata
  • Job Restartability
  • Skip and Retry
  • Batch Testing

One thing I particularly enjoyed about this module was understanding how Spring Batch breaks a batch process into smaller, manageable components.

Jobs and Steps

I started with jobs and steps.

A Job represents the overall batch process, while Steps define the individual operations that make up that process.

From there, I explored job parameters and how they allow values to be passed into a job at runtime.

This also helped me understand how Spring Batch identifies job instances and distinguishes between identifying and non-identifying parameters.

Item Readers, Processors, and Writers

Next came item readers, processors, and writers.

These are the core components of chunk-oriented processing.

An ItemReader reads input data, an ItemProcessor transforms or filters it, and an ItemWriter writes the resulting items.

For example, a simple processor can transform an order description into uppercase:

@Override public ProcessedOrder process(Order order) { return new ProcessedOrder( order.id(), order.description().toUpperCase(Locale.ROOT) ); } 

Chunk-Oriented Processing

Chunk-oriented processing introduced another important concept.

Rather than processing and writing one item at a time, Spring Batch can process items in chunks.

For example:

new ChunkOrientedStepBuilder<Order, ProcessedOrder>( "processOrdersStep", jobRepository, 3 ) .reader(orderItemReader) .processor(orderItemProcessor) .writer(orderItemWriter) .build(); 

With a chunk size of three, Spring Batch processes items in groups of three before writing them.

This helped me understand transaction boundaries and how chunk size affects the execution of a batch step.

Tasklet Processing

I also explored tasklet processing.

Unlike chunk-oriented processing, a tasklet is useful for a single operation or a small, self-contained task, such as archiving records, performing cleanup, or executing a database operation.

Job Execution and Metadata

Job execution and metadata were another important part of the module.

I explored how Spring Batch stores information about job instances, job executions, and step executions using a JDBC-backed JobRepository.

This made it possible to expose execution information through REST endpoints and understand what happened during a batch run.

Restartability

Restartability was particularly interesting.

A batch job can fail partway through execution, but that doesn't necessarily mean everything needs to start again.

Spring Batch can use persisted execution metadata and execution contexts to restore state and continue processing from where the job left off.

Skip and Retry

I also explored skip and retry policies.

Not every processing failure should necessarily stop an entire batch job.

Some records may be invalid and can be skipped, while temporary failures may be worth retrying.

For example:

.faultTolerant() .skipPolicy(skipPolicy) .retryPolicy(retryPolicy) 

This demonstrated how Spring Batch can handle different failure scenarios while allowing the overall job to complete when appropriate.

Batch Testing

Finally, I finished the module with batch testing.

Using @SpringBatchTest, JobOperatorTestUtils, and Spring Boot testing support, I explored how to test individual components, execute jobs and steps, verify execution metadata, and test step-scoped components.

One important lesson from this was that testing a batch application involves more than checking whether the final output is correct.

It is also important to verify execution status, read and write counts, commit counts, job parameters, and the behavior of individual steps.

The project is open source, and I'm continuing to build it as I learn:

🔗 GitHub: https://gith.ub/dsAQrAU5

🔗 GitLab: https://gitl.ab/gfDEyGH3

There’s still a long way to go, but completing Module 07 - Spring Batch feels like another important milestone. 🚀

Next up: Module 08 - Spring Integration continuing to explore the Spring ecosystem through small, focused, runnable examples.

One focused example at a time. 🚀

If you've worked with Spring Batch before, what do you find most useful in your batch applications - chunk processing, restartability, skip and retry, or something else?

java #springframework #springbatch #springboot #opensource #github #learninginpublic #backend #softwareengineering