Skip to content

Instantly share code, notes, and snippets.

@canthony
Created September 6, 2012 12:47
Show Gist options
  • Star 6 You must be signed in to star a gist
  • Fork 3 You must be signed in to fork a gist
  • Save canthony/3655917 to your computer and use it in GitHub Desktop.
Save canthony/3655917 to your computer and use it in GitHub Desktop.
Vaadin : Reading an uploaded CSV File and using it to populate a Container/Table
package org.backstage;
import au.com.bytecode.opencsv.CSVReader;
import com.vaadin.Application;
import com.vaadin.data.Item;
import com.vaadin.data.util.IndexedContainer;
import com.vaadin.ui.Table;
import com.vaadin.ui.Upload;
import com.vaadin.ui.VerticalLayout;
import com.vaadin.ui.Window;
import java.io.File;
import java.io.FileOutputStream;
import java.io.FileReader;
import java.io.IOException;
import java.io.OutputStream;
import java.io.Reader;
public class CSVFileApplication extends Application {
protected File tempFile;
protected Table table;
@Override
public void init() {
/* Create and configure the upload component */
Upload upload = new Upload("Upload CSV File", new Upload.Receiver() {
@Override
public OutputStream receiveUpload(String filename, String mimeType) {
try {
/* Here, we'll stored the uploaded file as a temporary file. No doubt there's
a way to use a ByteArrayOutputStream, a reader around it, use ProgressListener (and
a progress bar) and a separate reader thread to populate a container *during*
the update.
This is quick and easy example, though.
*/
tempFile = File.createTempFile("temp", ".csv");
return new FileOutputStream(tempFile);
} catch (IOException e) {
e.printStackTrace();
return null;
}
}
});
upload.addListener(new Upload.FinishedListener() {
@Override
public void uploadFinished(Upload.FinishedEvent finishedEvent) {
try {
/* Let's build a container from the CSV File */
FileReader reader = new FileReader(tempFile);
IndexedContainer indexedContainer = buildContainerFromCSV(reader);
reader.close();
tempFile.delete();
/* Finally, let's update the table with the container */
table.setCaption(finishedEvent.getFilename());
table.setContainerDataSource(indexedContainer);
table.setVisible(true);
} catch (IOException e) {
e.printStackTrace();
}
}
});
/* Table to show the contents of the file */
table = new Table();
table.setVisible(false);
/* Main layout */
VerticalLayout layout = new VerticalLayout();
layout.setMargin(true);
layout.setSpacing(true);
layout.addComponent(table);
layout.addComponent(upload);
/* Build the main window */
Window w = new Window("CSV Upload Demo");
w.setContent(layout);
setMainWindow(w);
}
/**
* Uses http://opencsv.sourceforge.net/ to read the entire contents of a CSV
* file, and creates an IndexedContainer from it
*
* @param reader
* @return
* @throws IOException
*/
protected IndexedContainer buildContainerFromCSV(Reader reader) throws IOException {
IndexedContainer container = new IndexedContainer();
CSVReader csvReader = new CSVReader(reader);
String[] columnHeaders = null;
String[] record;
while ((record = csvReader.readNext()) != null) {
if (columnHeaders == null) {
columnHeaders = record;
addItemProperties(container, columnHeaders);
} else {
addItem(container, columnHeaders, record);
}
}
return container;
}
/**
* Set's up the item property ids for the container. Each is a String (of course,
* you can create whatever data type you like, but I guess you need to parse the whole file
* to work it out)
*
* @param container The container to set
* @param columnHeaders The column headers, i.e. the first row from the CSV file
*/
private static void addItemProperties(IndexedContainer container, String[] columnHeaders) {
for (String propertyName : columnHeaders) {
container.addContainerProperty(propertyName, String.class, null);
}
}
/**
* Adds an item to the given container, assuming each field maps to it's corresponding property id.
* Again, note that I am assuming that the field is a string.
*
* @param container
* @param propertyIds
* @param fields
*/
private static void addItem(IndexedContainer container, String[] propertyIds, String[] fields) {
if (propertyIds.length != fields.length) {
throw new IllegalArgumentException("Hmmm - Different number of columns to fields in the record");
}
Object itemId = container.addItem();
Item item = container.getItem(itemId);
for (int i = 0; i < fields.length; i++) {
String propertyId = propertyIds[i];
String field = fields[i];
item.getItemProperty(propertyId).setValue(field);
}
}
}
@r1k4rd0
Copy link

r1k4rd0 commented Jul 15, 2013

Very useful... Thanks. Greetz from Costa Rica.

@iamviyer
Copy link

I am new to Vaadin and was interested using this code for reading CSV files.
But I am getting error in following imports

import au.com.bytecode.opencsv.CSVReader;
import com.vaadin.Application;

Can you please share the same ?

@canthony
Copy link
Author

@iamviyer: this code was written well over a year ago, and was for Vaadin 6.x; that's where the Application comes from. The bulk of the code will work just fine with Vaadin 7.x: I suggest you get a normal "application/UI working, and then try and adapt this code to work with V7.

As the comments suggest, the CSVReader comes from http://opencsv.sourceforge.net/

@poovannan89
Copy link

Hi Cathony, I am new to Vaadin and have a query. We have loaded the csv file data to a table using Indexed container. We were not able to select a row in that table. Also, We like to have the field editable for user to edit it once a particular row is selected. Hope you got the query ? Awaiting for your response

@phamtienthanh-luvina
Copy link

Thanks :)

@anjul
Copy link

anjul commented Apr 22, 2019

Could someone assist me on the same use case as mentioned here but need to do in vaadin flow java grid. Cause Table component does require bean type to define but ‘’’Grid grid=new Grid<>();’’’ does. It dint work when you don’t know the column names beforehand.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment