Spring 批次中的多个写入器具有不同的实体
Multiple Writers in Spring Batch with different entities
初始代码:
Tasklet class 被定义为有 3 个方法:
class Tasklet{
doBeforeStep(){
//Records a retrieved from the table.
}
doExecute(){
//It opens the file and reads the file.
//Does all the processing one by one and creates a 2 list of records to update into the database.
}
doAfterStep(){
//The 2 list of records(Entities) are saved into the 2 different tables database using its corresponding repository class. Example:
RepositoryClass.saveall(List containing 105,000 records) //using the CRUDRepository method
}
}
面临的问题:
该文件包含 150,000 条记录,因此,在 doExecute() 方法之后,它在列表中存储了 150,000 条数据记录。在 doAfterStep() 方法中,它尝试将列表中的所有 150,000 条记录保存到数据库,因此出现事务超时错误。
解决方法:
尝试将上面的class重新设计为ItemReader、ItemProcessor和ItemWriter这样我就可以引入Chunk的概念并尝试一次更新1000条记录并继续循环.
-- 这种方法的问题:
在块概念的情况下,我们需要提及传入实体和传出实体,例如:
.get("stepToReadDataFromFile")
.<Entity1, Entity2>chunk(1000)
.reader(FileReader())
.processor(Processor())
.writer(Writer())
.build();```
但情况是,它会从文件中读取(可能是Entity1),然后将其写入2个表(即2个实体)。 我们如何在这里定义 2 个实体。
还将数据从一个 class 发送到另一个,例如:
在 ItemReader 中,ItemReader 的结果通过这样发送到 ItemProcessor:
public class FileReader extends Itemreader<Entity1>
在 ItemProcessor 中,ItemProcessor 的结果通过 :
发送到 ItemWriter
public class FileProcessor extends ItemProcessor<Entity1, Entity2> {
现阶段我们如何发送 2 个实体,Entity2 和 Entity3?
您可以将 Entity2
和 Entity3
组合在一个对象中,并将 ItemProcessor
调整为 return 这个组合对象。例如:
public class ProcessResult {
private Entity2 e2;
private Entity3 e3;
}
ItemProcessor 看起来像:
public class FileProcessor extends ItemProcessor<Entity1, ProcessResult> {
public ProcessResult process(Entity1 e1){
//processing ....
return new ProcessResult(entity2 , entity3);
}
}
在 ItemWriter
中,您可以从 ProcessResult
.
访问 Entity2
和 Entity3
初始代码:
Tasklet class 被定义为有 3 个方法:
class Tasklet{
doBeforeStep(){
//Records a retrieved from the table.
}
doExecute(){
//It opens the file and reads the file.
//Does all the processing one by one and creates a 2 list of records to update into the database.
}
doAfterStep(){
//The 2 list of records(Entities) are saved into the 2 different tables database using its corresponding repository class. Example:
RepositoryClass.saveall(List containing 105,000 records) //using the CRUDRepository method
}
}
面临的问题: 该文件包含 150,000 条记录,因此,在 doExecute() 方法之后,它在列表中存储了 150,000 条数据记录。在 doAfterStep() 方法中,它尝试将列表中的所有 150,000 条记录保存到数据库,因此出现事务超时错误。
解决方法:
尝试将上面的class重新设计为ItemReader、ItemProcessor和ItemWriter这样我就可以引入Chunk的概念并尝试一次更新1000条记录并继续循环. -- 这种方法的问题: 在块概念的情况下,我们需要提及传入实体和传出实体,例如:
.get("stepToReadDataFromFile") .<Entity1, Entity2>chunk(1000) .reader(FileReader()) .processor(Processor()) .writer(Writer()) .build();```
但情况是,它会从文件中读取(可能是Entity1),然后将其写入2个表(即2个实体)。 我们如何在这里定义 2 个实体。
还将数据从一个 class 发送到另一个,例如: 在 ItemReader 中,ItemReader 的结果通过这样发送到 ItemProcessor:
public class FileReader extends Itemreader<Entity1>
在 ItemProcessor 中,ItemProcessor 的结果通过 :
发送到 ItemWriterpublic class FileProcessor extends ItemProcessor<Entity1, Entity2> {
现阶段我们如何发送 2 个实体,Entity2 和 Entity3?
您可以将 Entity2
和 Entity3
组合在一个对象中,并将 ItemProcessor
调整为 return 这个组合对象。例如:
public class ProcessResult {
private Entity2 e2;
private Entity3 e3;
}
ItemProcessor 看起来像:
public class FileProcessor extends ItemProcessor<Entity1, ProcessResult> {
public ProcessResult process(Entity1 e1){
//processing ....
return new ProcessResult(entity2 , entity3);
}
}
在 ItemWriter
中,您可以从 ProcessResult
.
Entity2
和 Entity3