[英]Spring BeanWrapperFieldExtractor FlatFileItemWriter ignore missing null fields
I want to write to a csv file ignoring object field which are null.我想写入 csv 文件,忽略 null 字段的 object 字段。
Currently it writes:目前它写道:
Test,PBAFFF,,测试,PBAFFF,,
The 3rd and 4th values can be null in the object.第 3 和第 4 个值可以是 object 中的 null。
How can I configure FlatFileItemWriter
with BeanWrapperFieldExtractor
which would only write to file the non null
fields?如何使用BeanWrapperFieldExtractor
配置FlatFileItemWriter
,它只会写入非null
字段的文件?
I have my writer configured like this:我的作家配置如下:
csvWriter.setLineAggregator(new DelimitedLineAggregator<Transaction>() {
{
setDelimiter(",");
setFieldExtractor(new BeanWrapperFieldExtractor<Transaction>() {
{
setNames(new String[] { "id", "source", "startDate", "endDate"});
}
});
}
});
There are two ways to do this:有两种方法可以做到这一点:
LineAggregator
实现您的自定义LineAggregator
public class NullSafeDelimitedLineAggregator<T> extends ExtractorLineAggregator<T> {
private String delimiter;
public NullSafeDelimitedLineAggregator(String delimiter, FieldExtractor<T> fieldExtractor) {
this.delimiter = delimiter;
setFieldExtractor(fieldExtractor);
}
@Override
public String doAggregate(Object[] fields) {
return arrayToDelimitedString(fields, delimiter);
}
private String arrayToDelimitedString(@Nullable Object[] arr, String delim) {
if (ObjectUtils.isEmpty(arr)) {
return "";
}
if (arr.length == 1) {
return ObjectUtils.nullSafeToString(arr[0]);
}
StringBuilder sb = new StringBuilder();
for (int i = 0; i < arr.length; i++) {
if(arr[i] == null || "".equals(arr[i])) {
continue;
}
if (i > 0) {
sb.append(delim);
}
sb.append(arr[i]);
}
return sb.toString();
}
}
And change config in following way:并通过以下方式更改配置:
writer.setLineAggregator(new NullSafeDelimitedLineAggregator<>(
",",
new BeanWrapperFieldExtractor<Transaction>() {
{
setNames(new String[] { "id", "source", "startDate", "endDate"});
}
}));
FieldExtractor
实现您的自定义FieldExtractor
public class NullSafeBeanWrapperFieldExtractor<T> implements FieldExtractor<T>, InitializingBean {
private String[] names;
public void setNames(String[] names) {
Assert.notNull(names, "Names must be non-null");
this.names = Arrays.asList(names).toArray(new String[names.length]);
}
@Override
public Object[] extract(T item) {
List<Object> values = new ArrayList<Object>();
BeanWrapper bw = new BeanWrapperImpl(item);
for (String propertyName : this.names) {
Object value = bw.getPropertyValue(propertyName);
if(value == null || "".equals(value)) {
continue;
}
values.add(value);
}
return values.toArray();
}
@Override
public void afterPropertiesSet() {
Assert.notNull(names, "The 'names' property must be set.");
}
}
And change config in following way:并通过以下方式更改配置:
writer.setLineAggregator(new DelimitedLineAggregator<Transaction>() {
{
setDelimiter(",");
setFieldExtractor(new NullSafeBeanWrapperFieldExtractor<Transaction>() {
{
setNames(new String[] { "id", "source", "startDate", "endDate"});
}
});
}
});
Important: You should chose one of two options based on one question: is it important for you to know how many values you have in the array or not?重要提示:您应该根据一个问题选择两个选项之一:知道数组中有多少个值对您来说重要吗? if yes - LineAggregator
, no - FieldExtractor
.如果是 - LineAggregator
,否 - FieldExtractor
。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.