我正在尝试在异步(多线程)处理器中使用外部服务响应,并通过异步编写器将其写入数据库(Sybase)。我一直遇到I / O错误
java.util.concurrent.ExecutionException: org.springframework.web.client.ResourceAccessException: I/O error on GET request for "https://pcmiler.alk.com/apis/rest/v1.0/Service.svc/route/routeReports": Connection timed out: connect; nested exception is java.net.ConnectException: Connection timed out: connect
at java.util.concurrent.FutureTask.report(FutureTask.java:122) ~[na:1.8.0_144]
at java.util.concurrent.FutureTask.get(FutureTask.java:192) ~[na:1.8.0_144]
at org.springframework.batch.integration.async.AsyncItemWriter.write(AsyncItemWriter.java:44) ~[spring-batch-integration-1.2.1.RELEASE.jar!/:na]
at org.springframework.batch.core.step.item.SimpleChunkProcessor.writeItems(SimpleChunkProcessor.java:175) ~[spring-batch-core-3.0.9.RELEASE.jar!/:3.0.9.RELEASE]
at org.springframework.batch.core.step.item.SimpleChunkProcessor.doWrite(SimpleChunkProcessor.java:151) ~[spring-batch-core-3.0.9.RELEASE.jar!/:3.0.9.RELEASE]
at org.springframework.batch.core.step.item.SimpleChunkProcessor.write(SimpleChunkProcessor.java:274) ~[spring-batch-core-3.0.9.RELEASE.jar!/:3.0.9.RELEASE]
at org.springframework.batch.core.step.item.SimpleChunkProcessor.process(SimpleChunkProcessor.java:199) ~[spring-batch-core-3.0.9.RELEASE.jar!/:3.0.9.RELEASE]
at org.springframework.batch.core.step.item.ChunkOrientedTasklet.execute(ChunkOrientedTasklet.java:75) ~[spring-batch-core-3.0.9.RELEASE.jar!/:3.0.9.RELEASE]
at org.springframework.batch.core.step.tasklet.TaskletStep$ChunkTransactionCallback.doInTransaction(TaskletStep.java:406) ~[spring-batch-core-3.0.9.RELEASE.jar!/:3.0.9.RELEASE]
at org.springframework.batch.core.step.tasklet.TaskletStep$ChunkTransactionCallback.doInTransaction(TaskletStep.java:330) ~[spring-batch-core-3.0.9.RELEASE.jar!/:3.0.9.RELEASE]
at org.springframework.transaction.support.TransactionTemplate.execute(TransactionTemplate.java:133) ~[spring-tx-4.3.18.RELEASE.jar!/:4.3.18.RELEASE]
at org.springframework.batch.core.step.tasklet.TaskletStep$2.doInChunkContext(TaskletStep.java:272) ~[spring-batch-core-3.0.9.RELEASE.jar!/:3.0.9.RELEASE]
at org.springframework.batch.core.scope.context.StepContextRepeatCallback.doInIteration(StepContextRepeatCallback.java:81) ~[spring-batch-core-3.0.9.RELEASE.jar!/:3.0.9.RELEASE]
at org.springframework.batch.repeat.support.RepeatTemplate.getNextResult(RepeatTemplate.java:374) ~[spring-batch-infrastructure-3.0.9.RELEASE.jar!/:3.0.9.RELEASE]
at org.springframework.batch.repeat.support.RepeatTemplate.executeInternal(RepeatTemplate.java:215) ~[spring-batch-infrastructure-3.0.9.RELEASE.jar!/:3.0.9.RELEASE]
at org.springframework.batch.repeat.support.RepeatTemplate.iterate(RepeatTemplate.java:144) ~[spring-batch-infrastructure-3.0.9.RELEASE.jar!/:3.0.9.RELEASE]
at org.springframework.batch.core.step.tasklet.TaskletStep.doExecute(TaskletStep.java:257) ~[spring-batch-core-3.0.9.RELEASE.jar!/:3.0.9.RELEASE]
at org.springframework.batch.core.step.AbstractStep.execute(AbstractStep.java:200) ~[spring-batch-core-3.0.9.RELEASE.jar!/:3.0.9.RELEASE]
at org.springframework.batch.core.job.SimpleStepHandler.handleStep(SimpleStepHandler.java:148) [spring-batch-core-3.0.9.RELEASE.jar!/:3.0.9.RELEASE]
at org.springframework.batch.core.job.flow.JobFlowExecutor.executeStep(JobFlowExecutor.java:64) [spring-batch-core-3.0.9.RELEASE.jar!/:3.0.9.RELEASE]
at org.springframework.batch.core.job.flow.support.state.StepState.handle(StepState.java:67) [spring-batch-core-3.0.9.RELEASE.jar!/:3.0.9.RELEASE]
后跟
org.springframework.dao.DataIntegrityViolationException: PreparedStatementCallback;
SQL [UPDATE BATCH_STEP_EXECUTION set START_TIME = ?, END_TIME = ?, STATUS = ?,
COMMIT_COUNT = ?, READ_COUNT = ?, FILTER_COUNT = ?, WRITE_COUNT = ?, EXIT_CODE = ?,
EXIT_MESSAGE = ?, VERSION = ?, READ_SKIP_COUNT = ?, PROCESS_SKIP_COUNT = ?,
WRITE_SKIP_COUNT = ?, ROLLBACK_COUNT = ?, LAST_UPDATED = ? where STEP_EXECUTION_ID = ?
and VERSION = ?]; Attempt to update or insert row failed because resultant row of size
2633 bytes is larger than the maximum size (1962 bytes) allowed for this table.
; nested exception is com.sybase.jdbc4.jdbc.SybSQLException: Attempt to update or
insert row failed because resultant row of size 2633 bytes is larger than the maximum
size (1962 bytes) allowed for this table.
下面是我的配置
@Configuration
@EnableAutoConfiguration
@EnableBatchProcessing
public class SpringBatchConfig {
@Autowired
private JobBuilderFactory jobBuilderFactory;
@Autowired
private StepBuilderFactory stepBuilderFactory;
@Autowired
public DataSource dataSource;
@Bean
public JdbcPagingItemReader<DistanceFinderModel> reader() {
JdbcPagingItemReader<DistanceFinderModel> reader = new
JdbcPagingItemReader<>();
reader.setDataSource(dataSource);
reader.setFetchSize(200);
reader.setRowMapper(new DistanceFinderRowMapper());
SybasePagingQueryProvider queryProvider = new
SybasePagingQueryProvider();
queryProvider.setSelectClause("*");
queryProvider.setFromClause("from distance_finder");
queryProvider.setWhereClause("batch_id='102'");
Map<String, Order> sortKeys = new HashMap<>(2);
sortKeys.put("batch_id", Order.ASCENDING);
sortKeys.put("pair_id", Order.ASCENDING);
queryProvider.setSortKeys(sortKeys);
reader.setQueryProvider(queryProvider);
return reader;
}
public class DistanceFinderRowMapper implements
RowMapper<DistanceFinderModel>
{
@Override
public DistanceFinderModel mapRow(ResultSet rs, int rowNum) throws
SQLException
{
DistanceFinderModel data = new DistanceFinderModel();
data.setBatch_id(rs.getString("batch_id"));
data.setOrigin_lat(rs.getDouble("origin_lat"));
data.setOrigin_long(rs.getDouble("origin_long"));
data.setDest_lat(rs.getDouble("dest_lat"));
data.setDest_long(rs.getDouble("dest_long"));
data.setDistance(rs.getDouble("distance"));
data.setPair_id(rs.getInt("pair_id"));
return data;
}
}
@Bean
public Processor processor(){
return new Processor();
}
@Bean
public DBWriter writer()
{
return new DBWriter();
}
@Bean
public AsyncItemWriter<DistanceFinderModel> asyncItemWriter() throws
Exception
{
AsyncItemWriter<DistanceFinderModel> asyncItemWriter = new
AsyncItemWriter<>();
asyncItemWriter.setDelegate(writer());
asyncItemWriter.afterPropertiesSet();
return asyncItemWriter;
}
@SuppressWarnings("rawtypes")
@Bean
public AsyncItemProcessor asyncItemProcessor() throws Exception
{
AsyncItemProcessor<DistanceFinderModel, DistanceFinderModel>
asyncItemProcessor = new AsyncItemProcessor<>();
asyncItemProcessor.setDelegate(processor());
asyncItemProcessor.setTaskExecutor(new SimpleAsyncTaskExecutor());
asyncItemProcessor.afterPropertiesSet();
return asyncItemProcessor;
}
@Bean
public TaskExecutor taskExecutor(){
return new SimpleAsyncTaskExecutor("spring_batch");
}
@SuppressWarnings("unchecked")
@Bean
public Step step1() throws Exception{
return stepBuilderFactory.get("step1").
<DistanceFinderModel,DistanceFinderModel>chunk(300)
.reader(reader())
.processor(asyncProcessor())
.writer(asyncItemWriter())
//.taskExecutor(taskExecutor())
.build();
}
@Bean
public Job exportPerosnJob() throws Exception{
return jobBuilderFactory.get("exportPeronJob").incrementer(new
RunIdIncrementer()).flow(step1()).end().build();
}
}
下面是我的处理器
@Component
public class Processor implements ItemProcessor<DistanceFinderModel,
DistanceFinderModel> {
static int count =0;
public Processor() {
}
@Override
public DistanceFinderModel process(DistanceFinderModel val) throws Exception
{
System.out.println("Processsing..");
Thread.sleep(200);
System.out.println("Calculating distance");
RestTemplate restTemplate = new RestTemplate();
String requestURL = "someURl";
Object data = restTemplate.getForObject(requestURL, Object.class);
if(data==null)
{
System.out.println("Could not find distance for ");
System.out.println(val.getPair_id());
return null;
}
//Here I parse the distance from response.
val.setDistance(parsedDistanceValue);
}
}
下面是我的作家,它更新了sybase中的行
@Component
public class DBWriter implements ItemWriter<DistanceFinderModel> {
@Autowired
private DistanceFinderRepository distanceFinderRepository;
static int batch=1;
@Override
public void write(List<? extends DistanceFinderModel> data) throws Exception
{
System.out.println("Data Saved for batch: " + batch++);
distanceFinderRepository.save(data);
}
}
我在互联网上找不到此错误的参考。我尝试更改BATCH_STEP_EXECUTION表,因为它的行大小很大。更改后,我只得到ResourceAccessException和DataIntegrityException(我上面发布的跟进错误)似乎已经消失了。有人可以在这里放点光吗?预先感谢:)