Skip to content

Commit

Permalink
Merge pull request #71 from ozlerhakan/1.19.2
Browse files Browse the repository at this point in the history
version 1.19.2
  • Loading branch information
ozlerhakan committed Jan 10, 2019
2 parents 7fb47ad + 7cf9bde commit 351e497
Show file tree
Hide file tree
Showing 17 changed files with 247 additions and 86 deletions.
66 changes: 28 additions & 38 deletions README.adoc
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
= Poiji
:version: v1.19.1
:version: v1.19.2

image:https://travis-ci.org/ozlerhakan/poiji.svg?branch=master["Build Status", link="https://travis-ci.org/ozlerhakan/poiji"] image:https://api.codacy.com/project/badge/Grade/6587e90886184da29a1b7c5634695c9d["Codacy code quality", link="https://www.codacy.com/app/ozlerhakan/poiji?utm_source=github.com&utm_medium=referral&utm_content=ozlerhakan/poiji&utm_campaign=Badge_Grade"] image:https://coveralls.io/repos/github/ozlerhakan/poiji/badge.svg?branch=master["Coverage Status", link="https://coveralls.io/github/ozlerhakan/poiji?branch=master"] image:https://img.shields.io/badge/apache.poi-4.0.0-brightgreen.svg[] image:https://img.shields.io/badge/gitter-join%20chat-blue.svg["Gitter", link="https://gitter.im/poiji/Lobby"] image:https://img.shields.io/badge/license-MIT-blue.svg[]

Expand All @@ -15,15 +15,15 @@ In your Maven/Gradle project, first add the corresponding dependency:
<dependency>
<groupId>com.github.ozlerhakan</groupId>
<artifactId>poiji</artifactId>
<version>1.19.1</version>
<version>1.19.2</version>
</dependency>
----

.gradle
[source,groovy]
----
dependencies {
compile 'com.github.ozlerhakan:poiji:1.19.1'
compile 'com.github.ozlerhakan:poiji:1.19.2'
}
----

Expand Down Expand Up @@ -320,89 +320,79 @@ Car car = cars.get(0);
Consider you have a table like below:

|===
5+|Class A 5+| Class B
|Name | Age | City | State | Zip Code | Name | Age | City | State | Zip Code
3+|Group A 3+| Group B
|NameA | AgeA | CityA | NameB | AgeB | CityB

|John Doe
|21
|Vienna
|Virginia
|22349
|Smith Michael
|32
|McLean
|Virginia
|22309

|Jane Doe
|28
|Greenbelt
|Maryland
|20993
|Sean Paul
|25
|Los Angeles
|California
|92384

|Paul Ryan
|19
|Alexandria
|Virginia
|22312
|John Peter
|25
|Vienna
|Virginia
|22347

|Peter Pan
|23
|Alexandria
|Virginia
|22314
|Arnold Regan
|35
|Seattle
|Washington
|90384

|===

The new `ExcelCellRange` annotation (as of 1.19) lets us aggregate a range of information in one object model. In this case, we collect the details of the first person in `classA` and for second person in `classB`:

[source,java]
----
public class Classes {
public class Groups {
@ExcelCellRange(begin = 0, end = 4)
private Person classA;
@ExcelCellRange
private GroupA groupA;
@ExcelCellRange(begin = 5, end = 9)
private Person classB;
@ExcelCellRange
private GroupB groupB;
}
----

[source, java]
----
public class Person {
public class GroupA {
@ExcelCellName("Name")
@ExcelCellName("NameA")
private String name;
@ExcelCellName("Age")
@ExcelCellName("AgeA")
private Integer age;
@ExcelCellName("City")
@ExcelCellName("CityA")
private String city;
@ExcelCellName("State")
private String state;
}
public class GroupB {
@ExcelCellName("Zip Code")
private Integer zip;
@ExcelCellName("NameB")
private String name;
@ExcelCellName("AgeB")
private Integer age;
@ExcelCellName("CityB")
private String city;
}
----

Expand All @@ -411,12 +401,12 @@ Using the conventional way, we can retrieve the data using `Poiji.fromExcel`:
[source,java]
----
PoijiOptions options = PoijiOptionsBuilder.settings().headerStart(1).build(); // header starts at 1 (zero-based).
List<Classes> classes = Poiji.fromExcel(new File(excel), Classes.class, options);
List<Groups> groups = Poiji.fromExcel(new File(excel), Groups.class, options);
Classes firstRowClasses = actualClasses.get(0);
Groups firstRowGroups = actualGroups.get(0);
Person firstRowPerson1 = firstRowClasses.getClassA();
Person secondRowPerson2 = firstRowClasses.getClassB();
GroupA firstRowPerson1 = firstRowGroups.getGroupA();
GroupB secondRowPerson2 = firstRowGroups.getGroupB();
----

=== Example 5
Expand Down
2 changes: 1 addition & 1 deletion pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@

<groupId>com.github.ozlerhakan</groupId>
<artifactId>poiji</artifactId>
<version>1.19.1</version>
<version>1.19.2</version>
<packaging>jar</packaging>

<name>poiji</name>
Expand Down
4 changes: 0 additions & 4 deletions src/main/java/com/poiji/annotation/ExcelCellRange.java
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,4 @@
@Target(ElementType.FIELD)
@Documented
public @interface ExcelCellRange {

int begin() default 0;
int end();

}
23 changes: 7 additions & 16 deletions src/main/java/com/poiji/bind/mapping/HSSFUnmarshaller.java
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ abstract class HSSFUnmarshaller implements Unmarshaller {
this.options = options;
dataFormatter = new DataFormatter();
titles = new HashMap<>();
casting = options.getCasting();
casting = options.getCasting();
}

@Override
Expand Down Expand Up @@ -84,7 +84,7 @@ private void loadColumnTitles(Sheet sheet, int maxPhysicalNumberOfRows) {
int row = options.getHeaderStart();
Row firstRow = sheet.getRow(row);
for (Cell cell : firstRow) {
titles.put(cell.getStringCellValue() + cell.getColumnIndex(), cell.getColumnIndex());
titles.put(cell.getStringCellValue(), cell.getColumnIndex());
}
}
}
Expand All @@ -101,7 +101,6 @@ private <T> T deserialize0(Row currentRow, Class<T> type) {
}

private <T> T tailSetFieldValue(Row currentRow, Class<? super T> type, T instance) {
int column = 0;
for (Field field : type.getDeclaredFields()) {
ExcelRow excelRow = field.getAnnotation(ExcelRow.class);
if (excelRow != null) {
Expand All @@ -111,9 +110,6 @@ private <T> T tailSetFieldValue(Row currentRow, Class<? super T> type, T instanc
}
ExcelCellRange excelCellRange = field.getAnnotation(ExcelCellRange.class);
if (excelCellRange != null) {
if (column < excelCellRange.begin() || column > excelCellRange.end()) {
continue;
}
Class<?> o = field.getType();
Object ins;
try {
Expand All @@ -122,29 +118,24 @@ private <T> T tailSetFieldValue(Row currentRow, Class<? super T> type, T instanc
throw new PoijiInstantiationException("Cannot create a new instance of " + o.getName());
}
for (Field f : o.getDeclaredFields()) {
tailSetFieldValue(currentRow, ins, f, column++);
}
try {
field.setAccessible(true);
field.set(instance, ins);
} catch (IllegalArgumentException | IllegalAccessException e) {
throw new PoijiInstantiationException("Cannot access field " + field.getName());
tailSetFieldValue(currentRow, ins, f);
}
setFieldData(instance, field, ins);
} else {
tailSetFieldValue(currentRow, instance, field, column++);
tailSetFieldValue(currentRow, instance, field);
}
}
return instance;
}

private <T> void tailSetFieldValue(Row currentRow, T instance, Field field, int column) {
private <T> void tailSetFieldValue(Row currentRow, T instance, Field field) {
ExcelCell index = field.getAnnotation(ExcelCell.class);
if (index != null) {
constructTypeValue(currentRow, instance, field, index.value());
} else {
ExcelCellName excelCellName = field.getAnnotation(ExcelCellName.class);
if (excelCellName != null) {
Integer titleColumn = titles.get(excelCellName.value() + column);
Integer titleColumn = titles.get(excelCellName.value());
if (titleColumn != null) {
constructTypeValue(currentRow, instance, field, titleColumn);
}
Expand Down
7 changes: 2 additions & 5 deletions src/main/java/com/poiji/bind/mapping/PoijiHandler.java
Original file line number Diff line number Diff line change
Expand Up @@ -129,9 +129,6 @@ private boolean setValue(String content, Class<? super T> type, int column) {
}
ExcelCellRange range = field.getAnnotation(ExcelCellRange.class);
if (range != null) {
if (column < range.begin() || column > range.end()) {
continue;
}
Object ins = null;
ins = getInstance(field);
for (Field f : field.getType().getDeclaredFields()) {
Expand Down Expand Up @@ -164,7 +161,7 @@ private boolean setValue(Field field, int column, String content, Object ins) {
ExcelCellName excelCellName = field.getAnnotation(ExcelCellName.class);
if (excelCellName != null) {
Class<?> fieldType = field.getType();
Integer titleColumn = titles.get(excelCellName.value() + column);
Integer titleColumn = titles.get(excelCellName.value() );
//Fix both columns mapped to name passing this condition below
if (titleColumn != null && titleColumn == column) {
Object o = casting.castValue(fieldType, content, options);
Expand Down Expand Up @@ -215,7 +212,7 @@ public void cell(String cellReference, String formattedValue, XSSFComment commen
int headers = options.getHeaderStart();

if (row <= headers) {
titles.put(formattedValue + column, column);
titles.put(formattedValue, column);
}

if (row + 1 <= options.skip()) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,8 @@

import com.poiji.bind.Poiji;
import com.poiji.deserialize.model.byid.Classes;
import com.poiji.deserialize.model.byid.PersonTest;
import com.poiji.deserialize.model.byid.PersonATest;
import com.poiji.deserialize.model.byid.PersonBTest;
import com.poiji.option.PoijiOptions;
import com.poiji.option.PoijiOptions.PoijiOptionsBuilder;
import org.junit.Test;
Expand Down Expand Up @@ -49,10 +50,10 @@ public void shouldMapExcelToJavaMulti() {
Classes actualClasses1 = actualClasses.get(0);
Classes actualClasses2 = actualClasses.get(1);

PersonTest expectedPerson1 = actualClasses1.getClassA();
PersonTest expectedPerson2 = actualClasses1.getClassB();
PersonTest expectedPerson3 = actualClasses2.getClassA();
PersonTest expectedPerson4 = actualClasses2.getClassB();
PersonATest expectedPerson1 = actualClasses1.getClassA();
PersonBTest expectedPerson2 = actualClasses1.getClassB();
PersonATest expectedPerson3 = actualClasses2.getClassA();
PersonBTest expectedPerson4 = actualClasses2.getClassB();

assertThat(expectedPerson1.getAge(), is(28));
assertThat(expectedPerson2.getCity(), is("Los Angeles"));
Expand Down
54 changes: 54 additions & 0 deletions src/test/java/com/poiji/deserialize/DeserializerCaseTest.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
package com.poiji.deserialize;

import com.poiji.bind.Poiji;
import com.poiji.deserialize.model.ProductExcelDTO;
import com.poiji.exception.PoijiExcelType;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.Parameterized;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.Arrays;
import java.util.List;

import static org.hamcrest.CoreMatchers.not;
import static org.hamcrest.CoreMatchers.notNullValue;
import static org.junit.Assert.assertThat;
import static org.junit.Assert.fail;

/**
* Created by hakan on 2019-01-10
*/
@RunWith(Parameterized.class)
public class DeserializerCaseTest {

private String path;
private PoijiExcelType poijiExcelType;

public DeserializerCaseTest(String path, PoijiExcelType type) {
this.path = path;
this.poijiExcelType = type;
}

@Parameterized.Parameters(name = "{index}: ({0})={1}")
public static Iterable<Object[]> queries() {
return Arrays.asList(new Object[][]{
{"src/test/resources/test.xlsx", PoijiExcelType.XLSX},
{"src/test/resources/test.xls", PoijiExcelType.XLS},
});
}

@Test
public void shouldMapExcelToJava() {
try (InputStream stream = new FileInputStream(new File(path))) {
List<ProductExcelDTO> products = Poiji.fromExcel(stream, poijiExcelType, ProductExcelDTO.class);
assertThat(products, notNullValue());
assertThat(products.size(), not(0));
} catch (IOException e) {
fail(e.getMessage());
}
}
}

2 comments on commit 351e497

@kpolli
Copy link
Contributor

@kpolli kpolli commented on 351e497 Jan 11, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sorry to jump in, I tested the excel and java objects that fermartinez1 posted with the 1.19.1 and it worked for both xls and xlsx. The excelcellrange is for cases when the column names are not unique and so the range is meant to differentiate which name belongs to which object.

I'm going to look further into why it happened in the master branch.

@ozlerhakan
Copy link
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hi @kpolli , I made some changes in @ExcelCellRange. From now on, we don't need to give a range on this annotation. and the part that I totally overlooked is the header names. The header names must be unique always. Please look at the updated readme file, example 4.

Please sign in to comment.