Spring-batch使用PatternMatchingCompositeLineTokenizer解析不规则数据文件



     大家都知道,传统Spring-batch能够很好的处理批量任务,其中,提供的trunk组件(batch:trunk)能够处理行文本或者数据库的普通读写操作。下面这个例子可以读写基本的规范数据文件:

     


       
       
       


    
    	
        
    	
    	    
    		    
    
    

上述代码中,wxReader负责解析源文件:

resource配置源文件的地址,

encoding配置文件的编码方式,

comments配置注释行的开头,可以跳过注释行,本文例子跳过以#开头的注释行,不进行处理

lineMapper负责具体的处理文件的类,后文会介绍

lineToSkip用来指定跳过处理文本的头N行,本例跳过1行

 

 

lineMapper的配置

 

  
    	
    	
    		
    		
    	
    

     	
    	
	   		
	   			tradeTime
	   			pubAccountId
	   			merchantId
	   			subMerchantId
	   			deviceId
	   			wxOrderId
	   			merchantOrderId
	   			userTag
	   			tradeType
	   			tradeStatus
	   			payerBank
	   			capitalType
	   			totalAmount
	   			enterpriseRedAmount
	   			wxRefundId
	   			merchantRefundId
	   			refundAmount
	   			enterpriseRedRefundAmount
	   			refundType
	   			refundStatus
	   			goodsName
	   			merchantData
	   			fee
	   			feeRate
	   		
    	
    

 

该配置中,使用org.springframework.batch.item.file.transform.DelimitedLineTokenizer进行文件解析,能够将解析出来的每一行利用类com.secondgame.demo_service.demo.batch.task.WxFileSetMapper进行处理。

实际应用中,数据源没有想象的那么“整齐”,可以通过离线数据清洗(各种脚本)的方式将数据进行预处理。但对于基本整齐的文件,可以采用spring-batch提供的行解析器org.springframework.batch.item.file.transform.PatternMatchingCompositeLineTokenizer进行处理。该解析器不受限于一种解析器,可以根据通配符配置,对不同的行进行不同的解析,假设文本文件有如下结构:

 

1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24
1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24
1,2,3,4,5
1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24

该文件每行数据由逗号分隔,但是存在不规则的行(或者有特殊意义,作者遇到的情况是,对账明细单最后有汇总项,而且无法通过前缀区分)。该文本在上述代码配置中,会直接在解析第三行的地方报错:需要24个参数,实际只有5个。

笔者想到的解决方案有如下几种:

1. 与处理文件,把不规则的第三行处理掉

2. 补齐第三行的数据,凑足24个内容。

两者都需要额外的处理数据过程,而使用前文介绍的PatternMatchingCompositeLineTokenizer则可以直接处理该种情况。

 

部分实现的代码如下(仅体现核心思想,直接拷贝代码无法使用,实际工程需要额外配置文件):


    	
    	
    		
    		
    	
    
    
    	
   		
   			
   				
   				
   			
   		
   	
    
     	
    	
	   		
	   			tradeTime
	   			pubAccountId
	   			merchantId
	   			subMerchantId
	   			deviceId
	   			wxOrderId
	   			merchantOrderId
	   			userTag
	   			tradeType
	   			tradeStatus
	   			payerBank
	   			capitalType
	   			totalAmount
	   			enterpriseRedAmount
	   			wxRefundId
	   			merchantRefundId
	   			refundAmount
	   			enterpriseRedRefundAmount
	   			refundType
	   			refundStatus
	   			goodsName
	   			merchantData
	   			fee
	   			feeRate
	   		
    	
    
    
     	
     	
	   		
	   			totalCount
	   			totalAmount
	   			refundAmount
	   			enterpriseRedRefundAmount
	   			fee
	   		
    	
    

上述代码实现了两个行解析器,分别解析24个数据和5个数据的情况,其他情况可以继续增加行解析器即可。

 

如果数据文件情况更加复杂,可以考虑自定义行解析器,实现自定义功能,这个笔者并没有进一步的研究,以后可以再尝试,本文思路来自于stackoverflow:

http://stackoverflow.com/questions/27504722/how-to-custom-spring-batch-delimitedlinetokenizer

不过这个作者的代码通配符部分我实现*全量替代过不去,还需要进一步看源码。

 

 

 

你可能感兴趣的:(java,Spring)