diff --git a/easyexcel-core/src/main/java/com/alibaba/excel/util/ClassUtils.java b/easyexcel-core/src/main/java/com/alibaba/excel/util/ClassUtils.java index f9a53e08..77acc43d 100644 --- a/easyexcel-core/src/main/java/com/alibaba/excel/util/ClassUtils.java +++ b/easyexcel-core/src/main/java/com/alibaba/excel/util/ClassUtils.java @@ -313,10 +313,12 @@ public class ClassUtils { Map> orderFieldMap = new TreeMap<>(); Map indexFieldMap = new TreeMap<>(); Set ignoreSet = new HashSet<>(); + Map excelPropertyFieldMap = new HashMap<>(16); ExcelIgnoreUnannotated excelIgnoreUnannotated = clazz.getAnnotation(ExcelIgnoreUnannotated.class); for (Field field : tempFieldList) { - declaredOneField(field, orderFieldMap, indexFieldMap, ignoreSet, excelIgnoreUnannotated); + declaredOneField(field, orderFieldMap, indexFieldMap, ignoreSet, excelPropertyFieldMap, + excelIgnoreUnannotated); } Map sortedFieldMap = buildSortedAllFieldMap(orderFieldMap, indexFieldMap); FieldCache fieldCache = new FieldCache(sortedFieldMap, indexFieldMap); @@ -451,7 +453,7 @@ public class ClassUtils { } private static void declaredOneField(Field field, Map> orderFieldMap, - Map indexFieldMap, Set ignoreSet, + Map indexFieldMap, Set ignoreSet, Map excelPropertyFieldMap, ExcelIgnoreUnannotated excelIgnoreUnannotated) { String fieldName = FieldUtils.resolveCglibFieldName(field); FieldWrapper fieldWrapper = new FieldWrapper(); @@ -477,6 +479,19 @@ public class ClassUtils { ignoreSet.add(fieldName); return; } + + // Ignore parent field when the child field is set to be ignored + if (ignoreSet.contains(field.getName())) { + return; + } + + // Ignore parent field when the child field is set to be excel column + if (excelPropertyFieldMap.containsKey(field.getName())) { + return; + } + + excelPropertyFieldMap.put(field.getName(), field); + // set heads if (excelProperty != null) { fieldWrapper.setHeads(excelProperty.value()); diff --git a/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/Child1.java b/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/Child1.java new file mode 100644 index 00000000..ed56e6a1 --- /dev/null +++ b/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/Child1.java @@ -0,0 +1,17 @@ +package com.alibaba.easyexcel.test.temp.ignore_annotation; + +import com.alibaba.excel.annotation.ExcelIgnore; +import com.alibaba.excel.annotation.ExcelProperty; +import lombok.Data; + +/** + * @author atdt + */ +@Data +public class Child1 extends ParentWithPropertyAnnotation { + @ExcelProperty("地址") + private String address; + + @ExcelIgnore + private String phone; +} diff --git a/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/Child2.java b/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/Child2.java new file mode 100644 index 00000000..4a4a8ee5 --- /dev/null +++ b/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/Child2.java @@ -0,0 +1,17 @@ +package com.alibaba.easyexcel.test.temp.ignore_annotation; + +import com.alibaba.excel.annotation.ExcelIgnore; +import com.alibaba.excel.annotation.ExcelProperty; +import lombok.Data; + +/** + * @author atdt + */ +@Data +public class Child2 extends ParentWithIgnoreAnnotation { + @ExcelProperty("地址") + private String address; + + @ExcelIgnore + private String phone; +} diff --git a/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/Child3.java b/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/Child3.java new file mode 100644 index 00000000..e30ce450 --- /dev/null +++ b/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/Child3.java @@ -0,0 +1,16 @@ +package com.alibaba.easyexcel.test.temp.ignore_annotation; + +import com.alibaba.excel.annotation.ExcelProperty; +import lombok.Data; + +/** + * @author atdt + */ +@Data +public class Child3 extends ParentWithPropertyAnnotation { + @ExcelProperty("地址") + private String address; + + @ExcelProperty("电话") + private String phone; +} diff --git a/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/Child4.java b/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/Child4.java new file mode 100644 index 00000000..7c50eab6 --- /dev/null +++ b/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/Child4.java @@ -0,0 +1,16 @@ +package com.alibaba.easyexcel.test.temp.ignore_annotation; + +import com.alibaba.excel.annotation.ExcelProperty; +import lombok.Data; + +/** + * @author atdt + */ +@Data +public class Child4 extends ParentWithIgnoreAnnotation { + @ExcelProperty("地址") + private String address; + + @ExcelProperty("电话") + private String phone; +} diff --git a/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/IgnoreAnnotationTest.java b/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/IgnoreAnnotationTest.java new file mode 100644 index 00000000..b56963b1 --- /dev/null +++ b/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/IgnoreAnnotationTest.java @@ -0,0 +1,177 @@ +package com.alibaba.easyexcel.test.temp.ignore_annotation; + +import com.alibaba.easyexcel.test.util.TestFileUtil; +import com.alibaba.excel.EasyExcel; +import com.alibaba.excel.ExcelWriter; +import com.alibaba.excel.write.metadata.WriteSheet; +import org.apache.poi.ss.usermodel.Sheet; +import org.apache.poi.ss.usermodel.Workbook; +import org.apache.poi.ss.usermodel.WorkbookFactory; +import org.junit.jupiter.api.Assertions; +import org.junit.jupiter.api.Test; + +import java.io.File; +import java.util.Collections; + +/** + * @author atdt + */ +public class IgnoreAnnotationTest { + + /** + * 父类与子类存在相同名字属性, + * 并且子类注解为 ExcelIgnore,父类注解为 ExcelProperty 时 + * 输出文档中忽略该属性 + */ + @Test + public void test1() throws Exception { + String fileName = TestFileUtil.getPath() + "excelIgnoreAnnotation" + System.currentTimeMillis() + ".xlsx"; + try (ExcelWriter excelWriter = EasyExcel.write(fileName, Child1.class).build()) { + WriteSheet writeSheet = EasyExcel.writerSheet("test").build(); + Child1 child = new Child1(); + child.setAddress("武汉"); + child.setName("张三"); + child.setPhone("123"); + excelWriter.write(Collections.singletonList(child), writeSheet); + } + + Sheet sheet; + try (Workbook workbook = WorkbookFactory.create(new File(fileName))) { + sheet = workbook.getSheet("test"); + } + + /* + 预想结果(phone属性被忽略) + | 地址(子类定义) | 名字(父类定义) | + | --- | --- | + | 武汉 | 张三 | + */ + Assertions.assertEquals(sheet.getLastRowNum(), 1); + Assertions.assertEquals("地址", sheet.getRow(0).getCell(0).getStringCellValue(), "表头不正"); + Assertions.assertEquals("名字", sheet.getRow(0).getCell(1).getStringCellValue(), "表头不正"); + Assertions.assertNull(sheet.getRow(0).getCell(2)); + + Assertions.assertEquals("武汉", sheet.getRow(1).getCell(0).getStringCellValue(), "地址不正"); + Assertions.assertEquals("张三", sheet.getRow(1).getCell(1).getStringCellValue(), "名字不正"); + Assertions.assertNull(sheet.getRow(1).getCell(2)); + } + + /** + * 父类与子类存在相同名字属性, + * 并且子类注解为 ExcelIgnore,父类注解为 ExcelIgnore 时 + * 输出文档中忽略该属性 + */ + @Test + public void test2() throws Exception { + String fileName = TestFileUtil.getPath() + "excelIgnoreAnnotation" + System.currentTimeMillis() + ".xlsx"; + try (ExcelWriter excelWriter = EasyExcel.write(fileName, Child2.class).build()) { + WriteSheet writeSheet = EasyExcel.writerSheet("test").build(); + Child2 child = new Child2(); + child.setAddress("武汉"); + child.setName("张三"); + child.setPhone("123"); + excelWriter.write(Collections.singletonList(child), writeSheet); + } + + Sheet sheet; + try (Workbook workbook = WorkbookFactory.create(new File(fileName))) { + sheet = workbook.getSheet("test"); + } + + /* + 预想结果(phone属性被忽略) + | 地址(子类定义) | 名字(父类定义) | + | --- | --- | + | 武汉 | 张三 | + */ + Assertions.assertEquals(sheet.getLastRowNum(), 1); + Assertions.assertEquals("地址", sheet.getRow(0).getCell(0).getStringCellValue(), "表头不正"); + Assertions.assertEquals("名字", sheet.getRow(0).getCell(1).getStringCellValue(), "表头不正"); + Assertions.assertNull(sheet.getRow(0).getCell(2)); + + Assertions.assertEquals("武汉", sheet.getRow(1).getCell(0).getStringCellValue(), "地址不正"); + Assertions.assertEquals("张三", sheet.getRow(1).getCell(1).getStringCellValue(), "名字不正"); + Assertions.assertNull(sheet.getRow(1).getCell(2)); + } + + /** + * 父类与子类存在相同名字属性, + * 并且子类注解为 ExcelProperty,父类注解也为 ExcelProperty 时 + * 输出文档中只包含子类属性,不包含父类属性 + */ + @Test + public void test3() throws Exception { + String fileName = TestFileUtil.getPath() + "excelIgnoreAnnotation" + System.currentTimeMillis() + ".xlsx"; + try (ExcelWriter excelWriter = EasyExcel.write(fileName, Child3.class).build()) { + WriteSheet writeSheet = EasyExcel.writerSheet("test").build(); + Child3 child = new Child3(); + child.setAddress("武汉"); + child.setName("张三"); + child.setPhone("123"); + excelWriter.write(Collections.singletonList(child), writeSheet); + } + + Sheet sheet; + try (Workbook workbook = WorkbookFactory.create(new File(fileName))) { + sheet = workbook.getSheet("test"); + } + + /* + 预想结果(父类phone属性被忽略) + | 地址(子类定义) | 名字(父类定义) | 电话(子类定义) | + | --- | --- | --- | + | 武汉 | 张三 | 123 | + */ + Assertions.assertEquals(sheet.getLastRowNum(), 1); + Assertions.assertEquals("地址", sheet.getRow(0).getCell(0).getStringCellValue(), "表头不正"); + Assertions.assertEquals("电话", sheet.getRow(0).getCell(1).getStringCellValue(), "表头不正"); + Assertions.assertEquals("名字", sheet.getRow(0).getCell(2).getStringCellValue(), "表头不正"); + Assertions.assertNull(sheet.getRow(0).getCell(3)); + + Assertions.assertEquals("武汉", sheet.getRow(1).getCell(0).getStringCellValue(), "地址不正"); + Assertions.assertEquals("123", sheet.getRow(1).getCell(1).getStringCellValue(), "电话不正"); + Assertions.assertEquals("张三", sheet.getRow(1).getCell(2).getStringCellValue(), "名字不正"); + Assertions.assertNull(sheet.getRow(1).getCell(3)); + } + + /** + * 父类与子类存在相同名字属性, + * 并且子类注解为 ExcelProperty,父类注解为 ExcelIgnore 时 + * 输出文档中包含该属性 + */ + @Test + public void test4() throws Exception { + String fileName = TestFileUtil.getPath() + "excelIgnoreAnnotation" + System.currentTimeMillis() + ".xlsx"; + try (ExcelWriter excelWriter = EasyExcel.write(fileName, Child4.class).build()) { + WriteSheet writeSheet = EasyExcel.writerSheet("test").build(); + Child4 child = new Child4(); + child.setAddress("武汉"); + child.setName("张三"); + child.setPhone("123"); + excelWriter.write(Collections.singletonList(child), writeSheet); + } + + Sheet sheet; + try (Workbook workbook = WorkbookFactory.create(new File(fileName))) { + sheet = workbook.getSheet("test"); + } + + /* + 预想结果 + | 地址(子类定义) | 电话(父类定义) | 名字(子类定义) | + | --- | --- | --- | + | 武汉 | 123 | 张三 | + */ + Assertions.assertEquals(sheet.getLastRowNum(), 1); + Assertions.assertEquals("地址", sheet.getRow(0).getCell(0).getStringCellValue(), "表头不正"); + Assertions.assertEquals("电话", sheet.getRow(0).getCell(1).getStringCellValue(), "表头不正"); + Assertions.assertEquals("名字", sheet.getRow(0).getCell(2).getStringCellValue(), "表头不正"); + Assertions.assertNull(sheet.getRow(0).getCell(3)); + + Assertions.assertEquals("武汉", sheet.getRow(1).getCell(0).getStringCellValue(), "地址不正"); + Assertions.assertEquals("123", sheet.getRow(1).getCell(1).getStringCellValue(), "名字不正"); + Assertions.assertEquals("张三", sheet.getRow(1).getCell(2).getStringCellValue(), "电话不正"); + Assertions.assertNull(sheet.getRow(1).getCell(3)); + } + +} diff --git a/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/ParentWithIgnoreAnnotation.java b/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/ParentWithIgnoreAnnotation.java new file mode 100644 index 00000000..a4484053 --- /dev/null +++ b/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/ParentWithIgnoreAnnotation.java @@ -0,0 +1,17 @@ +package com.alibaba.easyexcel.test.temp.ignore_annotation; + +import com.alibaba.excel.annotation.ExcelIgnore; +import com.alibaba.excel.annotation.ExcelProperty; +import lombok.Data; + +/** + * @author atdt + */ +@Data +public class ParentWithIgnoreAnnotation { + @ExcelProperty("名字") + private String name; + + @ExcelIgnore + private String phone; +} diff --git a/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/ParentWithPropertyAnnotation.java b/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/ParentWithPropertyAnnotation.java new file mode 100644 index 00000000..0b33da7f --- /dev/null +++ b/easyexcel-test/src/test/java/com/alibaba/easyexcel/test/temp/ignore_annotation/ParentWithPropertyAnnotation.java @@ -0,0 +1,16 @@ +package com.alibaba.easyexcel.test.temp.ignore_annotation; + +import com.alibaba.excel.annotation.ExcelProperty; +import lombok.Data; + +/** + * @author atdt + */ +@Data +public class ParentWithPropertyAnnotation { + @ExcelProperty("名字") + private String name; + + @ExcelProperty("电话") + private String phone; +}