Search code examples
javajavabeansopencsv

Can't write JavaBeans to CSV using OpenCSV


I'm trying to write some data to a CSV file using OpenCSV. However, when I try to store the data I get a CsvBeanIntrospectionException followed with a NoSuchMethodException: Unknown property 'Email' on class 'class SubscriberBean'.

Here's the code of my JavaBean class:

import com.opencsv.bean.CsvBindByName;

import java.io.Serializable;

public class SubscriberBean implements Serializable {

@CsvBindByName
String Email;

@CsvBindByName
String Name;

public SubscriberBean() {}

public SubscriberBean(String email, String name) {
    this.Email = email;
    this.Name = name;
}

public String getName() {
    return Name;
}

public void setName(String name) {
    Name = name;
}

public String getEmail() {
    return Email;
}

public void setEmail(String email) {
    Email = email;
}

@Override
public String toString() {
    return "SubscriberBean [" + "Email=" + Email + ", Name=" + Name + ']';
}

public Boolean isEmpty() {
    return (this.Name.equals("") || this.Email.equals("") || this.Name == null || this.Email == null);
}

and the code of how I try to store data in my csv file:

List<SubscriberBean>  lsb = new ArrayList<SubscriberBean>();
.
.
.

    try {
        Writer writer = new FileWriter("test.csv");
        StatefulBeanToCsv beanToCsv = new StatefulBeanToCsvBuilder(writer).build();

        beanToCsv.write(lsb);
        writer.close();
    } catch (CsvDataTypeMismatchException e) {
        e.printStackTrace();
    } catch (CsvRequiredFieldEmptyException e) {
        e.printStackTrace();
    } catch (IOException e) {
        e.printStackTrace();
    }

I checked the JavaBean class, it looks fine. The CSV code is almost the same as in the example that is provided on the opencsv website.


Solution

  • Almost there ;)

    The apache beanutils expects your fields to start with lowercase. E.g. email, not Email, etc. This is the fixed SubscriberBean:

    public class SubscriberBean implements Serializable {
    
        @CsvBindByName
        String email;
    
        @CsvBindByName
        String name;
    
        public SubscriberBean() {
        }
    
        public SubscriberBean(String email, String name) {
            this.email = email;
            this.name = name;
        }
    
        public String getName() {
            return name;
        }
    
        public void setName(String name) {
            this.name = name;
        }
    
        public String getEmail() {
            return email;
        }
    
        public void setEmail(String email) {
            this.email = email;
        }
    
        // ...
    
    }
    

    Please note that due to the lowercase fields, I had to change the setters slightly. I added the this reference: this.email = email;