IN PROGRESS - issue BATCH-212: Merge InputSource with ItemProvider
http://opensource.atlassian.com/projects/spring/browse/BATCH-212 Merge InputSource/ItemProvider -> ItemReader.
This commit is contained in:
@@ -1,37 +0,0 @@
|
||||
/*
|
||||
* Copyright 2006-2007 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.batch.io;
|
||||
|
||||
|
||||
/**
|
||||
* Basic interface for generic input operations. Class implementing this
|
||||
* interface will be responsible for reading records from input stream and also
|
||||
* possibly for mapping these records to objects. Generally it is responsibility
|
||||
* of implementing class to decide which technology to use for mapping and how
|
||||
* it should be configured.
|
||||
*
|
||||
* @author Dave Syer
|
||||
*/
|
||||
public interface InputSource {
|
||||
|
||||
/**
|
||||
* Read record from input stream and map it to an object.
|
||||
*
|
||||
* @return the value object
|
||||
*/
|
||||
public Object read();
|
||||
}
|
||||
@@ -23,9 +23,10 @@ import org.hibernate.ScrollableResults;
|
||||
import org.hibernate.Session;
|
||||
import org.hibernate.SessionFactory;
|
||||
import org.hibernate.StatelessSession;
|
||||
import org.springframework.batch.io.InputSource;
|
||||
import org.springframework.batch.io.Skippable;
|
||||
import org.springframework.batch.item.ItemReader;
|
||||
import org.springframework.batch.item.ResourceLifecycle;
|
||||
import org.springframework.batch.item.provider.AbstractItemReader;
|
||||
import org.springframework.batch.repeat.synch.BatchTransactionSynchronizationManager;
|
||||
import org.springframework.batch.restart.GenericRestartData;
|
||||
import org.springframework.batch.restart.RestartData;
|
||||
@@ -39,7 +40,7 @@ import org.springframework.util.ClassUtils;
|
||||
import org.springframework.util.StringUtils;
|
||||
|
||||
/**
|
||||
* {@link InputSource} for reading database records built on top of Hibernate.
|
||||
* {@link ItemReader} for reading database records built on top of Hibernate.
|
||||
*
|
||||
* It executes the HQL {@link #queryString} when initialized and iterates over
|
||||
* the result set as {@link #read()} method is called, returning an object
|
||||
@@ -56,15 +57,15 @@ import org.springframework.util.StringUtils;
|
||||
* @author Robert Kasanicky
|
||||
* @author Dave Syer
|
||||
*/
|
||||
public class HibernateCursorInputSource implements InputSource, Restartable,
|
||||
public class HibernateCursorItemReader extends AbstractItemReader implements ItemReader, Restartable,
|
||||
Skippable, InitializingBean, DisposableBean, ResourceLifecycle {
|
||||
|
||||
private static final String RESTART_DATA_ROW_NUMBER_KEY = ClassUtils
|
||||
.getShortName(HibernateCursorInputSource.class)
|
||||
.getShortName(HibernateCursorItemReader.class)
|
||||
+ ".rowNumber";
|
||||
|
||||
private static final String SKIPPED_ROWS = ClassUtils
|
||||
.getShortName(HibernateCursorInputSource.class)
|
||||
.getShortName(HibernateCursorItemReader.class)
|
||||
+ ".skippedRows";;
|
||||
|
||||
private SessionFactory sessionFactory;
|
||||
@@ -90,7 +91,7 @@ public class HibernateCursorInputSource implements InputSource, Restartable,
|
||||
|
||||
private boolean initialized = false;
|
||||
|
||||
private TransactionSynchronization synchronization = new HibernateInputSourceTransactionSynchronization();
|
||||
private TransactionSynchronization synchronization = new HibernateItemReaderTransactionSynchronization();
|
||||
|
||||
public Object read() {
|
||||
if (!initialized) {
|
||||
@@ -238,7 +239,7 @@ public class HibernateCursorInputSource implements InputSource, Restartable,
|
||||
/**
|
||||
* Encapsulates transaction events handling.
|
||||
*/
|
||||
private class HibernateInputSourceTransactionSynchronization extends
|
||||
private class HibernateItemReaderTransactionSynchronization extends
|
||||
TransactionSynchronizationAdapter {
|
||||
|
||||
public void afterCompletion(int status) {
|
||||
@@ -29,9 +29,9 @@ import javax.sql.DataSource;
|
||||
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.springframework.batch.io.InputSource;
|
||||
import org.springframework.batch.io.Skippable;
|
||||
import org.springframework.batch.io.support.AbstractTransactionalIoSource;
|
||||
import org.springframework.batch.item.ItemReader;
|
||||
import org.springframework.batch.item.ResourceLifecycle;
|
||||
import org.springframework.batch.restart.GenericRestartData;
|
||||
import org.springframework.batch.restart.RestartData;
|
||||
@@ -116,11 +116,11 @@ import org.springframework.util.StringUtils;
|
||||
* @author Lucas Ward
|
||||
* @author Peter Zozom
|
||||
*/
|
||||
public class JdbcCursorInputSource extends AbstractTransactionalIoSource
|
||||
implements InputSource, ResourceLifecycle, DisposableBean,
|
||||
public class JdbcCursorItemReader extends AbstractTransactionalIoSource
|
||||
implements ItemReader, ResourceLifecycle, DisposableBean,
|
||||
InitializingBean, Restartable, StatisticsProvider, Skippable {
|
||||
|
||||
private static Log log = LogFactory.getLog(JdbcCursorInputSource.class);
|
||||
private static Log log = LogFactory.getLog(JdbcCursorItemReader.class);
|
||||
|
||||
public static final int VALUE_NOT_SET = -1;
|
||||
|
||||
@@ -565,4 +565,13 @@ public class JdbcCursorInputSource extends AbstractTransactionalIoSource
|
||||
initialized = true;
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the item itself (which is already a key).
|
||||
* @see org.springframework.batch.item.ItemReader#getKey(java.lang.Object)
|
||||
*/
|
||||
public Object getKey(Object item) {
|
||||
return item;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -18,8 +18,8 @@ package org.springframework.batch.io.driving;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
|
||||
import org.springframework.batch.io.InputSource;
|
||||
import org.springframework.batch.io.support.AbstractTransactionalIoSource;
|
||||
import org.springframework.batch.item.ItemReader;
|
||||
import org.springframework.batch.item.ResourceLifecycle;
|
||||
import org.springframework.batch.repeat.synch.BatchTransactionSynchronizationManager;
|
||||
import org.springframework.batch.restart.RestartData;
|
||||
@@ -50,8 +50,8 @@ import org.springframework.util.Assert;
|
||||
* @author Lucas Ward
|
||||
* @since 1.0
|
||||
*/
|
||||
public class DrivingQueryInputSource extends AbstractTransactionalIoSource
|
||||
implements InputSource, ResourceLifecycle, InitializingBean,
|
||||
public class DrivingQueryItemReader extends AbstractTransactionalIoSource
|
||||
implements ItemReader, ResourceLifecycle, InitializingBean,
|
||||
DisposableBean, Restartable {
|
||||
|
||||
private boolean initialized = false;
|
||||
@@ -66,7 +66,7 @@ public class DrivingQueryInputSource extends AbstractTransactionalIoSource
|
||||
|
||||
private KeyGenerator keyGenerator;
|
||||
|
||||
public DrivingQueryInputSource() {
|
||||
public DrivingQueryItemReader() {
|
||||
|
||||
}
|
||||
|
||||
@@ -75,14 +75,14 @@ public class DrivingQueryInputSource extends AbstractTransactionalIoSource
|
||||
*
|
||||
* @param keys
|
||||
*/
|
||||
public DrivingQueryInputSource(List keys) {
|
||||
public DrivingQueryItemReader(List keys) {
|
||||
this.keys = keys;
|
||||
this.keysIterator = keys.iterator();
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the next key in the List. If the InputSource has not been
|
||||
* initialized yet, then {@link AbstractDrivingQueryInputSource.open()} will
|
||||
* Return the next key in the List. If the ItemReader has not been
|
||||
* initialized yet, then {@link AbstractDrivingQueryItemReader.open()} will
|
||||
* be called.
|
||||
*
|
||||
* @return next key in the list if not index is not at the last element,
|
||||
@@ -103,7 +103,7 @@ public class DrivingQueryInputSource extends AbstractTransactionalIoSource
|
||||
|
||||
/**
|
||||
* Get the current key. This method will return the same object returned by
|
||||
* the last read() method. If the InputSource hasn't been initialized yet,
|
||||
* the last read() method. If the ItemReader hasn't been initialized yet,
|
||||
* then null will be returned.
|
||||
*
|
||||
* @return the current key.
|
||||
@@ -217,4 +217,12 @@ public class DrivingQueryInputSource extends AbstractTransactionalIoSource
|
||||
keysIterator = keys.listIterator(lastCommitIndex);
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the item itself (which is already a key).
|
||||
* @see org.springframework.batch.item.ItemReader#getKey(java.lang.Object)
|
||||
*/
|
||||
public Object getKey(Object item) {
|
||||
return item;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -21,13 +21,13 @@ import org.springframework.orm.ibatis.SqlMapClientTemplate;
|
||||
import com.ibatis.sqlmap.client.SqlMapClient;
|
||||
|
||||
/**
|
||||
* Extension of {@link DrivingQueryInputSource} that maps keys to
|
||||
* Extension of {@link DrivingQueryItemReader} that maps keys to
|
||||
* objects. An iBatis query id must be set to map and return each 'detail record'.
|
||||
*
|
||||
* @author Lucas Ward
|
||||
* @see IbatisKeyGenerator
|
||||
*/
|
||||
public class IbatisDrivingQueryInputSource extends DrivingQueryInputSource {
|
||||
public class IbatisDrivingQueryItemReader extends DrivingQueryItemReader {
|
||||
|
||||
private String detailsQueryId;
|
||||
|
||||
@@ -36,7 +36,7 @@ public class IbatisDrivingQueryInputSource extends DrivingQueryInputSource {
|
||||
/**
|
||||
* Overridden read() that uses the returned key as arguments to the details query.
|
||||
*
|
||||
* @see org.springframework.batch.io.driving.DrivingQueryInputSource#read()
|
||||
* @see org.springframework.batch.io.driving.DrivingQueryItemReader#read()
|
||||
*/
|
||||
public Object read() {
|
||||
Object key = super.read();
|
||||
@@ -3,7 +3,7 @@ package org.springframework.batch.io.driving.support;
|
||||
import java.util.List;
|
||||
import java.util.Properties;
|
||||
|
||||
import org.springframework.batch.io.driving.DrivingQueryInputSource;
|
||||
import org.springframework.batch.io.driving.DrivingQueryItemReader;
|
||||
import org.springframework.batch.io.driving.KeyGenerator;
|
||||
import org.springframework.batch.restart.GenericRestartData;
|
||||
import org.springframework.batch.restart.RestartData;
|
||||
@@ -19,11 +19,11 @@ import com.ibatis.sqlmap.client.SqlMapClient;
|
||||
*
|
||||
* @author Robert Kasanicky
|
||||
* @author Lucas Ward
|
||||
* @see DrivingQueryInputSource
|
||||
* @see DrivingQueryItemReader
|
||||
*/
|
||||
public class IbatisKeyGenerator implements KeyGenerator {
|
||||
|
||||
public static final String RESTART_KEY = "IbatisDrivingQueryInputSource.keyIndex";
|
||||
public static final String RESTART_KEY = "IbatisDrivingQueryItemReader.keyIndex";
|
||||
|
||||
private SqlMapClientTemplate sqlMapClientTemplate;
|
||||
|
||||
@@ -34,7 +34,7 @@ public class IbatisKeyGenerator implements KeyGenerator {
|
||||
/*
|
||||
* Retrieve the keys using the provided driving query id.
|
||||
*
|
||||
* @see org.springframework.batch.io.support.AbstractDrivingQueryInputSource#retrieveKeys()
|
||||
* @see org.springframework.batch.io.support.AbstractDrivingQueryItemReader#retrieveKeys()
|
||||
*/
|
||||
public List retrieveKeys() {
|
||||
return sqlMapClientTemplate.queryForList(drivingQuery);
|
||||
@@ -54,7 +54,7 @@ public class IbatisKeyGenerator implements KeyGenerator {
|
||||
/**
|
||||
* Restore the keys list given the provided restart data.
|
||||
*
|
||||
* @see org.springframework.batch.io.driving.DrivingQueryInputSource#restoreKeys(org.springframework.batch.restart.RestartData)
|
||||
* @see org.springframework.batch.io.driving.DrivingQueryItemReader#restoreKeys(org.springframework.batch.restart.RestartData)
|
||||
*/
|
||||
public List restoreKeys(RestartData data) {
|
||||
|
||||
|
||||
@@ -18,7 +18,7 @@ package org.springframework.batch.io.driving.support;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import org.springframework.batch.io.driving.DrivingQueryInputSource;
|
||||
import org.springframework.batch.io.driving.DrivingQueryItemReader;
|
||||
import org.springframework.batch.io.driving.KeyGenerator;
|
||||
import org.springframework.batch.restart.RestartData;
|
||||
import org.springframework.jdbc.core.JdbcTemplate;
|
||||
@@ -33,13 +33,13 @@ import org.springframework.util.StringUtils;
|
||||
* </p>
|
||||
*
|
||||
* @author Lucas Ward
|
||||
* @see DrivingQueryInputSource
|
||||
* @see DrivingQueryItemReader
|
||||
* @since 1.0
|
||||
*/
|
||||
public class MultipleColumnJdbcKeyGenerator implements
|
||||
KeyGenerator {
|
||||
|
||||
public static final String RESTART_KEY = "CompositeKeySqlDrivingQueryInputSource.key";
|
||||
public static final String RESTART_KEY = "CompositeKeySqlDrivingQueryItemReader.key";
|
||||
|
||||
private JdbcTemplate jdbcTemplate;
|
||||
|
||||
@@ -54,7 +54,7 @@ public class MultipleColumnJdbcKeyGenerator implements
|
||||
}
|
||||
|
||||
/**
|
||||
* Construct a new InputSource.
|
||||
* Construct a new ItemReader.
|
||||
*
|
||||
* @param jdbcTemplate
|
||||
* @param sql - Sql statement that returns all keys to process.
|
||||
@@ -71,14 +71,14 @@ public class MultipleColumnJdbcKeyGenerator implements
|
||||
}
|
||||
|
||||
/* (non-Javadoc)
|
||||
* @see org.springframework.batch.io.sql.scratch.AbstractDrivingQueryInputSource#retrieveKeys()
|
||||
* @see org.springframework.batch.io.sql.scratch.AbstractDrivingQueryItemReader#retrieveKeys()
|
||||
*/
|
||||
public List retrieveKeys() {
|
||||
return jdbcTemplate.query(sql, keyMapper);
|
||||
}
|
||||
|
||||
/* (non-Javadoc)
|
||||
* @see org.springframework.batch.io.sql.scratch.AbstractDrivingQueryInputSource#restoreKeys(org.springframework.batch.restart.RestartData)
|
||||
* @see org.springframework.batch.io.sql.scratch.AbstractDrivingQueryItemReader#restoreKeys(org.springframework.batch.restart.RestartData)
|
||||
*/
|
||||
public List restoreKeys(RestartData restartData) {
|
||||
|
||||
|
||||
@@ -33,7 +33,7 @@ import org.springframework.transaction.support.TransactionSynchronizationAdapter
|
||||
|
||||
/**
|
||||
* <p>
|
||||
* This class is a {@link FieldSetInputSource} that supports restart,
|
||||
* This class is a {@link FieldSetItemReader} that supports restart,
|
||||
* skipping invalid lines and storing statistics.
|
||||
* </p>
|
||||
*
|
||||
@@ -41,9 +41,9 @@ import org.springframework.transaction.support.TransactionSynchronizationAdapter
|
||||
* @author Tomas Slanina
|
||||
* @author Robert Kasanicky
|
||||
*/
|
||||
public class DefaultFlatFileInputSource extends SimpleFlatFileInputSource implements Skippable, Restartable,
|
||||
public class DefaultFlatFileItemReader extends SimpleFlatFileItemReader implements Skippable, Restartable,
|
||||
StatisticsProvider {
|
||||
private static Log log = LogFactory.getLog(DefaultFlatFileInputSource.class);
|
||||
private static Log log = LogFactory.getLog(DefaultFlatFileItemReader.class);
|
||||
|
||||
public static final String READ_STATISTICS_NAME = "lines.read.count";
|
||||
|
||||
@@ -25,11 +25,12 @@ import java.util.Collections;
|
||||
import java.util.HashSet;
|
||||
import java.util.Iterator;
|
||||
|
||||
import org.springframework.batch.io.InputSource;
|
||||
import org.springframework.batch.io.exception.BatchEnvironmentException;
|
||||
import org.springframework.batch.io.file.support.separator.DefaultRecordSeparatorPolicy;
|
||||
import org.springframework.batch.io.file.support.separator.RecordSeparatorPolicy;
|
||||
import org.springframework.batch.item.ItemReader;
|
||||
import org.springframework.batch.item.ResourceLifecycle;
|
||||
import org.springframework.batch.item.provider.AbstractItemReader;
|
||||
import org.springframework.beans.factory.DisposableBean;
|
||||
import org.springframework.core.io.Resource;
|
||||
import org.springframework.util.Assert;
|
||||
@@ -57,7 +58,7 @@ import org.springframework.util.Assert;
|
||||
* @author Dave Syer
|
||||
* @author Rob Harrop
|
||||
*/
|
||||
class ResourceLineReader implements ResourceLifecycle, InputSource,
|
||||
class ResourceLineReader extends AbstractItemReader implements ResourceLifecycle, ItemReader,
|
||||
DisposableBean {
|
||||
|
||||
private static final Collection DEFAULT_COMMENTS = Collections
|
||||
@@ -128,7 +129,7 @@ class ResourceLineReader implements ResourceLifecycle, InputSource,
|
||||
* if there is an IOException while accessing the input
|
||||
* resource.
|
||||
*
|
||||
* @see org.springframework.batch.item.provider.support.InputSource#read()
|
||||
* @see org.springframework.batch.item.provider.support.ItemReader#read()
|
||||
*/
|
||||
public synchronized Object read() {
|
||||
// Make a copy of the recordSeparatorPolicy reference, in case it is
|
||||
@@ -179,7 +180,7 @@ class ResourceLineReader implements ResourceLifecycle, InputSource,
|
||||
/**
|
||||
* Close the reader associated with this input source.
|
||||
*
|
||||
* @see org.springframework.batch.io.InputSource#close()
|
||||
* @see org.springframework.batch.io.ItemReader#close()
|
||||
* @throws BatchEnvironmentException
|
||||
* if there is an {@link IOException} during the close
|
||||
* operation.
|
||||
|
||||
@@ -18,7 +18,6 @@ package org.springframework.batch.io.file.support;
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
import org.springframework.batch.io.InputSource;
|
||||
import org.springframework.batch.io.exception.FlatFileParsingException;
|
||||
import org.springframework.batch.io.file.FieldSet;
|
||||
import org.springframework.batch.io.file.FieldSetMapper;
|
||||
@@ -26,7 +25,9 @@ import org.springframework.batch.io.file.support.separator.RecordSeparatorPolicy
|
||||
import org.springframework.batch.io.file.support.transform.AbstractLineTokenizer;
|
||||
import org.springframework.batch.io.file.support.transform.DelimitedLineTokenizer;
|
||||
import org.springframework.batch.io.file.support.transform.LineTokenizer;
|
||||
import org.springframework.batch.item.ItemReader;
|
||||
import org.springframework.batch.item.ResourceLifecycle;
|
||||
import org.springframework.batch.item.provider.AbstractItemReader;
|
||||
import org.springframework.beans.factory.DisposableBean;
|
||||
import org.springframework.beans.factory.InitializingBean;
|
||||
import org.springframework.core.io.Resource;
|
||||
@@ -39,16 +40,16 @@ import org.springframework.util.Assert;
|
||||
* structure of the file, {@link LineTokenizer} is used to parse data obtained
|
||||
* from the file. <br/>
|
||||
*
|
||||
* A {@link SimpleFlatFileInputSource} is not thread safe because it maintains
|
||||
* A {@link SimpleFlatFileItemReader} is not thread safe because it maintains
|
||||
* state in the form of a {@link ResourceLineReader}. Be careful to configure a
|
||||
* {@link SimpleFlatFileInputSource} using an appropriate factory or scope so
|
||||
* {@link SimpleFlatFileItemReader} using an appropriate factory or scope so
|
||||
* that it is not shared between threads.<br/>
|
||||
*
|
||||
* @see FieldSetInputSource
|
||||
* @see FieldSetItemReader
|
||||
*
|
||||
* @author Dave Syer
|
||||
*/
|
||||
public class SimpleFlatFileInputSource implements InputSource,
|
||||
public class SimpleFlatFileItemReader extends AbstractItemReader implements ItemReader,
|
||||
InitializingBean, DisposableBean {
|
||||
|
||||
// default encoding for input files - set to ISO-8859-1
|
||||
@@ -182,9 +183,9 @@ public class SimpleFlatFileInputSource implements InputSource,
|
||||
|
||||
/**
|
||||
* A wrapper for {@link #readFieldSet()} to make this into a real
|
||||
* {@link InputSource}.
|
||||
* {@link ItemReader}.
|
||||
*
|
||||
* @see org.springframework.batch.io.InputSource#read()
|
||||
* @see org.springframework.batch.io.ItemReader#read()
|
||||
*/
|
||||
public Object read() {
|
||||
String line = readLine();
|
||||
@@ -12,14 +12,15 @@ import javax.xml.stream.XMLInputFactory;
|
||||
import javax.xml.stream.XMLStreamException;
|
||||
import javax.xml.stream.events.StartElement;
|
||||
|
||||
import org.springframework.batch.io.InputSource;
|
||||
import org.springframework.batch.io.Skippable;
|
||||
import org.springframework.batch.io.file.support.stax.DefaultFragmentEventReader;
|
||||
import org.springframework.batch.io.file.support.stax.DefaultTransactionalEventReader;
|
||||
import org.springframework.batch.io.file.support.stax.FragmentDeserializer;
|
||||
import org.springframework.batch.io.file.support.stax.FragmentEventReader;
|
||||
import org.springframework.batch.io.file.support.stax.TransactionalEventReader;
|
||||
import org.springframework.batch.item.ItemReader;
|
||||
import org.springframework.batch.item.ResourceLifecycle;
|
||||
import org.springframework.batch.item.provider.AbstractItemReader;
|
||||
import org.springframework.batch.repeat.synch.BatchTransactionSynchronizationManager;
|
||||
import org.springframework.batch.restart.GenericRestartData;
|
||||
import org.springframework.batch.restart.RestartData;
|
||||
@@ -35,19 +36,20 @@ import org.springframework.util.Assert;
|
||||
|
||||
/**
|
||||
* Input source for reading XML input based on StAX.
|
||||
*
|
||||
*
|
||||
* It extracts fragments from the input XML document which correspond to records
|
||||
* for processing. The fragments are wrapped with StartDocument and EndDocument
|
||||
* events so that the fragments can be further processed like standalone XML
|
||||
* documents.
|
||||
*
|
||||
*
|
||||
* @author Robert Kasanicky
|
||||
*/
|
||||
public class StaxEventReaderInputSource implements InputSource, ResourceLifecycle, Skippable, Restartable, StatisticsProvider, InitializingBean, DisposableBean {
|
||||
public class StaxEventReaderItemReader extends AbstractItemReader implements ItemReader, ResourceLifecycle,
|
||||
Skippable, Restartable, StatisticsProvider, InitializingBean, DisposableBean {
|
||||
|
||||
public static final String READ_COUNT_STATISTICS_NAME = "StaxEventReaderInputSource.readCount";
|
||||
public static final String READ_COUNT_STATISTICS_NAME = "StaxEventReaderItemReader.readCount";
|
||||
|
||||
private static final String RESTART_DATA_NAME = "StaxEventReaderInputSource.recordcount";
|
||||
private static final String RESTART_DATA_NAME = "StaxEventReaderItemReader.recordcount";
|
||||
|
||||
private FragmentEventReader fragmentReader;
|
||||
|
||||
@@ -63,7 +65,7 @@ public class StaxEventReaderInputSource implements InputSource, ResourceLifecycl
|
||||
|
||||
private boolean initialized = false;
|
||||
|
||||
private TransactionSynchronization synchronization = new StaxEventReaderInputSourceTransactionSychronization();
|
||||
private TransactionSynchronization synchronization = new StaxEventReaderItemReaderTransactionSychronization();
|
||||
|
||||
private long lastCommitPointRecordCount = 0;
|
||||
|
||||
@@ -73,9 +75,9 @@ public class StaxEventReaderInputSource implements InputSource, ResourceLifecycl
|
||||
|
||||
/**
|
||||
* Read in the next root element from the file, and return it.
|
||||
*
|
||||
*
|
||||
* @return the next available record, if none exist, return null
|
||||
* @see org.springframework.batch.io.InputSource#read()
|
||||
* @see org.springframework.batch.io.ItemReader#read()
|
||||
*/
|
||||
public Object read() {
|
||||
if (!initialized) {
|
||||
@@ -120,8 +122,8 @@ public class StaxEventReaderInputSource implements InputSource, ResourceLifecycl
|
||||
registerSynchronization();
|
||||
try {
|
||||
inputStream = resource.getInputStream();
|
||||
txReader = new DefaultTransactionalEventReader(XMLInputFactory
|
||||
.newInstance().createXMLEventReader(inputStream));
|
||||
txReader = new DefaultTransactionalEventReader(XMLInputFactory.newInstance().createXMLEventReader(
|
||||
inputStream));
|
||||
fragmentReader = new DefaultFragmentEventReader(txReader);
|
||||
}
|
||||
catch (XMLStreamException xse) {
|
||||
@@ -138,8 +140,8 @@ public class StaxEventReaderInputSource implements InputSource, ResourceLifecycl
|
||||
}
|
||||
|
||||
/**
|
||||
* @param fragmentDeserializer maps xml fragments corresponding to records to
|
||||
* objects
|
||||
* @param fragmentDeserializer maps xml fragments corresponding to records
|
||||
* to objects
|
||||
*/
|
||||
public void setFragmentDeserializer(FragmentDeserializer fragmentDeserializer) {
|
||||
this.fragmentDeserializer = fragmentDeserializer;
|
||||
@@ -156,7 +158,7 @@ public class StaxEventReaderInputSource implements InputSource, ResourceLifecycl
|
||||
/**
|
||||
* Mark the last read record as 'skipped', so that I will not be returned
|
||||
* from read() in the case of a rollback.
|
||||
*
|
||||
*
|
||||
* @see Skippable#skip()
|
||||
*/
|
||||
public void skip() {
|
||||
@@ -173,9 +175,9 @@ public class StaxEventReaderInputSource implements InputSource, ResourceLifecycl
|
||||
}
|
||||
|
||||
/**
|
||||
* Ensure that all required dependencies for the InputSource to run are provided
|
||||
* after all properties have been set.
|
||||
*
|
||||
* Ensure that all required dependencies for the ItemReader to run are
|
||||
* provided after all properties have been set.
|
||||
*
|
||||
* @see org.springframework.beans.factory.InitializingBean#afterPropertiesSet()
|
||||
* @throws IllegalArgumentException if the Resource, FragmentDeserializer or
|
||||
* FragmentRootElementName is null, or if the root element is empty.
|
||||
@@ -201,17 +203,17 @@ public class StaxEventReaderInputSource implements InputSource, ResourceLifecycl
|
||||
}
|
||||
|
||||
/**
|
||||
* Restores the input source for the given restart data by rereading and skipping
|
||||
* the number of records stored in the RestartData.
|
||||
*
|
||||
* Restores the input source for the given restart data by rereading and
|
||||
* skipping the number of records stored in the RestartData.
|
||||
*
|
||||
* @param RestartData that holds the line count from the last commit.
|
||||
* @throws IllegalStateException if the InputSource has already been initialized
|
||||
* or if the number of records to read and skip exceeds the available records.
|
||||
* @throws IllegalStateException if the ItemReader has already been
|
||||
* initialized or if the number of records to read and skip exceeds the
|
||||
* available records.
|
||||
*/
|
||||
public void restoreFrom(RestartData data) {
|
||||
Assert.state(!initialized);
|
||||
if (data == null || data.getProperties() == null ||
|
||||
data.getProperties().getProperty(RESTART_DATA_NAME) == null) {
|
||||
if (data == null || data.getProperties() == null || data.getProperties().getProperty(RESTART_DATA_NAME) == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -232,13 +234,15 @@ public class StaxEventReaderInputSource implements InputSource, ResourceLifecycl
|
||||
}
|
||||
|
||||
/**
|
||||
* Responsible for moving the cursor before the StartElement of the fragment root.
|
||||
*
|
||||
* This implementation simply looks for the next corresponding element, it does not care
|
||||
* about element nesting. You will need to override this method to correctly handle
|
||||
* composite fragments.
|
||||
*
|
||||
* @return <code>true</code> if next fragment was found, <code>false</code> otherwise.
|
||||
* Responsible for moving the cursor before the StartElement of the fragment
|
||||
* root.
|
||||
*
|
||||
* This implementation simply looks for the next corresponding element, it
|
||||
* does not care about element nesting. You will need to override this
|
||||
* method to correctly handle composite fragments.
|
||||
*
|
||||
* @return <code>true</code> if next fragment was found,
|
||||
* <code>false</code> otherwise.
|
||||
*/
|
||||
protected boolean moveCursorToNextFragment(XMLEventReader reader) {
|
||||
try {
|
||||
@@ -252,7 +256,8 @@ public class StaxEventReaderInputSource implements InputSource, ResourceLifecycl
|
||||
QName startElementName = ((StartElement) reader.peek()).getName();
|
||||
if (startElementName.getLocalPart().equals(fragmentRootElementName)) {
|
||||
return true;
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
reader.nextEvent();
|
||||
}
|
||||
}
|
||||
@@ -268,9 +273,9 @@ public class StaxEventReaderInputSource implements InputSource, ResourceLifecycl
|
||||
}
|
||||
|
||||
/**
|
||||
* Encapsulates transaction events for the StaxEventReaderInputSource.
|
||||
* Encapsulates transaction events for the StaxEventReaderItemReader.
|
||||
*/
|
||||
private class StaxEventReaderInputSourceTransactionSychronization extends TransactionSynchronizationAdapter {
|
||||
private class StaxEventReaderItemReaderTransactionSychronization extends TransactionSynchronizationAdapter {
|
||||
|
||||
/**
|
||||
* @param status
|
||||
@@ -15,8 +15,8 @@
|
||||
*/
|
||||
package org.springframework.batch.io.support;
|
||||
|
||||
import org.springframework.batch.io.InputSource;
|
||||
import org.springframework.batch.io.ItemWriter;
|
||||
import org.springframework.batch.item.ItemReader;
|
||||
import org.springframework.batch.repeat.synch.BatchTransactionSynchronizationManager;
|
||||
import org.springframework.beans.factory.InitializingBean;
|
||||
import org.springframework.transaction.support.TransactionSynchronization;
|
||||
@@ -26,7 +26,7 @@ import org.springframework.transaction.support.TransactionSynchronizationManager
|
||||
/**
|
||||
* <p>
|
||||
* Abstract class that abstracts away transaction handling from input and
|
||||
* output. Any {@link InputSource} or {@link ItemWriter} that wants to be
|
||||
* output. Any {@link ItemReader} or {@link ItemWriter} that wants to be
|
||||
* notified of transaction events to maintain the contract that all calls to
|
||||
* read or write can extend this base class to ensure that correct ordering is
|
||||
* maintained regardless of rollbacks.
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
package org.springframework.batch.item;
|
||||
|
||||
/**
|
||||
* Mixin interface for {@link ItemProvider} implementations if they can
|
||||
* Mixin interface for {@link ItemReader} implementations if they can
|
||||
* distinguish a new item from one that has been processed before and failed,
|
||||
* e.g. by examining a message flag.
|
||||
*
|
||||
|
||||
@@ -24,7 +24,7 @@ package org.springframework.batch.item;
|
||||
* for each batch, with each call to {@link #next} returning a different value
|
||||
* and finally returning <code>null</code> when all input data is exhausted.<br/>
|
||||
*
|
||||
* Implementations need to be thread safe and clients of a {@link ItemProvider}
|
||||
* Implementations need to be thread safe and clients of a {@link ItemReader}
|
||||
* need to be aware that this is the case. Clients can code to this interface
|
||||
* without worrying about thread safety by using the AbstractItemProvider base
|
||||
* class.<br/>
|
||||
@@ -35,7 +35,7 @@ package org.springframework.batch.item;
|
||||
* @author Rob Harrop
|
||||
* @author Dave Syer
|
||||
*/
|
||||
public interface ItemProvider {
|
||||
public interface ItemReader {
|
||||
|
||||
/**
|
||||
* Reads a piece of input data and advance to the next one. Implementations
|
||||
@@ -46,7 +46,7 @@ public interface ItemProvider {
|
||||
*
|
||||
* @throws Exception if an underlying resource is unavailable.
|
||||
*/
|
||||
Object next() throws Exception;
|
||||
Object read() throws Exception;
|
||||
|
||||
/**
|
||||
* Get a unique identifier for the item that can be used to cache it between
|
||||
@@ -17,7 +17,7 @@
|
||||
package org.springframework.batch.item.processor;
|
||||
|
||||
import org.springframework.batch.item.ItemProcessor;
|
||||
import org.springframework.batch.support.AbstractDelegator;
|
||||
import org.springframework.batch.support.AbstractMethodInvokingDelegator;
|
||||
|
||||
|
||||
/**
|
||||
@@ -28,7 +28,7 @@ import org.springframework.batch.support.AbstractDelegator;
|
||||
*
|
||||
* @author Robert Kasanicky
|
||||
*/
|
||||
public class DelegatingItemProcessor extends AbstractDelegator implements ItemProcessor {
|
||||
public class ItemProcessorAdapter extends AbstractMethodInvokingDelegator implements ItemProcessor {
|
||||
|
||||
public void process(Object item) throws Exception {
|
||||
invokeDelegateMethodWithArgument(item);
|
||||
@@ -17,7 +17,7 @@
|
||||
package org.springframework.batch.item.processor;
|
||||
|
||||
import org.springframework.batch.item.ItemProcessor;
|
||||
import org.springframework.batch.support.AbstractDelegator;
|
||||
import org.springframework.batch.support.AbstractMethodInvokingDelegator;
|
||||
import org.springframework.beans.BeanWrapper;
|
||||
import org.springframework.beans.BeanWrapperImpl;
|
||||
import org.springframework.util.Assert;
|
||||
@@ -26,11 +26,11 @@ import org.springframework.util.Assert;
|
||||
* Delegates processing to a custom method - extracts property values
|
||||
* from item object and uses them as arguments for the delegate method.
|
||||
*
|
||||
* @see DelegatingItemProcessor
|
||||
* @see ItemProcessorAdapter
|
||||
*
|
||||
* @author Robert Kasanicky
|
||||
*/
|
||||
public class PropertyExtractingDelegatingItemProcessor extends AbstractDelegator implements ItemProcessor {
|
||||
public class PropertyExtractingDelegatingItemProcessor extends AbstractMethodInvokingDelegator implements ItemProcessor {
|
||||
|
||||
private String[] fieldsUsedAsTargetMethodArguments;
|
||||
|
||||
|
||||
@@ -16,21 +16,21 @@
|
||||
|
||||
package org.springframework.batch.item.provider;
|
||||
|
||||
import org.springframework.batch.item.ItemProvider;
|
||||
import org.springframework.batch.item.ItemReader;
|
||||
|
||||
/**
|
||||
* Base class for {@link ItemProvider} implementations.
|
||||
* Base class for {@link ItemReader} implementations.
|
||||
* @author Dave Syer
|
||||
*
|
||||
*/
|
||||
public abstract class AbstractItemProvider implements ItemProvider {
|
||||
public abstract class AbstractItemReader implements ItemReader {
|
||||
|
||||
/**
|
||||
* Simply returns the item itself. Will be adequate for many purposes, but
|
||||
* not (for example) if the item is a message - in which case the identifier
|
||||
* should be used.
|
||||
*
|
||||
* @see org.springframework.batch.item.ItemProvider#getKey(java.lang.Object)
|
||||
* @see org.springframework.batch.item.ItemReader#getKey(java.lang.Object)
|
||||
*/
|
||||
public Object getKey(Object item) {
|
||||
return item;
|
||||
@@ -21,36 +21,36 @@ import java.util.Collection;
|
||||
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.springframework.batch.io.InputSource;
|
||||
import org.springframework.batch.io.file.FieldSetMapper;
|
||||
import org.springframework.batch.item.ItemProvider;
|
||||
import org.springframework.batch.item.ItemReader;
|
||||
|
||||
/**
|
||||
* An {@link ItemProvider} that delivers a list as its item, storing up objects
|
||||
* from the injected {@link InputSource} until they are ready to be packed out
|
||||
* as a collection. The {@link InputSource} should mark the beginning and end of
|
||||
* An {@link ItemReader} that delivers a list as its item, storing up objects
|
||||
* from the injected {@link ItemReader} until they are ready to be packed out
|
||||
* as a collection. The {@link ItemReader} should mark the beginning and end of
|
||||
* records with the constant values in {@link FieldSetMapper} ({@link FieldSetMapper#BEGIN_RECORD}
|
||||
* and {@link FieldSetMapper#END_RECORD}).<br/>
|
||||
*
|
||||
* This class is thread safe (it can be used concurrently by multiple threads)
|
||||
* as long as the {@link InputSource} is also thread safe.
|
||||
* as long as the {@link ItemReader} is also thread safe.
|
||||
*
|
||||
* @author Dave Syer
|
||||
*
|
||||
*/
|
||||
public class AggregateItemProvider extends AbstractItemProvider {
|
||||
public class AggregateItemReader extends AbstractItemReader {
|
||||
|
||||
private static final Log log = LogFactory
|
||||
.getLog(AggregateItemProvider.class);
|
||||
.getLog(AggregateItemReader.class);
|
||||
|
||||
private InputSource inputSource;
|
||||
private ItemReader inputSource;
|
||||
|
||||
/**
|
||||
* Get the next list of records.
|
||||
* @throws Exception
|
||||
*
|
||||
* @see org.springframework.batch.item.ItemProvider#next()
|
||||
* @see org.springframework.batch.item.ItemReader#read()
|
||||
*/
|
||||
public Object next() {
|
||||
public Object read() throws Exception {
|
||||
ResultHolder holder = new ResultHolder();
|
||||
|
||||
while (process(inputSource.read(), holder)) {
|
||||
@@ -67,7 +67,7 @@ public class AggregateItemProvider extends AbstractItemProvider {
|
||||
private boolean process(Object value, ResultHolder holder) {
|
||||
// finish processing if we hit the end of file
|
||||
if (value == null) {
|
||||
log.debug("Exhausted InputSource");
|
||||
log.debug("Exhausted ItemReader");
|
||||
holder.exhausted = true;
|
||||
return false;
|
||||
}
|
||||
@@ -91,12 +91,12 @@ public class AggregateItemProvider extends AbstractItemProvider {
|
||||
}
|
||||
|
||||
/**
|
||||
* Injection setter for {@link InputSource}.
|
||||
* Injection setter for {@link ItemReader}.
|
||||
*
|
||||
* @param inputSource
|
||||
* an {@link InputSource}.
|
||||
* an {@link ItemReader}.
|
||||
*/
|
||||
public void setInputSource(InputSource inputSource) {
|
||||
public void setItemReader(ItemReader inputSource) {
|
||||
this.inputSource = inputSource;
|
||||
}
|
||||
|
||||
@@ -18,8 +18,8 @@ package org.springframework.batch.item.provider;
|
||||
|
||||
import java.util.Properties;
|
||||
|
||||
import org.springframework.batch.io.InputSource;
|
||||
import org.springframework.batch.io.Skippable;
|
||||
import org.springframework.batch.item.ItemReader;
|
||||
import org.springframework.batch.restart.RestartData;
|
||||
import org.springframework.batch.restart.Restartable;
|
||||
import org.springframework.batch.statistics.StatisticsProvider;
|
||||
@@ -27,24 +27,25 @@ import org.springframework.beans.factory.InitializingBean;
|
||||
import org.springframework.util.Assert;
|
||||
|
||||
/**
|
||||
* Simple wrapper around {@link InputSource}. The input source is expected to
|
||||
* Simple wrapper around {@link ItemReader}. The input source is expected to
|
||||
* take care of open and close operations. If necessary it should be registered
|
||||
* as a step scoped bean to ensure that the lifecycle methods are called.
|
||||
*
|
||||
* @author Dave Syer
|
||||
*/
|
||||
public class InputSourceItemProvider extends AbstractItemProvider implements Restartable, StatisticsProvider, Skippable, InitializingBean{
|
||||
public class DelegatingItemReader extends AbstractItemReader implements Restartable, StatisticsProvider, Skippable, InitializingBean{
|
||||
|
||||
private InputSource inputSource;
|
||||
private ItemReader inputSource;
|
||||
|
||||
public void afterPropertiesSet() throws Exception {
|
||||
Assert.notNull(inputSource, "InputSource must not be null.");
|
||||
Assert.notNull(inputSource, "ItemReader must not be null.");
|
||||
}
|
||||
/**
|
||||
* Get the next object from the input source.
|
||||
* @see org.springframework.batch.item.ItemProvider#next()
|
||||
* @throws Exception
|
||||
* @see org.springframework.batch.item.ItemReader#read()
|
||||
*/
|
||||
public Object next() {
|
||||
public Object read() throws Exception {
|
||||
return inputSource.read();
|
||||
}
|
||||
|
||||
@@ -89,11 +90,11 @@ public class InputSourceItemProvider extends AbstractItemProvider implements Res
|
||||
* Setter for input source.
|
||||
* @param source
|
||||
*/
|
||||
public void setInputSource(InputSource source) {
|
||||
public void setItemReader(ItemReader source) {
|
||||
this.inputSource = source;
|
||||
}
|
||||
|
||||
public InputSource getInputSource() {
|
||||
public ItemReader getItemReader() {
|
||||
return inputSource;
|
||||
}
|
||||
|
||||
@@ -16,20 +16,20 @@
|
||||
|
||||
package org.springframework.batch.item.provider;
|
||||
|
||||
import org.springframework.batch.item.ItemProvider;
|
||||
import org.springframework.batch.support.AbstractDelegator;
|
||||
import org.springframework.batch.item.ItemReader;
|
||||
import org.springframework.batch.support.AbstractMethodInvokingDelegator;
|
||||
|
||||
/**
|
||||
* Invokes a custom method which provides an item.
|
||||
*
|
||||
* @author Robert Kasanicky
|
||||
*/
|
||||
public class DelegatingItemProvider extends AbstractDelegator implements ItemProvider {
|
||||
public class ItemReaderAdapter extends AbstractMethodInvokingDelegator implements ItemReader {
|
||||
|
||||
/**
|
||||
* @return return value of the target method.
|
||||
*/
|
||||
public Object next() throws Exception {
|
||||
public Object read() throws Exception {
|
||||
return invokeDelegateMethod();
|
||||
}
|
||||
|
||||
@@ -23,7 +23,7 @@ import javax.jms.Message;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.springframework.batch.item.FailedItemIdentifier;
|
||||
import org.springframework.batch.item.ItemProvider;
|
||||
import org.springframework.batch.item.ItemReader;
|
||||
import org.springframework.batch.item.exception.UnexpectedInputException;
|
||||
import org.springframework.jms.JmsException;
|
||||
import org.springframework.jms.core.JmsOperations;
|
||||
@@ -31,15 +31,15 @@ import org.springframework.jms.core.JmsTemplate;
|
||||
import org.springframework.util.Assert;
|
||||
|
||||
/**
|
||||
* An {@link ItemProvider} for JMS using a {@link JmsTemplate}. The template
|
||||
* An {@link ItemReader} for JMS using a {@link JmsTemplate}. The template
|
||||
* should have a default destination, which will be used to provide items in
|
||||
* {@link #next()}. If a recovery step is needed, set the error destination and
|
||||
* {@link #read()}. If a recovery step is needed, set the error destination and
|
||||
* the item will be sent there if processing fails in an external retry.
|
||||
*
|
||||
* @author Dave Syer
|
||||
*
|
||||
*/
|
||||
public class JmsItemProvider extends AbstractItemProvider implements FailedItemIdentifier {
|
||||
public class JmsItemReader extends AbstractItemReader implements FailedItemIdentifier {
|
||||
|
||||
protected Log logger = LogFactory.getLog(getClass());
|
||||
|
||||
@@ -92,7 +92,7 @@ public class JmsItemProvider extends AbstractItemProvider implements FailedItemI
|
||||
this.itemType = itemType;
|
||||
}
|
||||
|
||||
public Object next() {
|
||||
public Object read() {
|
||||
if (itemType != null && itemType.isAssignableFrom(Message.class)) {
|
||||
return jmsTemplate.receive();
|
||||
}
|
||||
@@ -108,7 +108,7 @@ public class JmsItemProvider extends AbstractItemProvider implements FailedItemI
|
||||
* Send the message back to the proovider using the specified error
|
||||
* destination property of this provider.
|
||||
*
|
||||
* @see org.springframework.batch.item.provider.AbstractItemProvider#recover(java.lang.Object,
|
||||
* @see org.springframework.batch.item.provider.AbstractItemReader#recover(java.lang.Object,
|
||||
* Throwable)
|
||||
*/
|
||||
public boolean recover(Object item, Throwable cause) {
|
||||
@@ -137,7 +137,7 @@ public class JmsItemProvider extends AbstractItemProvider implements FailedItemI
|
||||
* If the message is a {@link Message} then returns the JMS message ID.
|
||||
* Otherwise just delegate to parent class.
|
||||
*
|
||||
* @see org.springframework.batch.item.provider.AbstractItemProvider#getKey(java.lang.Object)
|
||||
* @see org.springframework.batch.item.provider.AbstractItemReader#getKey(java.lang.Object)
|
||||
*
|
||||
* @throws UnexpectedInputException if the JMS id cannot be determined from
|
||||
* a JMS Message
|
||||
@@ -20,19 +20,19 @@ import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import org.springframework.aop.support.AopUtils;
|
||||
import org.springframework.batch.item.ItemProvider;
|
||||
import org.springframework.batch.item.ItemReader;
|
||||
|
||||
/**
|
||||
* An {@link ItemProvider} that pulls data from a list. Useful for testing.
|
||||
* An {@link ItemReader} that pulls data from a list. Useful for testing.
|
||||
*
|
||||
* @author Dave Syer
|
||||
*
|
||||
*/
|
||||
public class ListItemProvider extends AbstractItemProvider {
|
||||
public class ListItemReader extends AbstractItemReader {
|
||||
|
||||
private List list;
|
||||
|
||||
public ListItemProvider(List list) {
|
||||
public ListItemReader(List list) {
|
||||
// If it is a proxy we assume it knows how to deal with its own state.
|
||||
// (It's probably transaction aware.)
|
||||
if (AopUtils.isAopProxy(list)) {
|
||||
@@ -43,7 +43,7 @@ public class ListItemProvider extends AbstractItemProvider {
|
||||
}
|
||||
}
|
||||
|
||||
public Object next() {
|
||||
public Object read() {
|
||||
if (!list.isEmpty()) {
|
||||
return list.remove(0);
|
||||
}
|
||||
@@ -19,18 +19,18 @@ import org.springframework.batch.item.validator.Validator;
|
||||
import org.springframework.util.Assert;
|
||||
|
||||
/**
|
||||
* Simple extension of InputsourceItemProvider that provides for
|
||||
* Simple extension of {@link DelegatingItemReader} that provides for
|
||||
* validation before returning input.
|
||||
*
|
||||
* @author Lucas Ward
|
||||
*
|
||||
*/
|
||||
public class ValidatingItemProvider extends InputSourceItemProvider {
|
||||
public class ValidatingItemReader extends DelegatingItemReader {
|
||||
|
||||
private Validator validator;
|
||||
|
||||
/* (non-Javadoc)
|
||||
* @see org.springframework.batch.item.provider.InputSourceItemProvider#afterPropertiesSet()
|
||||
* @see org.springframework.batch.item.provider.ItemReaderItemProvider#afterPropertiesSet()
|
||||
*/
|
||||
public void afterPropertiesSet() throws Exception {
|
||||
super.afterPropertiesSet();
|
||||
@@ -38,10 +38,10 @@ public class ValidatingItemProvider extends InputSourceItemProvider {
|
||||
}
|
||||
|
||||
/* (non-Javadoc)
|
||||
* @see org.springframework.batch.item.provider.InputSourceItemProvider#next()
|
||||
* @see org.springframework.batch.item.provider.ItemReaderItemProvider#next()
|
||||
*/
|
||||
public Object next() {
|
||||
Object input = super.next();
|
||||
public Object read() throws Exception {
|
||||
Object input = super.read();
|
||||
if(input != null){
|
||||
validator.validate(input);
|
||||
}
|
||||
@@ -18,9 +18,8 @@ package org.springframework.batch.repeat;
|
||||
|
||||
/**
|
||||
* Callback interface for batch operations. Many simple batch processes will be
|
||||
* able to use off-the-shelf implementations of this interface, e.g.
|
||||
* {@link org.springframework.batch.repeat.callback.ItemProviderRepeatCallback},
|
||||
* enabling the batch developer to concentrate on business logic.
|
||||
* able to use off-the-shelf implementations of this interface, enabling the
|
||||
* batch developer to concentrate on business logic.
|
||||
*
|
||||
* @see RepeatOperations
|
||||
*
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
package org.springframework.batch.repeat.callback;
|
||||
|
||||
import org.springframework.batch.item.ItemProcessor;
|
||||
import org.springframework.batch.item.ItemProvider;
|
||||
import org.springframework.batch.item.ItemReader;
|
||||
import org.springframework.batch.repeat.RepeatCallback;
|
||||
import org.springframework.batch.repeat.RepeatContext;
|
||||
import org.springframework.batch.repeat.ExitStatus;
|
||||
@@ -29,13 +29,13 @@ import org.springframework.batch.repeat.ExitStatus;
|
||||
* @author Dave Syer
|
||||
*
|
||||
*/
|
||||
public class ItemProviderRepeatCallback implements RepeatCallback {
|
||||
public class ItemReaderRepeatCallback implements RepeatCallback {
|
||||
|
||||
ItemProvider provider;
|
||||
ItemReader provider;
|
||||
|
||||
ItemProcessor processor;
|
||||
|
||||
public ItemProviderRepeatCallback(ItemProvider provider, ItemProcessor processor) {
|
||||
public ItemReaderRepeatCallback(ItemReader provider, ItemProcessor processor) {
|
||||
super();
|
||||
this.provider = provider;
|
||||
this.processor = processor;
|
||||
@@ -47,7 +47,7 @@ public class ItemProviderRepeatCallback implements RepeatCallback {
|
||||
* provider by calling next().
|
||||
* @param provider
|
||||
*/
|
||||
public ItemProviderRepeatCallback(ItemProvider provider) {
|
||||
public ItemReaderRepeatCallback(ItemReader provider) {
|
||||
this(provider, null);
|
||||
}
|
||||
|
||||
@@ -61,7 +61,7 @@ public class ItemProviderRepeatCallback implements RepeatCallback {
|
||||
public ExitStatus doInIteration(RepeatContext context) throws Exception {
|
||||
|
||||
ExitStatus result = ExitStatus.FINISHED;
|
||||
Object item = provider.next();
|
||||
Object item = provider.read();
|
||||
|
||||
if (processor != null) {
|
||||
if (item != null) {
|
||||
@@ -19,41 +19,41 @@ package org.springframework.batch.retry.callback;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.springframework.batch.item.ItemProcessor;
|
||||
import org.springframework.batch.item.ItemProvider;
|
||||
import org.springframework.batch.item.ItemReader;
|
||||
import org.springframework.batch.item.ItemRecoverer;
|
||||
import org.springframework.batch.retry.RetryCallback;
|
||||
import org.springframework.batch.retry.RetryContext;
|
||||
import org.springframework.batch.retry.RetryPolicy;
|
||||
import org.springframework.batch.retry.exception.ExhaustedRetryException;
|
||||
import org.springframework.batch.retry.exception.RetryException;
|
||||
import org.springframework.batch.retry.policy.ItemProviderRetryPolicy;
|
||||
import org.springframework.batch.retry.policy.ItemReaderRetryPolicy;
|
||||
|
||||
/**
|
||||
* A {@link RetryCallback} that knows about and caches the value from an
|
||||
* {@link ItemProvider}. Used by the {@link ItemProviderRetryPolicy} to enable
|
||||
* {@link ItemReader}. Used by the {@link ItemReaderRetryPolicy} to enable
|
||||
* external retry of the item processing.
|
||||
*
|
||||
* @author Dave Syer
|
||||
*
|
||||
* @see ItemProviderRetryPolicy
|
||||
* @see ItemReaderRetryPolicy
|
||||
* @see RetryPolicy#handleRetryExhausted(RetryContext)
|
||||
*
|
||||
*/
|
||||
public class ItemProviderRetryCallback implements RetryCallback {
|
||||
public class ItemReaderRetryCallback implements RetryCallback {
|
||||
|
||||
private final static Log logger = LogFactory
|
||||
.getLog(ItemProviderRetryCallback.class);
|
||||
.getLog(ItemReaderRetryCallback.class);
|
||||
|
||||
public static final String ITEM = ItemProviderRetryCallback.class.getName()
|
||||
public static final String ITEM = ItemReaderRetryCallback.class.getName()
|
||||
+ ".ITEM";
|
||||
|
||||
private ItemProvider provider;
|
||||
private ItemReader provider;
|
||||
|
||||
private ItemProcessor processor;
|
||||
|
||||
private ItemRecoverer recoverer;
|
||||
|
||||
public ItemProviderRetryCallback(ItemProvider provider,
|
||||
public ItemReaderRetryCallback(ItemReader provider,
|
||||
ItemProcessor processor) {
|
||||
super();
|
||||
this.provider = provider;
|
||||
@@ -81,7 +81,7 @@ public class ItemProviderRetryCallback implements RetryCallback {
|
||||
Object item = context.getAttribute(ITEM);
|
||||
if (item == null) {
|
||||
try {
|
||||
item = provider.next();
|
||||
item = provider.read();
|
||||
} catch (Exception e) {
|
||||
throw new ExhaustedRetryException(
|
||||
"Unexpected end of item provider", e);
|
||||
@@ -107,7 +107,7 @@ public class ItemProviderRetryCallback implements RetryCallback {
|
||||
|
||||
/**
|
||||
* Accessor for the {@link ItemRecoverer}. If the handler is null but
|
||||
* the {@link ItemProvider} is an instanceof {@link ItemRecoverer},
|
||||
* the {@link ItemReader} is an instanceof {@link ItemRecoverer},
|
||||
* then it will be returned instead.
|
||||
*
|
||||
* @return the {@link ItemRecoverer}.
|
||||
@@ -123,11 +123,11 @@ public class ItemProviderRetryCallback implements RetryCallback {
|
||||
}
|
||||
|
||||
/**
|
||||
* Public getter for the {@link ItemProvider}.
|
||||
* Public getter for the {@link ItemReader}.
|
||||
*
|
||||
* @return the {@link ItemProvider} instance.
|
||||
* @return the {@link ItemReader} instance.
|
||||
*/
|
||||
public ItemProvider getProvider() {
|
||||
public ItemReader getProvider() {
|
||||
return provider;
|
||||
}
|
||||
|
||||
@@ -19,33 +19,33 @@ package org.springframework.batch.retry.policy;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.springframework.batch.item.FailedItemIdentifier;
|
||||
import org.springframework.batch.item.ItemProvider;
|
||||
import org.springframework.batch.item.ItemReader;
|
||||
import org.springframework.batch.item.ItemRecoverer;
|
||||
import org.springframework.batch.repeat.synch.RepeatSynchronizationManager;
|
||||
import org.springframework.batch.retry.RetryCallback;
|
||||
import org.springframework.batch.retry.RetryContext;
|
||||
import org.springframework.batch.retry.RetryPolicy;
|
||||
import org.springframework.batch.retry.callback.ItemProviderRetryCallback;
|
||||
import org.springframework.batch.retry.callback.ItemReaderRetryCallback;
|
||||
import org.springframework.batch.retry.context.RetryContextSupport;
|
||||
import org.springframework.batch.retry.exception.TerminatedRetryException;
|
||||
import org.springframework.batch.retry.synch.RetrySynchronizationManager;
|
||||
import org.springframework.util.Assert;
|
||||
|
||||
/**
|
||||
* A {@link RetryPolicy} that detects an {@link ItemProviderRetryCallback} when
|
||||
* A {@link RetryPolicy} that detects an {@link ItemReaderRetryCallback} when
|
||||
* it opens a new context, and uses it to make sure the item is in place for
|
||||
* later decisions about how to retry or backoff. The callback should be an
|
||||
* instance of {@link ItemProviderRetryCallback} otherwise an exception will be
|
||||
* instance of {@link ItemReaderRetryCallback} otherwise an exception will be
|
||||
* thrown when the context is created.
|
||||
*
|
||||
* @author Dave Syer
|
||||
*
|
||||
*/
|
||||
public class ItemProviderRetryPolicy extends AbstractStatefulRetryPolicy {
|
||||
public class ItemReaderRetryPolicy extends AbstractStatefulRetryPolicy {
|
||||
|
||||
protected Log logger = LogFactory.getLog(getClass());
|
||||
|
||||
public static final String EXHAUSTED = ItemProviderRetryPolicy.class
|
||||
public static final String EXHAUSTED = ItemReaderRetryPolicy.class
|
||||
.getName()
|
||||
+ ".EXHAUSTED";
|
||||
|
||||
@@ -56,7 +56,7 @@ public class ItemProviderRetryPolicy extends AbstractStatefulRetryPolicy {
|
||||
*
|
||||
* @param delegate
|
||||
*/
|
||||
public ItemProviderRetryPolicy(RetryPolicy delegate) {
|
||||
public ItemReaderRetryPolicy(RetryPolicy delegate) {
|
||||
super();
|
||||
this.delegate = delegate;
|
||||
}
|
||||
@@ -65,7 +65,7 @@ public class ItemProviderRetryPolicy extends AbstractStatefulRetryPolicy {
|
||||
* Default constructor. Creates a new {@link SimpleRetryPolicy} for the
|
||||
* delegate.
|
||||
*/
|
||||
public ItemProviderRetryPolicy() {
|
||||
public ItemReaderRetryPolicy() {
|
||||
this(new SimpleRetryPolicy());
|
||||
}
|
||||
|
||||
@@ -99,7 +99,7 @@ public class ItemProviderRetryPolicy extends AbstractStatefulRetryPolicy {
|
||||
|
||||
/**
|
||||
* Create a new context for the execution of the callback, which must be an
|
||||
* instance of {@link ItemProviderRetryCallback}.
|
||||
* instance of {@link ItemReaderRetryCallback}.
|
||||
*
|
||||
* @see org.springframework.batch.retry.RetryPolicy#open(org.springframework.batch.retry.RetryCallback)
|
||||
*
|
||||
@@ -107,10 +107,10 @@ public class ItemProviderRetryPolicy extends AbstractStatefulRetryPolicy {
|
||||
* if the callback is not of the required type.
|
||||
*/
|
||||
public RetryContext open(RetryCallback callback) {
|
||||
Assert.state(callback instanceof ItemProviderRetryCallback,
|
||||
Assert.state(callback instanceof ItemReaderRetryCallback,
|
||||
"Callback must be ItemProviderRetryCallback");
|
||||
ItemProviderRetryContext context = new ItemProviderRetryContext(
|
||||
(ItemProviderRetryCallback) callback);
|
||||
(ItemReaderRetryCallback) callback);
|
||||
context.open(callback);
|
||||
return context;
|
||||
}
|
||||
@@ -145,11 +145,11 @@ public class ItemProviderRetryPolicy extends AbstractStatefulRetryPolicy {
|
||||
// The delegate context...
|
||||
private RetryContext delegateContext;
|
||||
|
||||
private ItemProvider provider;
|
||||
private ItemReader provider;
|
||||
|
||||
private ItemRecoverer recoverer;
|
||||
|
||||
public ItemProviderRetryContext(ItemProviderRetryCallback callback) {
|
||||
public ItemProviderRetryContext(ItemReaderRetryCallback callback) {
|
||||
super(RetrySynchronizationManager.getContext());
|
||||
item = callback.next(this);
|
||||
this.provider = callback.getProvider();
|
||||
@@ -243,7 +243,7 @@ public class ItemProviderRetryPolicy extends AbstractStatefulRetryPolicy {
|
||||
* @param item
|
||||
* @return
|
||||
*/
|
||||
protected boolean hasFailed(ItemProvider provider, Object item) {
|
||||
protected boolean hasFailed(ItemReader provider, Object item) {
|
||||
if (provider instanceof FailedItemIdentifier) {
|
||||
return ((FailedItemIdentifier) provider).hasFailed(item);
|
||||
}
|
||||
@@ -32,7 +32,7 @@ import org.springframework.util.MethodInvoker;
|
||||
*
|
||||
* @author Robert Kasanicky
|
||||
*/
|
||||
public class AbstractDelegator implements InitializingBean {
|
||||
public class AbstractMethodInvokingDelegator implements InitializingBean {
|
||||
|
||||
private Object targetObject;
|
||||
|
||||
Reference in New Issue
Block a user