You are viewing a plain text version of this content. The canonical link for it is here.
Posted to jmeter-dev@jakarta.apache.org by se...@apache.org on 2004/01/23 02:14:11 UTC
cvs commit: jakarta-jmeter/src/functions/org/apache/jmeter/functions FileWrapper.java FileRowColContainer.java
sebb 2004/01/22 17:14:11
Added: src/functions/org/apache/jmeter/functions FileWrapper.java
FileRowColContainer.java
Log:
Support classes for multi-file CSVRead
Revision Changes Path
1.1 jakarta-jmeter/src/functions/org/apache/jmeter/functions/FileWrapper.java
Index: FileWrapper.java
===================================================================
/*
* ====================================================================
* The Apache Software License, Version 1.1
*
* Copyright (c) 2004 The Apache Software Foundation. All rights
* reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in
* the documentation and/or other materials provided with the
* distribution.
*
* 3. The end-user documentation included with the redistribution,
* if any, must include the following acknowledgment:
* "This product includes software developed by the
* Apache Software Foundation (http://www.apache.org/)."
* Alternately, this acknowledgment may appear in the software itself,
* if and wherever such third-party acknowledgments normally appear.
*
* 4. The names "Apache" and "Apache Software Foundation" and
* "Apache JMeter" must not be used to endorse or promote products
* derived from this software without prior written permission. For
* written permission, please contact apache@apache.org.
*
* 5. Products derived from this software may not be called "Apache",
* "Apache JMeter", nor may "Apache" appear in their name, without
* prior written permission of the Apache Software Foundation.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
* ====================================================================
*
* This software consists of voluntary contributions made by many
* individuals on behalf of the Apache Software Foundation. For more
* information on the Apache Software Foundation, please see
* <http://www.apache.org/>.
*/
package org.apache.jmeter.functions;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import org.apache.jorphan.logging.LoggingManager;
import org.apache.log.Logger;
/**
* This class wraps the FileRowColContainer for use across multiple
* threads.
*
* It does this by maintaining a list of open files, keyed by file name
* (or alias, if used).
* A list of open files is also maintained for each thread, together with
* the current line number.
*
* @author sebb AT apache DOT org
* @version $Revision: 1.1 $ $Date: 2004/01/23 01:14:11 $
*/
public class FileWrapper
{
transient private static Logger log = LoggingManager.getLoggerForClass();
private FileRowColContainer container;
private int currentRow;
private static final int NO_LINE = -1;
private static Map fileContainers = new HashMap(); // Map file names to containers
/*
* Only needed locally
*/
private FileWrapper(FileRowColContainer fdc)
{
super();
container = fdc;
currentRow = -1;
}
/* The cache of file packs */
private static ThreadLocal filePacks = new ThreadLocal(){
protected Object initialValue(){
return new HashMap();
}
};
/*
* called by (file,alias)
*/
public static void open(String file, String alias)
{
log.info("Opening "+file+ " as " + alias);
Map m = (Map) filePacks.get();
if (m.get(alias) == null)
{
FileRowColContainer frcc;
try
{
frcc = getFile(file, alias);
log.info("Stored "+file+" as "+alias);
m.put(alias,new FileWrapper(frcc));
}
catch (FileNotFoundException e)
{
//Already logged
}
catch (IOException e)
{
//Already logged
}
}
}
private static FileRowColContainer getFile(String file, String alias)
throws FileNotFoundException, IOException
{
FileRowColContainer frcc;
if ((frcc = (FileRowColContainer) fileContainers.get(alias)) == null)
{
frcc = new FileRowColContainer(file);
log.info("Opened "+file+" as "+alias);
fileContainers.put(alias,frcc);
}
return frcc;
}
/*
* Called by CSVRead(x,next) - sets the row to nil so the next
* row will be picked up the next time round
*
*/
public static void endRow(String file)
{
Map my = (Map) filePacks.get();
FileWrapper fw = (FileWrapper) (my).get(file);
if (fw == null)
{
log.warn("endRow(): no entry for "+file);
}
else
{
fw.endRow();
}
}
private void endRow()
{
if (currentRow == NO_LINE)
{
log.warn("endRow() called twice in succession");
}
currentRow = NO_LINE;
}
public static String getColumn(String file,int col)
{
Map my = (Map) filePacks.get();
FileWrapper fw = (FileWrapper) (my).get(file);
if (fw == null) // First call
{
log.info("Attaching "+file);
open(file,file);
fw = (FileWrapper) my.get(file);
//TODO improve the error handling
if (fw == null) return "";
}
return fw.getColumn(col);
}
private String getColumn(int col)
{
if (currentRow == NO_LINE)
{
currentRow = container.nextRow();
}
return container.getColumn(currentRow,col);
}
/**
*
*/
public static void clearAll()
{
log.debug("clearAll()");
Map my = (Map) filePacks.get();
for (Iterator i=my.entrySet().iterator();i.hasNext();)
{
Object fw = i.next();
log.info("Removing "+fw.toString());
i.remove();
}
fileContainers.clear();
}
}
1.1 jakarta-jmeter/src/functions/org/apache/jmeter/functions/FileRowColContainer.java
Index: FileRowColContainer.java
===================================================================
/*
* ====================================================================
* The Apache Software License, Version 1.1
*
* Copyright (c) 2001,2004 The Apache Software Foundation. All rights
* reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in
* the documentation and/or other materials provided with the
* distribution.
*
* 3. The end-user documentation included with the redistribution,
* if any, must include the following acknowledgment:
* "This product includes software developed by the
* Apache Software Foundation (http://www.apache.org/)."
* Alternately, this acknowledgment may appear in the software itself,
* if and wherever such third-party acknowledgments normally appear.
*
* 4. The names "Apache" and "Apache Software Foundation" and
* "Apache JMeter" must not be used to endorse or promote products
* derived from this software without prior written permission. For
* written permission, please contact apache@apache.org.
*
* 5. Products derived from this software may not be called "Apache",
* "Apache JMeter", nor may "Apache" appear in their name, without
* prior written permission of the Apache Software Foundation.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
* ====================================================================
*
* This software consists of voluntary contributions made by many
* individuals on behalf of the Apache Software Foundation. For more
* information on the Apache Software Foundation, please see
* <http://www.apache.org/>.
*/
package org.apache.jmeter.functions;
import java.io.BufferedReader;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.StringTokenizer;
import org.apache.jmeter.junit.JMeterTestCase;
import org.apache.jorphan.logging.LoggingManager;
import org.apache.log.Logger;
/**
* File data container for CSV (and similar delimited) files
* Data is accessible via row and column number
*
* @author sebb AT apache DOT org (multiple file version)
* @version $Revision: 1.1 $
*/
public class FileRowColContainer
{
transient private static Logger log = LoggingManager.getLoggerForClass();
private ArrayList fileData; // Lines in the file, split into columns
private String fileName; // name of the file
public static final String DELIMITER = ","; // Default delimiter
/** Keeping track of which row is next to be read. */
private int nextRow;
/** Delimiter for this file */
private String delimiter;
private FileRowColContainer()// Not intended to be called directly
{
}
public FileRowColContainer(String file,String delim)
throws IOException,FileNotFoundException
{
log.debug("FDC("+file+","+delim+")");
fileName = file;
delimiter = delim;
nextRow = 0;
load();
}
public FileRowColContainer(String file)
throws IOException,FileNotFoundException
{
log.debug("FDC("+file+")");
fileName = file;
delimiter = DELIMITER;
nextRow = 0;
load();
}
private void load()
throws IOException,FileNotFoundException
{
fileData = new ArrayList();
BufferedReader myBread=null;
try
{
FileReader fis = new FileReader(fileName);
myBread = new BufferedReader(fis);
String line = myBread.readLine();
while (line != null)
{
fileData.add(splitLine(line,delimiter));
line = myBread.readLine();
}
}
catch (FileNotFoundException e)
{
fileData = null;
log.warn(e.toString());
throw e;
}
catch (IOException e)
{
fileData = null;
log.warn(e.toString());
myBread.close();
throw e;
}
}
/**
* Get the string for the column from the current row
*
* @param row row number (from 0)
* @param col column number (from 0)
* @return the string (empty if out of bounds)
* @throws IndexOutOfBoundsException if the column number is out of bounds
*/
public String getColumn(int row,int col) throws IndexOutOfBoundsException
{
String colData;
colData = (String) ((ArrayList) fileData.get(row)).get(col);
log.debug(fileName+"("+row+","+col+"): "+colData);
return colData;
}
/**
* Returns the next row to the caller, and updates it,
* allowing for wrap round
*
* @return the first free (unread) row
*
*/
public int nextRow()
{
int row = nextRow;
nextRow++;
if (nextRow >= fileData.size())// 0-based
{
nextRow = 0;
}
log.debug ("Row: "+ row);
return row;
}
/**
* Splits the line according to the specified delimiter
*
* @return an ArrayList of Strings containing one element for each
* value in the line
*/
private static ArrayList splitLine(String theLine,String delim)
{
ArrayList result = new ArrayList();
StringTokenizer tokener = new StringTokenizer(theLine,delim);
while(tokener.hasMoreTokens())
{
String token = tokener.nextToken();
result.add(token);
}
return result;
}
public static class Test extends JMeterTestCase
{
static{
// LoggingManager.setPriority("DEBUG","jmeter");
// LoggingManager.setTarget(new PrintWriter(System.out));
}
public Test(String a)
{
super(a);
}
public void testNull() throws Exception
{
try
{
FileRowColContainer f = new FileRowColContainer("testfiles/xyzxyz");
fail("Should not find the file");
}
catch (FileNotFoundException e)
{
}
}
public void testrowNum() throws Exception
{
FileRowColContainer f = new FileRowColContainer("testfiles/test.csv");
assertNotNull(f);
assertEquals("Expected 4 lines",4,f.fileData.size());
int myRow=f.nextRow();
assertEquals(0,myRow);
assertEquals(1,f.nextRow);
myRow = f.nextRow();
assertEquals(1,myRow);
assertEquals(2,f.nextRow);
myRow = f.nextRow();
assertEquals(2,myRow);
assertEquals(3,f.nextRow);
myRow = f.nextRow();
assertEquals(3,myRow);
assertEquals(0,f.nextRow);
myRow = f.nextRow();
assertEquals(0,myRow);
assertEquals(1,f.nextRow);
}
public void testColumns() throws Exception
{
FileRowColContainer f = new FileRowColContainer("testfiles/test.csv");
assertNotNull(f);
assertTrue("Not empty",f.fileData.size() > 0);
int myRow=f.nextRow();
assertEquals(0,myRow);
assertEquals("a1",f.getColumn(myRow,0));
assertEquals("d1",f.getColumn(myRow,3));
try {
f.getColumn(myRow,4);
fail("Expected out of bounds");
}
catch (IndexOutOfBoundsException e)
{
}
myRow=f.nextRow();
assertEquals(1,myRow);
assertEquals("b2",f.getColumn(myRow,1));
assertEquals("c2",f.getColumn(myRow,2));
}
}
/**
* @return the file name for this class
*/
public String getFileName()
{
return fileName;
}
}
---------------------------------------------------------------------
To unsubscribe, e-mail: jmeter-dev-unsubscribe@jakarta.apache.org
For additional commands, e-mail: jmeter-dev-help@jakarta.apache.org