Testcases for new classes from Avalon excalibur.
git-svn-id: https://svn.apache.org/repos/asf/jakarta/commons/proper/io/trunk@140305 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/src/test/org/apache/commons/io/DemuxTestCase.java b/src/test/org/apache/commons/io/DemuxTestCase.java
new file mode 100644
index 0000000..ffdec57
--- /dev/null
+++ b/src/test/org/apache/commons/io/DemuxTestCase.java
@@ -0,0 +1,286 @@
+/*
+ * $Header: /home/jerenkrantz/tmp/commons/commons-convert/cvs/home/cvs/jakarta-commons//io/src/test/org/apache/commons/io/DemuxTestCase.java,v 1.1 2002/07/08 22:19:10 nicolaken Exp $
+ * $Revision: 1.1 $
+ * $Date: 2002/07/08 22:19:10 $
+ *
+ * ====================================================================
+ *
+ * The Apache Software License, Version 1.1
+ *
+ * Copyright (c) 1999-2002 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 acknowlegement:
+ * "This product includes software developed by the
+ * Apache Software Foundation (http://www.apache.org/)."
+ * Alternately, this acknowlegement may appear in the software itself,
+ * if and wherever such third-party acknowlegements normally appear.
+ *
+ * 4. The names "The Jakarta Project", "Commons", and "Apache Software
+ * Foundation" 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"
+ * nor may "Apache" appear in their names without prior written
+ * permission of the Apache Group.
+ *
+ * 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.commons.io;
+
+import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.Random;
+import junit.framework.TestCase;
+import org.apache.avalon.excalibur.io.DemuxInputStream;
+import org.apache.avalon.excalibur.io.DemuxOutputStream;
+
+/**
+ * Basic unit tests for the multiplexing streams.
+ *
+ * @author <a href="mailto:peter@apache.org">Peter Donald</a>
+ */
+public final class DemuxTestCase
+ extends TestCase
+{
+ private static final String T1 = "Thread1";
+ private static final String T2 = "Thread2";
+ private static final String T3 = "Thread3";
+ private static final String T4 = "Thread4";
+
+ private static final String DATA1 = "Data for thread1";
+ private static final String DATA2 = "Data for thread2";
+ private static final String DATA3 = "Data for thread3";
+ private static final String DATA4 = "Data for thread4";
+
+ private static final Random c_random = new Random();
+ private final HashMap m_outputMap = new HashMap();
+ private final HashMap m_threadMap = new HashMap();
+
+ public DemuxTestCase( final String name )
+ {
+ super( name );
+ }
+
+ private String getOutput( final String threadName )
+ throws IOException
+ {
+ final ByteArrayOutputStream output =
+ (ByteArrayOutputStream)m_outputMap.get( threadName );
+ assertNotNull( "getOutput()", output );
+
+ return output.toString();
+ }
+
+ private String getInput( final String threadName )
+ throws IOException
+ {
+ final ReaderThread thread = (ReaderThread)m_threadMap.get( threadName );
+ assertNotNull( "getInput()", thread );
+
+ return thread.getData();
+ }
+
+ private void doStart()
+ throws Exception
+ {
+ final Iterator iterator = m_threadMap.keySet().iterator();
+ while( iterator.hasNext() )
+ {
+ final String name = (String)iterator.next();
+ final Thread thread = (Thread)m_threadMap.get( name );
+ thread.start();
+ }
+ }
+
+ private void doJoin()
+ throws Exception
+ {
+ final Iterator iterator = m_threadMap.keySet().iterator();
+ while( iterator.hasNext() )
+ {
+ final String name = (String)iterator.next();
+ final Thread thread = (Thread)m_threadMap.get( name );
+ thread.join();
+ }
+ }
+
+ private void startWriter( final String name,
+ final String data,
+ final DemuxOutputStream demux )
+ throws Exception
+ {
+ final ByteArrayOutputStream output = new ByteArrayOutputStream();
+ m_outputMap.put( name, output );
+ final WriterThread thread =
+ new WriterThread( name, data, output, demux );
+ m_threadMap.put( name, thread );
+ }
+
+ private void startReader( final String name,
+ final String data,
+ final DemuxInputStream demux )
+ throws Exception
+ {
+ final ByteArrayInputStream input = new ByteArrayInputStream( data.getBytes() );
+ final ReaderThread thread = new ReaderThread( name, input, demux );
+ m_threadMap.put( name, thread );
+ }
+
+ public void testOutputStream()
+ throws Exception
+ {
+ final DemuxOutputStream output = new DemuxOutputStream();
+ startWriter( T1, DATA1, output );
+ startWriter( T2, DATA2, output );
+ startWriter( T3, DATA3, output );
+ startWriter( T4, DATA4, output );
+
+ doStart();
+ doJoin();
+
+ assertEquals( "Data1", DATA1, getOutput( T1 ) );
+ assertEquals( "Data2", DATA2, getOutput( T2 ) );
+ assertEquals( "Data3", DATA3, getOutput( T3 ) );
+ assertEquals( "Data4", DATA4, getOutput( T4 ) );
+ }
+
+ public void testInputStream()
+ throws Exception
+ {
+ final DemuxInputStream input = new DemuxInputStream();
+ startReader( T1, DATA1, input );
+ startReader( T2, DATA2, input );
+ startReader( T3, DATA3, input );
+ startReader( T4, DATA4, input );
+
+ doStart();
+ doJoin();
+
+ assertEquals( "Data1", DATA1, getInput( T1 ) );
+ assertEquals( "Data2", DATA2, getInput( T2 ) );
+ assertEquals( "Data3", DATA3, getInput( T3 ) );
+ assertEquals( "Data4", DATA4, getInput( T4 ) );
+ }
+
+ private static class ReaderThread
+ extends Thread
+ {
+ private final StringBuffer m_buffer = new StringBuffer();
+ private final InputStream m_input;
+ private final DemuxInputStream m_demux;
+
+ ReaderThread( final String name,
+ final InputStream input,
+ final DemuxInputStream demux )
+ {
+ super( name );
+ m_input = input;
+ m_demux = demux;
+ }
+
+ public String getData()
+ {
+ return m_buffer.toString();
+ }
+
+ public void run()
+ {
+ m_demux.bindStream( m_input );
+
+ try
+ {
+ int ch = m_demux.read();
+ while( -1 != ch )
+ {
+ //System.out.println( "Reading: " + (char)ch );
+ m_buffer.append( (char)ch );
+
+ final int sleepTime = Math.abs( c_random.nextInt() % 10 );
+ Thread.sleep( sleepTime );
+ ch = m_demux.read();
+ }
+ }
+ catch( final Exception e )
+ {
+ e.printStackTrace();
+ }
+ }
+ }
+
+ private static class WriterThread
+ extends Thread
+ {
+ private final byte[] m_data;
+ private final OutputStream m_output;
+ private final DemuxOutputStream m_demux;
+
+ WriterThread( final String name,
+ final String data,
+ final OutputStream output,
+ final DemuxOutputStream demux )
+ {
+ super( name );
+ m_output = output;
+ m_demux = demux;
+ m_data = data.getBytes();
+ }
+
+ public void run()
+ {
+ m_demux.bindStream( m_output );
+ for( int i = 0; i < m_data.length; i++ )
+ {
+ try
+ {
+ //System.out.println( "Writing: " + (char)m_data[ i ] );
+ m_demux.write( m_data[ i ] );
+ final int sleepTime = Math.abs( c_random.nextInt() % 10 );
+ Thread.sleep( sleepTime );
+ }
+ catch( final Exception e )
+ {
+ e.printStackTrace();
+ }
+ }
+ }
+ }
+}
diff --git a/src/test/org/apache/commons/io/FileUtilTestCase.java b/src/test/org/apache/commons/io/FileUtilTestCase.java
new file mode 100644
index 0000000..273f6ab
--- /dev/null
+++ b/src/test/org/apache/commons/io/FileUtilTestCase.java
@@ -0,0 +1,243 @@
+/*
+ * $Header: /home/jerenkrantz/tmp/commons/commons-convert/cvs/home/cvs/jakarta-commons//io/src/test/org/apache/commons/io/Attic/FileUtilTestCase.java,v 1.1 2002/07/08 22:19:10 nicolaken Exp $
+ * $Revision: 1.1 $
+ * $Date: 2002/07/08 22:19:10 $
+ *
+ * ====================================================================
+ *
+ * The Apache Software License, Version 1.1
+ *
+ * Copyright (c) 1999-2002 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 acknowlegement:
+ * "This product includes software developed by the
+ * Apache Software Foundation (http://www.apache.org/)."
+ * Alternately, this acknowlegement may appear in the software itself,
+ * if and wherever such third-party acknowlegements normally appear.
+ *
+ * 4. The names "The Jakarta Project", "Commons", and "Apache Software
+ * Foundation" 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"
+ * nor may "Apache" appear in their names without prior written
+ * permission of the Apache Group.
+ *
+ * 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.commons.io;
+
+import java.io.BufferedOutputStream;
+import java.io.File;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import junit.framework.Test;
+import junit.framework.TestCase;
+import junit.framework.TestSuite;
+import org.apache.avalon.excalibur.io.FileUtil;
+
+/**
+ * This is used to test FileUtil for correctness.
+ *
+ * @author <a href="mailto:peter@apache.org">Peter Donald</a>
+ */
+public final class FileUtilTestCase
+ extends TestCase
+{
+ private final int FILE1_SIZE = 1;
+ private final int FILE2_SIZE = 1024 * 4 + 1;
+
+ private final File m_testDirectory;
+ private final File m_testFile1;
+ private final File m_testFile2;
+
+ public FileUtilTestCase( final String name )
+ throws IOException
+ {
+ super( name );
+
+ m_testDirectory = ( new File( "test/io/" ) ).getAbsoluteFile();
+ if( !m_testDirectory.exists() )
+ {
+ m_testDirectory.mkdirs();
+ }
+
+ m_testFile1 = new File( m_testDirectory, "file1-test.txt" );
+ m_testFile2 = new File( m_testDirectory, "file2-test.txt" );
+
+ createFile( m_testFile1, FILE1_SIZE );
+ createFile( m_testFile2, FILE2_SIZE );
+ }
+
+ private void createFile( final File file, final long size )
+ throws IOException
+ {
+ final BufferedOutputStream output =
+ new BufferedOutputStream( new FileOutputStream( file ) );
+
+ for( int i = 0; i < size; i++ )
+ {
+ output.write( (byte)'X' );
+ }
+
+ output.close();
+ }
+
+ public static Test suite()
+ throws IOException
+ {
+ final TestSuite suite = new TestSuite();
+ suite.addTest( new FileUtilTestCase( "testCopyFile1" ) );
+ suite.addTest( new FileUtilTestCase( "testCopyFile2" ) );
+ suite.addTest( new FileUtilTestCase( "testForceDeleteAFile1" ) );
+ suite.addTest( new FileUtilTestCase( "testForceDeleteAFile2" ) );
+ suite.addTest( new FileUtilTestCase( "testCopyFile1ToDir" ) );
+ suite.addTest( new FileUtilTestCase( "testCopyFile2ToDir" ) );
+ suite.addTest( new FileUtilTestCase( "testForceDeleteDir" ) );
+ suite.addTest( new FileUtilTestCase( "testResolveFileDotDot" ) );
+ suite.addTest( new FileUtilTestCase( "testResolveFileDot" ) );
+ suite.addTest( new FileUtilTestCase( "testNormalize" ) );
+ return suite;
+ }
+
+ public void testCopyFile1()
+ throws Exception
+ {
+ final File destination = new File( m_testDirectory, "copy1.txt" );
+ FileUtil.copyFile( m_testFile1, destination );
+ assertTrue( "Check Exist", destination.exists() );
+ assertTrue( "Check Full copy", destination.length() == FILE1_SIZE );
+ }
+
+ public void testCopyFile2()
+ throws Exception
+ {
+ final File destination = new File( m_testDirectory, "copy2.txt" );
+ FileUtil.copyFile( m_testFile2, destination );
+ assertTrue( "Check Exist", destination.exists() );
+ assertTrue( "Check Full copy", destination.length() == FILE2_SIZE );
+ }
+
+ public void testForceDeleteAFile1()
+ throws Exception
+ {
+ final File destination = new File( m_testDirectory, "copy1.txt" );
+ destination.createNewFile();
+ assertTrue( "Copy1.txt doesn't exist to delete", destination.exists() );
+ FileUtil.forceDelete( destination );
+ assertTrue( "Check No Exist", !destination.exists() );
+ }
+
+ public void testForceDeleteAFile2()
+ throws Exception
+ {
+ final File destination = new File( m_testDirectory, "copy2.txt" );
+ destination.createNewFile();
+ assertTrue( "Copy2.txt doesn't exist to delete", destination.exists() );
+ FileUtil.forceDelete( destination );
+ assertTrue( "Check No Exist", !destination.exists() );
+ }
+
+ public void testCopyFile1ToDir()
+ throws Exception
+ {
+ final File directory = new File( m_testDirectory, "subdir" );
+ if( !directory.exists() ) directory.mkdirs();
+ final File destination = new File( directory, "file1-test.txt" );
+ FileUtil.copyFileToDirectory( m_testFile1, directory );
+ assertTrue( "Check Exist", destination.exists() );
+ assertTrue( "Check Full copy", destination.length() == FILE1_SIZE );
+ }
+
+ public void testCopyFile2ToDir()
+ throws Exception
+ {
+ final File directory = new File( m_testDirectory, "subdir" );
+ if( !directory.exists() ) directory.mkdirs();
+ final File destination = new File( directory, "file2-test.txt" );
+ FileUtil.copyFileToDirectory( m_testFile2, directory );
+ assertTrue( "Check Exist", destination.exists() );
+ assertTrue( "Check Full copy", destination.length() == FILE2_SIZE );
+ }
+
+ public void testForceDeleteDir()
+ throws Exception
+ {
+ FileUtil.forceDelete( m_testDirectory.getParentFile() );
+ assertTrue( "Check No Exist", !m_testDirectory.getParentFile().exists() );
+ }
+
+ public void testResolveFileDotDot()
+ throws Exception
+ {
+ final File file = FileUtil.resolveFile( m_testDirectory, ".." );
+ assertEquals( "Check .. operator", file, m_testDirectory.getParentFile() );
+ }
+
+ public void testResolveFileDot()
+ throws Exception
+ {
+ final File file = FileUtil.resolveFile( m_testDirectory, "." );
+ assertEquals( "Check . operator", file, m_testDirectory );
+ }
+
+ public void testNormalize()
+ throws Exception
+ {
+ final String[] src =
+ {
+ "", "/", "///", "/foo", "/foo//", "/./", "/foo/./", "/foo/./bar",
+ "/foo/../bar", "/foo/../bar/../baz", "/foo/bar/../../baz", "/././",
+ "/foo/./../bar", "/foo/.././bar/", "//foo//./bar", "/../",
+ "/foo/../../"
+ };
+
+ final String[] dest =
+ {
+ "", "/", "/", "/foo", "/foo/", "/", "/foo/", "/foo/bar", "/bar",
+ "/baz", "/baz", "/", "/bar", "/bar/", "/foo/bar", null, null
+ };
+
+ assertEquals( "Oops, test writer goofed", src.length, dest.length );
+
+ for( int i = 0; i < src.length; i++ )
+ {
+ assertEquals( "Check if '" + src[ i ] + "' normalized to '" + dest[ i ] + "'",
+ dest[ i ], FileUtil.normalize( src[ i ] ) );
+ }
+ }
+}
diff --git a/src/test/org/apache/commons/io/IOTestSuite.java b/src/test/org/apache/commons/io/IOTestSuite.java
new file mode 100644
index 0000000..1d1b6e1
--- /dev/null
+++ b/src/test/org/apache/commons/io/IOTestSuite.java
@@ -0,0 +1,79 @@
+/*
+ * $Header: /home/jerenkrantz/tmp/commons/commons-convert/cvs/home/cvs/jakarta-commons//io/src/test/org/apache/commons/io/Attic/IOTestSuite.java,v 1.1 2002/07/08 22:19:10 nicolaken Exp $
+ * $Revision: 1.1 $
+ * $Date: 2002/07/08 22:19:10 $
+ *
+ * ====================================================================
+ *
+ * The Apache Software License, Version 1.1
+ *
+ * Copyright (c) 1999-2002 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 acknowlegement:
+ * "This product includes software developed by the
+ * Apache Software Foundation (http://www.apache.org/)."
+ * Alternately, this acknowlegement may appear in the software itself,
+ * if and wherever such third-party acknowlegements normally appear.
+ *
+ * 4. The names "The Jakarta Project", "Commons", and "Apache Software
+ * Foundation" 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"
+ * nor may "Apache" appear in their names without prior written
+ * permission of the Apache Group.
+ *
+ * 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.commons.io;
+
+import junit.framework.Test;
+import junit.framework.TestSuite;
+
+/**
+ * A basic test suite that tests all the IO package.
+ */
+public class IOTestSuite
+{
+ public static Test suite()
+ {
+ final TestSuite suite = new TestSuite( "IO Utilities" );
+ suite.addTest( new TestSuite( FileUtilTestCase.class ) );
+ suite.addTest( new TestSuite( IOUtilTestCase.class ) );
+ return suite;
+ }
+}
diff --git a/src/test/org/apache/commons/io/IOUtilTestCase.java b/src/test/org/apache/commons/io/IOUtilTestCase.java
new file mode 100644
index 0000000..8be1bc8
--- /dev/null
+++ b/src/test/org/apache/commons/io/IOUtilTestCase.java
@@ -0,0 +1,484 @@
+/*
+ * $Header: /home/jerenkrantz/tmp/commons/commons-convert/cvs/home/cvs/jakarta-commons//io/src/test/org/apache/commons/io/Attic/IOUtilTestCase.java,v 1.1 2002/07/08 22:19:10 nicolaken Exp $
+ * $Revision: 1.1 $
+ * $Date: 2002/07/08 22:19:10 $
+ *
+ * ====================================================================
+ *
+ * The Apache Software License, Version 1.1
+ *
+ * Copyright (c) 1999-2002 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 acknowlegement:
+ * "This product includes software developed by the
+ * Apache Software Foundation (http://www.apache.org/)."
+ * Alternately, this acknowlegement may appear in the software itself,
+ * if and wherever such third-party acknowlegements normally appear.
+ *
+ * 4. The names "The Jakarta Project", "Commons", and "Apache Software
+ * Foundation" 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"
+ * nor may "Apache" appear in their names without prior written
+ * permission of the Apache Group.
+ *
+ * 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.commons.io;
+
+import java.io.BufferedOutputStream;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileOutputStream;
+import java.io.FileReader;
+import java.io.FileWriter;
+import java.io.IOException;
+import java.io.OutputStream;
+import java.io.PrintStream;
+import java.io.PrintWriter;
+import java.io.Writer;
+import java.util.Arrays;
+import junit.framework.AssertionFailedError;
+import junit.framework.TestCase;
+import org.apache.avalon.excalibur.io.FileUtil;
+import org.apache.avalon.excalibur.io.IOUtil;
+
+// Note: jdk1.2 dependency
+
+/**
+ * This is used to test IOUtil for correctness. The following checks are performed:
+ * <ul>
+ * <li>The return must not be null, must be the same type and equals() to the method's second arg</li>
+ * <li>All bytes must have been read from the source (available() == 0)</li>
+ * <li>The source and destination content must be identical (byte-wise comparison check)</li>
+ * <li>The output stream must not have been closed (a byte/char is written to test this, and
+ * subsequent size checked)</li>
+ * </ul>
+ * Due to interdependencies in IOUtils and IOUtilsTestlet, one bug may cause
+ * multiple tests to fail.
+ *
+ * @author <a href="mailto:jefft@apache.org">Jeff Turner</a>
+ */
+public final class IOUtilTestCase
+ extends TestCase
+{
+ /*
+ * Note: this is not particularly beautiful code. A better way to check for
+ * flush and close status would be to implement "trojan horse" wrapper
+ * implementations of the various stream classes, which set a flag when
+ * relevant methods are called. (JT)
+ */
+
+ private final int FILE_SIZE = 1024 * 4 + 1;
+
+ private File m_testDirectory;
+ private File m_testFile;
+
+ public void setUp()
+ {
+ try
+ {
+ m_testDirectory = ( new File( "test/io/" ) ).getAbsoluteFile();
+ if( !m_testDirectory.exists() )
+ {
+ m_testDirectory.mkdirs();
+ }
+
+ m_testFile = new File( m_testDirectory, "file2-test.txt" );
+
+ createFile( m_testFile, FILE_SIZE );
+ }
+ catch( IOException ioe )
+ {
+ throw new RuntimeException( "Can't run this test because environment could not be built" );
+ }
+ }
+
+ public void tearDown()
+ {
+ try
+ {
+ FileUtil.deleteDirectory( "test" );
+ }
+ catch( IOException ioe )
+ {
+ // Ignore, because by this time, it is too late.
+ }
+ }
+
+ public IOUtilTestCase( String name )
+ {
+ super( name );
+ }
+
+ private void createFile( final File file, final long size )
+ throws IOException
+ {
+ final BufferedOutputStream output =
+ new BufferedOutputStream( new FileOutputStream( file ) );
+
+ for( int i = 0; i < size; i++ )
+ {
+ output.write( (byte)( i % 128 ) ); // nice varied byte pattern compatible with Readers and Writers
+ }
+
+ output.close();
+ }
+
+ /** Assert that the contents of two byte arrays are the same. */
+ private void assertEqualContent( final byte[] b0, final byte[] b1 )
+ throws IOException
+ {
+ assertTrue( "Content not equal according to java.util.Arrays#equals()", Arrays.equals( b0, b1 ) );
+ }
+
+ /** Assert that the content of two files is the same. */
+ private void assertEqualContent( final File f0, final File f1 )
+ throws IOException
+ {
+ final FileInputStream is0 = new FileInputStream( f0 );
+ final FileInputStream is1 = new FileInputStream( f1 );
+ final byte[] buf0 = new byte[ FILE_SIZE ];
+ final byte[] buf1 = new byte[ FILE_SIZE ];
+ int n0 = 0;
+ int n1 = 0;
+
+ while( -1 != n0 )
+ {
+ n0 = is0.read( buf0 );
+ n1 = is1.read( buf1 );
+ assertTrue( "The files " + f0 + " and " + f1 +
+ " have differing number of bytes available (" + n0 +
+ " vs " + n1 + ")", ( n0 == n1 ) );
+
+ assertTrue( "The files " + f0 + " and " + f1 +
+ " have different content", Arrays.equals( buf0, buf1 ) );
+ }
+ }
+
+ /** Assert that the content of a file is equal to that in a byte[]. */
+ private void assertEqualContent( final byte[] b0, final File file )
+ throws IOException
+ {
+ final FileInputStream is = new FileInputStream( file );
+ byte[] b1 = new byte[ b0.length ];
+ int numRead = is.read( b1 );
+ assertTrue( "Different number of bytes", numRead == b0.length && is.available() == 0 );
+ for( int i = 0;
+ i < numRead;
+ assertTrue( "Byte " + i + " differs (" + b0[ i ] + " != " + b1[ i ] + ")", b0[ i ] == b1[ i ] ), i++
+ )
+ ;
+ }
+
+ public void testInputStreamToOutputStream()
+ throws Exception
+ {
+ final File destination = newFile( "copy1.txt" );
+ final FileInputStream fin = new FileInputStream( m_testFile );
+ final FileOutputStream fout = new FileOutputStream( destination );
+
+ IOUtil.copy( fin, fout );
+ assertTrue( "Not all bytes were read", fin.available() == 0 );
+ fout.flush();
+
+ checkFile( destination );
+ checkWrite( fout );
+ fout.close();
+ fin.close();
+ deleteFile( destination );
+ }
+
+ public void testInputStreamToWriter()
+ throws Exception
+ {
+ final File destination = newFile( "copy2.txt" );
+ final FileInputStream fin = new FileInputStream( m_testFile );
+ final FileWriter fout = new FileWriter( destination );
+
+ IOUtil.copy( fin, fout );
+
+ assertTrue( "Not all bytes were read", fin.available() == 0 );
+ fout.flush();
+
+ checkFile( destination );
+ checkWrite( fout );
+ fout.close();
+ fin.close();
+ deleteFile( destination );
+ }
+
+ public void testInputStreamToString()
+ throws Exception
+ {
+ final FileInputStream fin = new FileInputStream( m_testFile );
+ final String out = IOUtil.toString( fin );
+ assertNotNull( out );
+ assertTrue( "Not all bytes were read", fin.available() == 0 );
+ assertTrue( "Wrong output size: out.length()=" + out.length() +
+ "!=" + FILE_SIZE, out.length() == FILE_SIZE );
+ fin.close();
+ }
+
+ public void testReaderToOutputStream()
+ throws Exception
+ {
+ final File destination = newFile( "copy3.txt" );
+ final FileReader fin = new FileReader( m_testFile );
+ final FileOutputStream fout = new FileOutputStream( destination );
+ IOUtil.copy( fin, fout );
+ //Note: this method *does* flush. It is equivalent to:
+ // final OutputStreamWriter _out = new OutputStreamWriter(fout);
+ // IOUtil.copy( fin, _out, 4096 ); // copy( Reader, Writer, int );
+ // _out.flush();
+ // out = fout;
+
+ // Note: rely on the method to flush
+ checkFile( destination );
+ checkWrite( fout );
+ fout.close();
+ fin.close();
+ deleteFile( destination );
+ }
+
+ public void testReaderToWriter()
+ throws Exception
+ {
+ final File destination = newFile( "copy4.txt" );
+ final FileReader fin = new FileReader( m_testFile );
+ final FileWriter fout = new FileWriter( destination );
+ IOUtil.copy( fin, fout );
+
+ fout.flush();
+ checkFile( destination );
+ checkWrite( fout );
+ fout.close();
+ fin.close();
+ deleteFile( destination );
+ }
+
+ public void testReaderToString()
+ throws Exception
+ {
+ final FileReader fin = new FileReader( m_testFile );
+ final String out = IOUtil.toString( fin );
+ assertNotNull( out );
+ assertTrue( "Wrong output size: out.length()=" +
+ out.length() + "!=" + FILE_SIZE,
+ out.length() == FILE_SIZE );
+ fin.close();
+ }
+
+ public void testStringToOutputStream()
+ throws Exception
+ {
+ final File destination = newFile( "copy5.txt" );
+ final FileReader fin = new FileReader( m_testFile );
+ // Create our String. Rely on testReaderToString() to make sure this is valid.
+ final String str = IOUtil.toString( fin );
+ final FileOutputStream fout = new FileOutputStream( destination );
+ IOUtil.copy( str, fout );
+ //Note: this method *does* flush. It is equivalent to:
+ // final OutputStreamWriter _out = new OutputStreamWriter(fout);
+ // IOUtil.copy( str, _out, 4096 ); // copy( Reader, Writer, int );
+ // _out.flush();
+ // out = fout;
+ // note: we don't flush here; this IOUtils method does it for us
+
+ checkFile( destination );
+ checkWrite( fout );
+ fout.close();
+ fin.close();
+ deleteFile( destination );
+ }
+
+ public void testStringToWriter()
+ throws Exception
+ {
+ final File destination = newFile( "copy6.txt" );
+ FileReader fin = new FileReader( m_testFile );
+ // Create our String. Rely on testReaderToString() to make sure this is valid.
+ final String str = IOUtil.toString( fin );
+ final FileWriter fout = new FileWriter( destination );
+ IOUtil.copy( str, fout );
+ fout.flush();
+
+ checkFile( destination );
+ checkWrite( fout );
+ fout.close();
+ fin.close();
+
+ deleteFile( destination );
+ }
+
+ public void testInputStreamToByteArray()
+ throws Exception
+ {
+ final FileInputStream fin = new FileInputStream( m_testFile );
+ final byte[] out = IOUtil.toByteArray( fin );
+ assertNotNull( out );
+ assertTrue( "Not all bytes were read", fin.available() == 0 );
+ assertTrue( "Wrong output size: out.length=" + out.length +
+ "!=" + FILE_SIZE, out.length == FILE_SIZE );
+ assertEqualContent( out, m_testFile );
+ fin.close();
+ }
+
+ public void testStringToByteArray()
+ throws Exception
+ {
+ final FileReader fin = new FileReader( m_testFile );
+
+ // Create our String. Rely on testReaderToString() to make sure this is valid.
+ final String str = IOUtil.toString( fin );
+
+ final byte[] out = IOUtil.toByteArray( str );
+ assertEqualContent( str.getBytes(), out );
+ fin.close();
+ }
+
+ public void testByteArrayToWriter()
+ throws Exception
+ {
+ final File destination = newFile( "copy7.txt" );
+ final FileWriter fout = new FileWriter( destination );
+ final FileInputStream fin = new FileInputStream( m_testFile );
+
+ // Create our byte[]. Rely on testInputStreamToByteArray() to make sure this is valid.
+ final byte[] in = IOUtil.toByteArray( fin );
+ IOUtil.copy( in, fout );
+ fout.flush();
+ checkFile( destination );
+ checkWrite( fout );
+ fout.close();
+ fin.close();
+ deleteFile( destination );
+ }
+
+ public void testByteArrayToString()
+ throws Exception
+ {
+ final FileInputStream fin = new FileInputStream( m_testFile );
+ final byte[] in = IOUtil.toByteArray( fin );
+ // Create our byte[]. Rely on testInputStreamToByteArray() to make sure this is valid.
+ String str = IOUtil.toString( in );
+ assertEqualContent( in, str.getBytes() );
+ fin.close();
+ }
+
+ public void testByteArrayToOutputStream()
+ throws Exception
+ {
+ final File destination = newFile( "copy8.txt" );
+ final FileOutputStream fout = new FileOutputStream( destination );
+ final FileInputStream fin = new FileInputStream( m_testFile );
+
+ // Create our byte[]. Rely on testInputStreamToByteArray() to make sure this is valid.
+ final byte[] in = IOUtil.toByteArray( fin );
+
+ IOUtil.copy( in, fout );
+
+ fout.flush();
+
+ checkFile( destination );
+ checkWrite( fout );
+ fout.close();
+ fin.close();
+ deleteFile( destination );
+ }
+
+
+ //////////////////////////////////////////////////////
+ // xxxxxxxxx
+
+
+ private File newFile( String filename )
+ throws Exception
+ {
+ final File destination = new File( m_testDirectory, filename );
+ assertTrue( filename + "Test output data file shouldn't previously exist",
+ !destination.exists() );
+
+ return destination;
+ }
+
+ private void checkFile( final File file )
+ throws Exception
+ {
+ assertTrue( "Check existence of output file", file.exists() );
+ assertEqualContent( m_testFile, file );
+ }
+
+ private void checkWrite( final OutputStream output )
+ throws Exception
+ {
+ try
+ {
+ new PrintStream( output ).write( 0 );
+ }
+ catch( final Throwable t )
+ {
+ throw new AssertionFailedError( "The copy() method closed the stream " +
+ "when it shouldn't have. " + t.getMessage() );
+ }
+ }
+
+ private void checkWrite( final Writer output )
+ throws Exception
+ {
+ try
+ {
+ new PrintWriter( output ).write( 'a' );
+ }
+ catch( final Throwable t )
+ {
+ throw new AssertionFailedError( "The copy() method closed the stream " +
+ "when it shouldn't have. " + t.getMessage() );
+ }
+ }
+
+ private void deleteFile( final File file )
+ throws Exception
+ {
+ assertTrue( "Wrong output size: file.length()=" +
+ file.length() + "!=" + FILE_SIZE + 1,
+ file.length() == FILE_SIZE + 1 );
+
+ //assertTrue( "File would not delete", (file.delete() || ( !file.exists() )));
+ }
+}
diff --git a/src/test/org/apache/commons/io/compress/bzip2/BzipTestCase.java b/src/test/org/apache/commons/io/compress/bzip2/BzipTestCase.java
new file mode 100644
index 0000000..ad4e4fa
--- /dev/null
+++ b/src/test/org/apache/commons/io/compress/bzip2/BzipTestCase.java
@@ -0,0 +1,230 @@
+/*
+ * Copyright (C) The Apache Software Foundation. All rights reserved.
+ *
+ * This software is published under the terms of the Apache Software License
+ * version 1.1, a copy of which has been included with this distribution in
+ * the LICENSE.txt file.
+ */
+package org.apache.excalibur.bzip2.test;
+
+import java.io.BufferedInputStream;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import junit.framework.TestCase;
+import org.apache.excalibur.bzip2.CBZip2InputStream;
+import org.apache.excalibur.bzip2.CBZip2OutputStream;
+
+/**
+ * A test the stress tested the BZip implementation to verify
+ * that it behaves correctly.
+ *
+ * @author <a href="mailto:peter@apache.org">Peter Donald</a>
+ * @version $Revision: 1.1 $ $Date: 2002/07/08 22:19:09 $
+ */
+public class BzipTestCase
+ extends TestCase
+{
+ private static final byte[] HEADER = new byte[]{(byte)'B', (byte)'Z'};
+
+ public BzipTestCase( final String name )
+ {
+ super( name );
+ }
+
+ public void testBzipOutputStream()
+ throws Exception
+ {
+ final InputStream input = getInputStream( "asf-logo-huge.tar" );
+ final File outputFile = getOutputFile( ".tar.bz2" );
+ final OutputStream output = new FileOutputStream( outputFile );
+ final CBZip2OutputStream packedOutput = getPackedOutput( output );
+ copy( input, packedOutput );
+ shutdownStream( input );
+ shutdownStream( packedOutput );
+ shutdownStream( output );
+ compareContents( "asf-logo-huge.tar.bz2", outputFile );
+ forceDelete( outputFile );
+ }
+
+ private void forceDelete( final File outputFile ) throws IOException
+ {
+ if( !outputFile.delete() )
+ {
+ final String message = "File " + outputFile + " unable to be deleted.";
+ throw new IOException( message );
+ }
+ }
+
+ public void testBzipInputStream()
+ throws Exception
+ {
+ final InputStream input = getInputStream( "asf-logo-huge.tar.bz2" );
+ final File outputFile = getOutputFile( ".tar" );
+ final OutputStream output = new FileOutputStream( outputFile );
+ final CBZip2InputStream packedInput = getPackedInput( input );
+ copy( packedInput, output );
+ shutdownStream( input );
+ shutdownStream( packedInput );
+ shutdownStream( output );
+ compareContents( "asf-logo-huge.tar", outputFile );
+ forceDelete( outputFile );
+ }
+
+ /**
+ * Copy bytes from an <code>InputStream</code> to an <code>OutputStream</code>.
+ */
+ private void copy( final InputStream input,
+ final OutputStream output )
+ throws IOException
+ {
+ final byte[] buffer = new byte[ 8024 ];
+ int n = 0;
+ while( -1 != ( n = input.read( buffer ) ) )
+ {
+ output.write( buffer, 0, n );
+ }
+ }
+
+ private void compareContents( final String initial, final File generated )
+ throws Exception
+ {
+ final InputStream input1 = getInputStream( initial );
+ final InputStream input2 = new FileInputStream( generated );
+ final boolean test = contentEquals( input1, input2 );
+ shutdownStream( input1 );
+ shutdownStream( input2 );
+ assertTrue( "Contents of " + initial + " matches generated version " + generated, test );
+ }
+
+ private CBZip2InputStream getPackedInput( final InputStream input )
+ throws IOException
+ {
+ final int b1 = input.read();
+ final int b2 = input.read();
+ assertEquals( "Equal header byte1", b1, 'B' );
+ assertEquals( "Equal header byte2", b2, 'Z' );
+ return new CBZip2InputStream( input );
+ }
+
+ private CBZip2OutputStream getPackedOutput( final OutputStream output )
+ throws IOException
+ {
+ output.write( HEADER );
+ return new CBZip2OutputStream( output );
+ }
+
+ private File getOutputFile( final String postfix )
+ throws IOException
+ {
+ final File cwd = new File( "." );
+ return File.createTempFile( "ant-test", postfix, cwd );
+ }
+
+ private InputStream getInputStream( final String resource )
+ throws Exception
+ {
+ final String filename = ".." + File.separator + ".." + File.separator +
+ "src" + File.separator + "test" + File.separator +
+ getClass().getName().replace( '.', File.separatorChar );
+ final String path = getPath( filename );
+ final File input = new File( path, resource );
+ return new FileInputStream( input );
+ //final ClassLoader loader = getClass().getClassLoader();
+ //return loader.getResourceAsStream( resource );
+ }
+
+ /**
+ * Compare the contents of two Streams to determine if they are equal or not.
+ *
+ * @param input1 the first stream
+ * @param input2 the second stream
+ * @return true if the content of the streams are equal or they both don't exist, false otherwise
+ */
+ private boolean contentEquals( final InputStream input1,
+ final InputStream input2 )
+ throws IOException
+ {
+ final InputStream bufferedInput1 = new BufferedInputStream( input1 );
+ final InputStream bufferedInput2 = new BufferedInputStream( input2 );
+
+ int ch = bufferedInput1.read();
+ while( -1 != ch )
+ {
+ final int ch2 = bufferedInput2.read();
+ if( ch != ch2 )
+ {
+ return false;
+ }
+ ch = bufferedInput1.read();
+ }
+
+ final int ch2 = bufferedInput2.read();
+ if( -1 != ch2 )
+ {
+ return false;
+ }
+ else
+ {
+ return true;
+ }
+ }
+
+ private String getPath( final String filepath )
+ {
+ final int index = filepath.lastIndexOf( File.separatorChar );
+ if( -1 == index )
+ {
+ return "";
+ }
+ else
+ {
+ return filepath.substring( 0, index );
+ }
+ }
+
+ /**
+ * Unconditionally close an <code>OutputStream</code>.
+ * Equivalent to {@link java.io.OutputStream#close()}, except any exceptions will be ignored.
+ * @param output A (possibly null) OutputStream
+ */
+ private static void shutdownStream( final OutputStream output )
+ {
+ if( null == output )
+ {
+ return;
+ }
+
+ try
+ {
+ output.close();
+ }
+ catch( final IOException ioe )
+ {
+ }
+ }
+
+ /**
+ * Unconditionally close an <code>InputStream</code>.
+ * Equivalent to {@link java.io.InputStream#close()}, except any exceptions will be ignored.
+ * @param input A (possibly null) InputStream
+ */
+ private static void shutdownStream( final InputStream input )
+ {
+ if( null == input )
+ {
+ return;
+ }
+
+ try
+ {
+ input.close();
+ }
+ catch( final IOException ioe )
+ {
+ }
+ }
+}
diff --git a/src/test/org/apache/commons/io/compress/bzip2/asf-logo-huge.tar b/src/test/org/apache/commons/io/compress/bzip2/asf-logo-huge.tar
new file mode 100644
index 0000000..3f92609
--- /dev/null
+++ b/src/test/org/apache/commons/io/compress/bzip2/asf-logo-huge.tar
Binary files differ
diff --git a/src/test/org/apache/commons/io/compress/bzip2/asf-logo-huge.tar.bz2 b/src/test/org/apache/commons/io/compress/bzip2/asf-logo-huge.tar.bz2
new file mode 100644
index 0000000..7c2d215
--- /dev/null
+++ b/src/test/org/apache/commons/io/compress/bzip2/asf-logo-huge.tar.bz2
Binary files differ
diff --git a/src/test/org/apache/commons/io/compress/tar/TarTestCase.java b/src/test/org/apache/commons/io/compress/tar/TarTestCase.java
new file mode 100644
index 0000000..c9c6269
--- /dev/null
+++ b/src/test/org/apache/commons/io/compress/tar/TarTestCase.java
@@ -0,0 +1,309 @@
+/*
+ * Copyright (C) The Apache Software Foundation. All rights reserved.
+ *
+ * This software is published under the terms of the Apache Software License
+ * version 1.1, a copy of which has been included with this distribution in
+ * the LICENSE.txt file.
+ */
+package org.apache.commons.compress.tar;
+
+import java.io.BufferedInputStream;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import junit.framework.TestCase;
+import org.apache.excalibur.tar.TarEntry;
+import org.apache.excalibur.tar.TarInputStream;
+import org.apache.excalibur.tar.TarOutputStream;
+
+/**
+ * Test case for all tar resources.
+ *
+ * @todo Find V7 tar and do tests against it
+ * @author <a href="mailto:peter@apache.org">Peter Donald</a>
+ * @version $Revision: 1.1 $ $Date: 2002/07/08 22:19:10 $
+ */
+public final class TarTestCase
+ extends TestCase
+{
+ private static final char SP = File.separatorChar;
+ private static final String BASE_DATA_NAME = "data.txt";
+ private static final String LFN_PART = "a-b-c-d-e-f-g-h-i-j/";
+ private static final String LONG_FILE_NAME =
+ LFN_PART + LFN_PART + LFN_PART + LFN_PART + LFN_PART + "a";
+
+ private static final String BASEDIR = calcBaseDir();
+
+ private static final File BASEDIR_FILE = new File( BASEDIR );
+ private static final File POSIX_TAR_FILE =
+ new File( BASEDIR_FILE, "posix.tar" );
+ // private static final File V7_TAR_FILE =
+ // new File( BASEDIR_FILE, "v7.tar" );
+ private static final File GNU_TAR_FILE =
+ new File( BASEDIR_FILE, "gnu.tar" );
+ private static final File DATA_FILE1 =
+ new File( BASEDIR_FILE, BASE_DATA_NAME );
+ private static final String USER_NAME = "avalon";
+ private static final String GROUP_NAME = "excalibur";
+ private static final long SIZE = DATA_FILE1.length();
+ private static final int GROUP_ID = 0;
+ private static final int USER_ID = 0;
+ private static final int MODE = 0100000;
+ private static final int MOD_TIME = 0;
+
+ public TarTestCase()
+ {
+ this( "Tar Test Case" );
+ }
+
+ public TarTestCase( String name )
+ {
+ super( name );
+ }
+
+ private static String calcBaseDir()
+ {
+ final String name = TarTestCase.class.getName();
+ final int size = name.length();
+ final String filename =
+ name.substring( 0, size - 11 ).replace( '.', SP );
+ return ".." + SP + ".." + SP +
+ "src" + SP + "test" + SP + filename + SP;
+ }
+
+ public void testReadPosixTar()
+ throws Exception
+ {
+ compareTar( BASE_DATA_NAME, POSIX_TAR_FILE );
+ }
+
+ public void testReadGnuTar()
+ throws Exception
+ {
+ compareTar( LONG_FILE_NAME, GNU_TAR_FILE );
+ }
+
+ public void testWritePosixTar()
+ throws Exception
+ {
+ //final File temp = new File( BASEDIR_FILE, "posix2.tar" );
+ final File temp = File.createTempFile( "delete-me", "tar" );
+ final FileOutputStream fileOutput = new FileOutputStream( temp );
+ final TarOutputStream output = new TarOutputStream( fileOutput );
+ //output.setBufferDebug( true );
+ final TarEntry entry = new TarEntry( BASE_DATA_NAME );
+ setupEntry( entry );
+ output.putNextEntry( entry );
+
+ final FileInputStream fileInput = new FileInputStream( DATA_FILE1 );
+ output.copyEntryContents( fileInput );
+ output.closeEntry();
+ shutdownStream( fileInput );
+ shutdownStream( output );
+ shutdownStream( fileOutput );
+
+ assertTrue( "Tar files Equal", contentEquals( temp, POSIX_TAR_FILE ) );
+ temp.delete();
+ }
+
+ public void testWriteGnuTar()
+ throws Exception
+ {
+ //final File temp = new File( BASEDIR_FILE, "gnu2.tar" );
+ final File temp = File.createTempFile( "delete-me", "tar" );
+ final FileOutputStream fileOutput = new FileOutputStream( temp );
+ final TarOutputStream output = new TarOutputStream( fileOutput );
+ //output.setBufferDebug( true );
+ output.setLongFileMode( TarOutputStream.LONGFILE_GNU );
+ final TarEntry entry = new TarEntry( LONG_FILE_NAME );
+ setupEntry( entry );
+ output.putNextEntry( entry );
+
+ final FileInputStream fileInput = new FileInputStream( DATA_FILE1 );
+ output.copyEntryContents( fileInput );
+ output.closeEntry();
+ shutdownStream( fileInput );
+ shutdownStream( output );
+ shutdownStream( fileOutput );
+
+ //Have to compare it this way as the contents will differ
+ //due to entry created for second part of name
+ compareTar( LONG_FILE_NAME, temp );
+ temp.delete();
+ }
+
+ private void setupEntry( final TarEntry entry )
+ {
+ entry.setModTime( MOD_TIME );
+ entry.setSize( SIZE );
+ entry.setUserID( USER_ID );
+ entry.setGroupID( GROUP_ID );
+ entry.setUserName( USER_NAME );
+ entry.setGroupName( GROUP_NAME );
+ entry.setMode( MODE );
+ }
+
+ private void checkEntry( final TarEntry entry )
+ {
+ assertEquals( "Entry size", SIZE, entry.getSize() );
+ assertEquals( "Entry User ID", USER_ID, entry.getUserID() );
+ assertEquals( "Entry Group ID", GROUP_ID, entry.getGroupID() );
+ assertEquals( "Entry User name", USER_NAME, entry.getUserName() );
+ assertEquals( "Entry group name", GROUP_NAME, entry.getGroupName() );
+ assertEquals( "Entry mode", MODE, entry.getMode() );
+ assertEquals( "Entry mode", MOD_TIME, entry.getModTime().getTime() / 1000 );
+ }
+
+ /**
+ * Read tar entry with specified name from tar file1 and compare
+ * against data file DATA_FILE1.
+ *
+ * @param entryName the expected name of entry
+ * @param file1 the tar file comparing
+ * @throws IOException if an error occurs
+ */
+ private void compareTar( final String entryName,
+ final File file1 )
+ throws IOException
+ {
+ final FileInputStream fileInput = new FileInputStream( file1 );
+ final TarInputStream input = new TarInputStream( fileInput );
+ //input.setDebug( true );
+ final TarEntry entry = input.getNextEntry();
+
+ assertEquals( "Entry name", entryName, entry.getName() );
+ checkEntry( entry );
+
+ final File temp = new File( BASEDIR_FILE, entryName.length() + "data.txt" );//File.createTempFile( "delete-me", "tar" );
+ final FileOutputStream output = new FileOutputStream( temp );
+ input.copyEntryContents( output );
+ shutdownStream( output );
+
+ assertNull( "Next Entry", input.getNextEntry() );
+
+ shutdownStream( input );
+
+ assertTrue( "Data Equals", contentEquals( temp, DATA_FILE1 ) );
+ temp.delete();
+ }
+
+ /**
+ * Compare the contents of two files to determine if they are equal or not.
+ *
+ * @param file1 the first file
+ * @param file2 the second file
+ * @return true if the content of the files are equal or they both don't exist, false otherwise
+ */
+ private boolean contentEquals( final File file1, final File file2 )
+ throws IOException
+ {
+ final boolean file1Exists = file1.exists();
+ if( file1Exists != file2.exists() )
+ {
+ return false;
+ }
+
+ if( !file1Exists )
+ {
+ // two not existing files are equal
+ return true;
+ }
+
+ if( file1.isDirectory() || file2.isDirectory() )
+ {
+ // don't want to compare directory contents
+ return false;
+ }
+
+ InputStream input1 = null;
+ InputStream input2 = null;
+ try
+ {
+ input1 = new FileInputStream( file1 );
+ input2 = new FileInputStream( file2 );
+ return contentEquals( input1, input2 );
+
+ }
+ finally
+ {
+ shutdownStream( input1 );
+ shutdownStream( input2 );
+ }
+ }
+
+ /**
+ * Compare the contents of two Streams to determine if they are equal or not.
+ *
+ * @param input1 the first stream
+ * @param input2 the second stream
+ * @return true if the content of the streams are equal or they both don't exist, false otherwise
+ */
+ private boolean contentEquals( final InputStream input1,
+ final InputStream input2 )
+ throws IOException
+ {
+ final InputStream bufferedInput1 = new BufferedInputStream( input1 );
+ final InputStream bufferedInput2 = new BufferedInputStream( input2 );
+
+ int count = 0;
+ int ch = bufferedInput1.read();
+ while( -1 != ch )
+ {
+ final int ch2 = bufferedInput2.read();
+ count++;
+ if( ch != ch2 )
+ {
+ System.out.println( "count = " + count );
+ System.out.println( "ch2 = " + ch2 );
+ System.out.println( "ch = " + ch );
+ return false;
+ }
+ ch = bufferedInput1.read();
+ }
+
+ final int ch2 = bufferedInput2.read();
+ if( -1 != ch2 )
+ {
+ return false;
+ }
+ else
+ {
+ return true;
+ }
+ }
+
+ private void shutdownStream( final InputStream input )
+ {
+ if( null == input )
+ {
+ return;
+ }
+
+ try
+ {
+ input.close();
+ }
+ catch( final IOException ioe )
+ {
+ }
+ }
+
+ private void shutdownStream( final OutputStream output )
+ {
+ if( null == output )
+ {
+ return;
+ }
+
+ try
+ {
+ output.close();
+ }
+ catch( final IOException ioe )
+ {
+ }
+ }
+}
diff --git a/src/test/org/apache/commons/io/compress/tar/TarTestSuite.java b/src/test/org/apache/commons/io/compress/tar/TarTestSuite.java
new file mode 100644
index 0000000..96baafc
--- /dev/null
+++ b/src/test/org/apache/commons/io/compress/tar/TarTestSuite.java
@@ -0,0 +1,23 @@
+/*
+ * Copyright The Apache Software Foundation. All rights reserved.
+ *
+ * This software is published under the terms of the Apache Software License
+ * version 1.1, a copy of which has been included with this distribution in
+ * the LICENSE.txt file.
+ */
+package org.apache.commons.compress.tar;
+
+import junit.framework.Test;
+import junit.framework.TestSuite;
+
+/**
+ * A basic test suite that tests all the tar package.
+ */
+public class TarTestSuite
+{
+ public static Test suite()
+ {
+ final TestSuite suite = new TestSuite( "Tar Utilities" );
+ return suite;
+ }
+}
diff --git a/src/test/org/apache/commons/io/compress/tar/data.txt b/src/test/org/apache/commons/io/compress/tar/data.txt
new file mode 100644
index 0000000..f03277e
--- /dev/null
+++ b/src/test/org/apache/commons/io/compress/tar/data.txt
@@ -0,0 +1,15 @@
+ One of the greatest benefactors of all lifekind was a man who
+couldn't keep his mind on the job at hand.
+ Brilliant?
+ Certainly.
+ One of the foremost genetic engineers of his or any other
+generation, including a number he had designed himself?
+ Without a doubt.
+ The problem was that he was far too interested in things which
+he shouldn't be interested in, at least as people would tell him,
+not now.
+ He was also, partly because of this, of a rather irritable
+disposition.
+ So when the world was threatened by terrible invaders from a
+distant star, who were still a fair way off but traveling fast,
+he, Blart Versenwald III...
\ No newline at end of file
diff --git a/src/test/org/apache/commons/io/compress/tar/gnu.tar b/src/test/org/apache/commons/io/compress/tar/gnu.tar
new file mode 100644
index 0000000..22f006a
--- /dev/null
+++ b/src/test/org/apache/commons/io/compress/tar/gnu.tar
Binary files differ
diff --git a/src/test/org/apache/commons/io/compress/tar/posix.tar b/src/test/org/apache/commons/io/compress/tar/posix.tar
new file mode 100644
index 0000000..8044616
--- /dev/null
+++ b/src/test/org/apache/commons/io/compress/tar/posix.tar
Binary files differ
diff --git a/src/test/org/apache/commons/io/compress/tar/update-tars.bat b/src/test/org/apache/commons/io/compress/tar/update-tars.bat
new file mode 100644
index 0000000..355b2f2
--- /dev/null
+++ b/src/test/org/apache/commons/io/compress/tar/update-tars.bat
@@ -0,0 +1,3 @@
+copy gnu2.tar gnu.tar
+copy posix2.tar posix.tar
+pause
\ No newline at end of file
diff --git a/src/test/org/apache/commons/io/compress/zip/AsiExtraFieldTestCase.java b/src/test/org/apache/commons/io/compress/zip/AsiExtraFieldTestCase.java
new file mode 100644
index 0000000..059f3af
--- /dev/null
+++ b/src/test/org/apache/commons/io/compress/zip/AsiExtraFieldTestCase.java
@@ -0,0 +1,167 @@
+/*
+ * Copyright (C) The Apache Software Foundation. All rights reserved.
+ *
+ * This software is published under the terms of the Apache Software License
+ * version 1.1, a copy of which has been included with this distribution in
+ * the LICENSE.txt file.
+ */
+package org.apache.commons.io.compress.zip;
+
+import java.util.zip.ZipException;
+import junit.framework.TestCase;
+import org.apache.excalibur.zip.AsiExtraField;
+import org.apache.excalibur.zip.UnixStat;
+
+/**
+ * JUnit testcases AsiExtraField.
+ *
+ * @author <a href="mailto:stefan.bodewig@epost.de">Stefan Bodewig</a>
+ */
+public class AsiExtraFieldTestCase
+ extends TestCase
+ implements UnixStat
+{
+ public AsiExtraFieldTestCase( final String name )
+ {
+ super( name );
+ }
+
+ /**
+ * Test file mode magic.
+ */
+ public void testModes()
+ {
+ final AsiExtraField field = new AsiExtraField();
+ field.setMode( 0123 );
+ assertEquals( "plain file", 0100123, field.getMode() );
+ field.setDirectory( true );
+ assertEquals( "directory", 040123, field.getMode() );
+ field.setLinkedFile( "test" );
+ assertEquals( "symbolic link", 0120123, field.getMode() );
+ }
+
+ private AsiExtraField createField()
+ {
+ final AsiExtraField field = new AsiExtraField();
+ field.setMode( 0123 );
+ field.setUserId( 5 );
+ field.setGroupId( 6 );
+ return field;
+ }
+
+ public void testContent1()
+ {
+ final AsiExtraField field = createField();
+ final byte[] data = field.getLocalFileDataData();
+
+ // CRC manually calculated, sorry
+ final byte[] expect = {(byte)0xC6, 0x02, 0x78, (byte)0xB6, // CRC
+ 0123, (byte)0x80, // mode
+ 0, 0, 0, 0, // link length
+ 5, 0, 6, 0}; // uid, gid
+ assertEquals( "no link", expect.length, data.length );
+ for( int i = 0; i < expect.length; i++ )
+ {
+ assertEquals( "no link, byte " + i, expect[ i ], data[ i ] );
+ }
+
+ field.setLinkedFile( "test" );
+ }
+
+ public void testContent2()
+ {
+ final AsiExtraField field = createField();
+ field.setLinkedFile( "test" );
+
+ final byte[] data = field.getLocalFileDataData();
+ final byte[] expect = new byte[]{0x75, (byte)0x8E, 0x41, (byte)0xFD, // CRC
+ 0123, (byte)0xA0, // mode
+ 4, 0, 0, 0, // link length
+ 5, 0, 6, 0, // uid, gid
+ (byte)'t', (byte)'e', (byte)'s', (byte)'t'};
+ assertEquals( "no link", expect.length, data.length );
+ for( int i = 0; i < expect.length; i++ )
+ {
+ assertEquals( "no link, byte " + i, expect[ i ], data[ i ] );
+ }
+
+ }
+
+ public void testReparse1()
+ throws ZipException
+ {
+ // CRC manually calculated, sorry
+ final byte[] data = {(byte)0xC6, 0x02, 0x78, (byte)0xB6, // CRC
+ 0123, (byte)0x80, // mode
+ 0, 0, 0, 0, // link length
+ 5, 0, 6, 0}; // uid, gid
+ final AsiExtraField field = new AsiExtraField();
+ field.parseFromLocalFileData( data, 0, data.length );
+
+ assertEquals( "length plain file", data.length,
+ field.getLocalFileDataLength().getValue() );
+ assertTrue( "plain file, no link", !field.isLink() );
+ assertTrue( "plain file, no dir", !field.isDirectory() );
+ assertEquals( "mode plain file", FILE_FLAG | 0123, field.getMode() );
+ assertEquals( "uid plain file", 5, field.getUserId() );
+ assertEquals( "gid plain file", 6, field.getGroupID() );
+ }
+
+ public void testReparse2()
+ throws ZipException
+ {
+ final byte[] data = new byte[]{0x75, (byte)0x8E, 0x41, (byte)0xFD, // CRC
+ 0123, (byte)0xA0, // mode
+ 4, 0, 0, 0, // link length
+ 5, 0, 6, 0, // uid, gid
+ (byte)'t', (byte)'e', (byte)'s', (byte)'t'};
+ final AsiExtraField field = new AsiExtraField();
+ field.parseFromLocalFileData( data, 0, data.length );
+ assertEquals( "length link", data.length,
+ field.getLocalFileDataLength().getValue() );
+ assertTrue( "link, is link", field.isLink() );
+ assertTrue( "link, no dir", !field.isDirectory() );
+ assertEquals( "mode link", LINK_FLAG | 0123, field.getMode() );
+ assertEquals( "uid link", 5, field.getUserId() );
+ assertEquals( "gid link", 6, field.getGroupID() );
+ assertEquals( "test", field.getLinkedFile() );
+ }
+
+ public void testReparse3()
+ throws ZipException
+ {
+ final byte[] data = new byte[]{(byte)0x8E, 0x01, (byte)0xBF, (byte)0x0E, // CRC
+ 0123, (byte)0x40, // mode
+ 0, 0, 0, 0, // link
+ 5, 0, 6, 0}; // uid, gid
+ final AsiExtraField field = new AsiExtraField();
+ field.parseFromLocalFileData( data, 0, data.length );
+ assertEquals( "length dir", data.length,
+ field.getLocalFileDataLength().getValue() );
+ assertTrue( "dir, no link", !field.isLink() );
+ assertTrue( "dir, is dir", field.isDirectory() );
+ assertEquals( "mode dir", DIR_FLAG | 0123, field.getMode() );
+ assertEquals( "uid dir", 5, field.getUserId() );
+ assertEquals( "gid dir", 6, field.getGroupID() );
+ }
+
+ public void testReparse4()
+ throws Exception
+ {
+ final byte[] data = new byte[]{0, 0, 0, 0, // bad CRC
+ 0123, (byte)0x40, // mode
+ 0, 0, 0, 0, // link
+ 5, 0, 6, 0}; // uid, gid
+ final AsiExtraField field = new AsiExtraField();
+ try
+ {
+ field.parseFromLocalFileData( data, 0, data.length );
+ fail( "should raise bad CRC exception" );
+ }
+ catch( Exception e )
+ {
+ assertEquals( "bad CRC checksum 0 instead of ebf018e",
+ e.getMessage() );
+ }
+ }
+}
diff --git a/src/test/org/apache/commons/io/compress/zip/ExtraFieldUtilsTestCase.java b/src/test/org/apache/commons/io/compress/zip/ExtraFieldUtilsTestCase.java
new file mode 100644
index 0000000..b6eeb53
--- /dev/null
+++ b/src/test/org/apache/commons/io/compress/zip/ExtraFieldUtilsTestCase.java
@@ -0,0 +1,120 @@
+/*
+ * Copyright (C) The Apache Software Foundation. All rights reserved.
+ *
+ * This software is published under the terms of the Apache Software License
+ * version 1.1, a copy of which has been included with this distribution in
+ * the LICENSE.txt file.
+ */
+package org.apache.commons.io.compress.zip;
+
+import junit.framework.TestCase;
+import org.apache.excalibur.zip.AsiExtraField;
+import org.apache.excalibur.zip.ExtraFieldUtils;
+import org.apache.excalibur.zip.UnixStat;
+import org.apache.excalibur.zip.UnrecognizedExtraField;
+import org.apache.excalibur.zip.ZipExtraField;
+import org.apache.excalibur.zip.ZipShort;
+
+/**
+ * JUnit testcases ExtraFieldUtils.
+ *
+ * @author <a href="mailto:stefan.bodewig@epost.de">Stefan Bodewig</a>
+ */
+public class ExtraFieldUtilsTestCase
+ extends TestCase
+ implements UnixStat
+{
+ private AsiExtraField m_field;
+ private UnrecognizedExtraField m_dummy;
+ private byte[] m_data;
+ private byte[] m_local;
+
+ public ExtraFieldUtilsTestCase( final String name )
+ {
+ super( name );
+ }
+
+ public void setUp()
+ {
+ m_field = new AsiExtraField();
+ m_field.setMode( 0755 );
+ m_field.setDirectory( true );
+ m_dummy = new UnrecognizedExtraField();
+ m_dummy.setHeaderId( new ZipShort( 1 ) );
+ m_dummy.setLocalFileDataData( new byte[ 0 ] );
+ m_dummy.setCentralDirectoryData( new byte[]{0} );
+
+ m_local = m_field.getLocalFileDataData();
+ final byte[] dummyLocal = m_dummy.getLocalFileDataData();
+ m_data = new byte[ 4 + m_local.length + 4 + dummyLocal.length ];
+ System.arraycopy( m_field.getHeaderID().getBytes(), 0, m_data, 0, 2 );
+ System.arraycopy( m_field.getLocalFileDataLength().getBytes(), 0, m_data, 2, 2 );
+ System.arraycopy( m_local, 0, m_data, 4, m_local.length );
+ System.arraycopy( m_dummy.getHeaderID().getBytes(), 0, m_data,
+ 4 + m_local.length, 2 );
+ System.arraycopy( m_dummy.getLocalFileDataLength().getBytes(), 0, m_data,
+ 4 + m_local.length + 2, 2 );
+ System.arraycopy( dummyLocal, 0, m_data,
+ 4 + m_local.length + 4, dummyLocal.length );
+
+ }
+
+ /**
+ * test parser.
+ */
+ public void testParse() throws Exception
+ {
+ final ZipExtraField[] extraField = ExtraFieldUtils.parse( m_data );
+ assertEquals( "number of fields", 2, extraField.length );
+ assertTrue( "type field 1", extraField[ 0 ] instanceof AsiExtraField );
+ assertEquals( "mode field 1", 040755,
+ ( (AsiExtraField)extraField[ 0 ] ).getMode() );
+ assertTrue( "type field 2", extraField[ 1 ] instanceof UnrecognizedExtraField );
+ assertEquals( "data length field 2", 0,
+ extraField[ 1 ].getLocalFileDataLength().getValue() );
+
+ final byte[] data2 = new byte[ m_data.length - 1 ];
+ System.arraycopy( m_data, 0, data2, 0, data2.length );
+ try
+ {
+ ExtraFieldUtils.parse( data2 );
+ fail( "data should be invalid" );
+ }
+ catch( Exception e )
+ {
+ assertEquals( "message",
+ "data starting at " + ( 4 + m_local.length ) + " is in unknown format",
+ e.getMessage() );
+ }
+ }
+
+ /**
+ * Test merge methods
+ */
+ public void testMerge()
+ {
+ final byte[] local =
+ ExtraFieldUtils.mergeLocalFileDataData( new ZipExtraField[]{m_field, m_dummy} );
+ assertEquals( "local length", m_data.length, local.length );
+ for( int i = 0; i < local.length; i++ )
+ {
+ assertEquals( "local byte " + i, m_data[ i ], local[ i ] );
+ }
+
+ final byte[] dummyCentral = m_dummy.getCentralDirectoryData();
+ final byte[] data2 = new byte[ 4 + m_local.length + 4 + dummyCentral.length ];
+ System.arraycopy( m_data, 0, data2, 0, 4 + m_local.length + 2 );
+ System.arraycopy( m_dummy.getCentralDirectoryLength().getBytes(), 0,
+ data2, 4 + m_local.length + 2, 2 );
+ System.arraycopy( dummyCentral, 0, data2,
+ 4 + m_local.length + 4, dummyCentral.length );
+
+ final byte[] central =
+ ExtraFieldUtils.mergeCentralDirectoryData( new ZipExtraField[]{m_field, m_dummy} );
+ assertEquals( "central length", data2.length, central.length );
+ for( int i = 0; i < central.length; i++ )
+ {
+ assertEquals( "central byte " + i, data2[ i ], central[ i ] );
+ }
+ }
+}
diff --git a/src/test/org/apache/commons/io/compress/zip/ZipEntryTestCase.java b/src/test/org/apache/commons/io/compress/zip/ZipEntryTestCase.java
new file mode 100644
index 0000000..8fc5d9d
--- /dev/null
+++ b/src/test/org/apache/commons/io/compress/zip/ZipEntryTestCase.java
@@ -0,0 +1,99 @@
+/*
+ * Copyright (C) The Apache Software Foundation. All rights reserved.
+ *
+ * This software is published under the terms of the Apache Software License
+ * version 1.1, a copy of which has been included with this distribution in
+ * the LICENSE.txt file.
+ */
+package org.apache.commons.io.compress.zip;
+
+import java.util.NoSuchElementException;
+import junit.framework.TestCase;
+import org.apache.excalibur.zip.AsiExtraField;
+import org.apache.excalibur.zip.UnrecognizedExtraField;
+import org.apache.excalibur.zip.ZipEntry;
+import org.apache.excalibur.zip.ZipExtraField;
+import org.apache.excalibur.zip.ZipShort;
+
+/**
+ * JUnit testcases ZipEntry.
+ *
+ * @author <a href="mailto:stefan.bodewig@epost.de">Stefan Bodewig</a>
+ */
+public class ZipEntryTestCase
+ extends TestCase
+{
+ public ZipEntryTestCase( final String name )
+ {
+ super( name );
+ }
+
+ /**
+ * test handling of extra fields
+ */
+ public void testExtraFields()
+ {
+ final AsiExtraField field = createField();
+ final UnrecognizedExtraField extraField = createExtraField();
+
+ final ZipEntry entry = new ZipEntry( "test/" );
+ entry.setExtraFields( new ZipExtraField[]{field, extraField} );
+ final byte[] data1 = entry.getExtra();
+ ZipExtraField[] result = entry.getExtraFields();
+ assertEquals( "first pass", 2, result.length );
+ assertSame( field, result[ 0 ] );
+ assertSame( extraField, result[ 1 ] );
+
+ UnrecognizedExtraField u2 = new UnrecognizedExtraField();
+ u2.setHeaderId( new ZipShort( 1 ) );
+ u2.setLocalFileDataData( new byte[]{1} );
+
+ entry.addExtraField( u2 );
+ byte[] data2 = entry.getExtra();
+ result = entry.getExtraFields();
+ assertEquals( "second pass", 2, result.length );
+ assertSame( field, result[ 0 ] );
+ assertSame( u2, result[ 1 ] );
+ assertEquals( "length second pass", data1.length + 1, data2.length );
+
+ UnrecognizedExtraField u3 = new UnrecognizedExtraField();
+ u3.setHeaderId( new ZipShort( 2 ) );
+ u3.setLocalFileDataData( new byte[]{1} );
+ entry.addExtraField( u3 );
+ result = entry.getExtraFields();
+ assertEquals( "third pass", 3, result.length );
+
+ entry.removeExtraField( new ZipShort( 1 ) );
+ byte[] data3 = entry.getExtra();
+ result = entry.getExtraFields();
+ assertEquals( "fourth pass", 2, result.length );
+ assertSame( field, result[ 0 ] );
+ assertSame( u3, result[ 1 ] );
+ assertEquals( "length fourth pass", data2.length, data3.length );
+
+ try
+ {
+ entry.removeExtraField( new ZipShort( 1 ) );
+ fail( "should be no such element" );
+ }
+ catch( final NoSuchElementException nse )
+ {
+ }
+ }
+
+ private UnrecognizedExtraField createExtraField()
+ {
+ UnrecognizedExtraField extraField = new UnrecognizedExtraField();
+ extraField.setHeaderId( new ZipShort( 1 ) );
+ extraField.setLocalFileDataData( new byte[ 0 ] );
+ return extraField;
+ }
+
+ private AsiExtraField createField()
+ {
+ final AsiExtraField field = new AsiExtraField();
+ field.setDirectory( true );
+ field.setMode( 0755 );
+ return field;
+ }
+}
diff --git a/src/test/org/apache/commons/io/compress/zip/ZipLongTestCase.java b/src/test/org/apache/commons/io/compress/zip/ZipLongTestCase.java
new file mode 100644
index 0000000..065c17a
--- /dev/null
+++ b/src/test/org/apache/commons/io/compress/zip/ZipLongTestCase.java
@@ -0,0 +1,80 @@
+/*
+ * Copyright (C) The Apache Software Foundation. All rights reserved.
+ *
+ * This software is published under the terms of the Apache Software License
+ * version 1.1, a copy of which has been included with this distribution in
+ * the LICENSE.txt file.
+ */
+package org.apache.commons.io.compress.zip;
+
+import junit.framework.TestCase;
+import org.apache.excalibur.zip.ZipLong;
+
+/**
+ * JUnit 3 testcases for org.apache.tools.zip.ZipLong.
+ *
+ * @author <a href="mailto:stefan.bodewig@epost.de">Stefan Bodewig</a>
+ */
+public class ZipLongTestCase
+ extends TestCase
+{
+
+ public ZipLongTestCase( final String name )
+ {
+ super( name );
+ }
+
+ /**
+ * Test conversion to bytes.
+ */
+ public void testToBytes()
+ {
+ final ZipLong zipLong = new ZipLong( 0x12345678 );
+ final byte[] result = zipLong.getBytes();
+ assertEquals( "length getBytes", 4, result.length );
+ assertEquals( "first byte getBytes", 0x78, result[ 0 ] );
+ assertEquals( "second byte getBytes", 0x56, result[ 1 ] );
+ assertEquals( "third byte getBytes", 0x34, result[ 2 ] );
+ assertEquals( "fourth byte getBytes", 0x12, result[ 3 ] );
+ }
+
+ /**
+ * Test conversion from bytes.
+ */
+ public void testFromBytes()
+ {
+ final byte[] value = new byte[]{0x78, 0x56, 0x34, 0x12};
+ final ZipLong zipLong = new ZipLong( value );
+ assertEquals( "value from bytes", 0x12345678, zipLong.getValue() );
+ }
+
+ /**
+ * Test the contract of the equals method.
+ */
+ public void testEquals()
+ {
+ final ZipLong zipLong1 = new ZipLong( 0x12345678 );
+ final ZipLong zipLong2 = new ZipLong( 0x12345678 );
+ final ZipLong zipLong3 = new ZipLong( 0x87654321 );
+
+ assertTrue( "reflexive", zipLong1.equals( zipLong1 ) );
+
+ assertTrue( "works", zipLong1.equals( zipLong2 ) );
+ assertTrue( "works, part two", !zipLong1.equals( zipLong3 ) );
+
+ assertTrue( "symmetric", zipLong2.equals( zipLong1 ) );
+
+ assertTrue( "null handling", !zipLong1.equals( null ) );
+ assertTrue( "non ZipLong handling", !zipLong1.equals( new Integer( 0x1234 ) ) );
+ }
+
+ /**
+ * Test sign handling.
+ */
+ public void testSign()
+ {
+ final ZipLong zipLong =
+ new ZipLong( new byte[]{(byte)0xFF, (byte)0xFF, (byte)0xFF, (byte)0xFF} );
+ assertEquals( 0x00000000FFFFFFFFl, zipLong.getValue() );
+ }
+}
diff --git a/src/test/org/apache/commons/io/compress/zip/ZipShortTestCase.java b/src/test/org/apache/commons/io/compress/zip/ZipShortTestCase.java
new file mode 100644
index 0000000..cef8dc9
--- /dev/null
+++ b/src/test/org/apache/commons/io/compress/zip/ZipShortTestCase.java
@@ -0,0 +1,76 @@
+/*
+ * Copyright (C) The Apache Software Foundation. All rights reserved.
+ *
+ * This software is published under the terms of the Apache Software License
+ * version 1.1, a copy of which has been included with this distribution in
+ * the LICENSE.txt file.
+ */
+package org.apache.commons.io.compress.zip;
+
+import junit.framework.TestCase;
+import org.apache.excalibur.zip.ZipShort;
+
+/**
+ * JUnit 3 testcases for org.apache.tools.zip.ZipShort.
+ *
+ * @author <a href="mailto:stefan.bodewig@epost.de">Stefan Bodewig</a>
+ */
+public class ZipShortTestCase
+ extends TestCase
+{
+ public ZipShortTestCase( String name )
+ {
+ super( name );
+ }
+
+ /**
+ * Test conversion to bytes.
+ */
+ public void testToBytes()
+ {
+ final ZipShort zipShort = new ZipShort( 0x1234 );
+ byte[] result = zipShort.getBytes();
+ assertEquals( "length getBytes", 2, result.length );
+ assertEquals( "first byte getBytes", 0x34, result[ 0 ] );
+ assertEquals( "second byte getBytes", 0x12, result[ 1 ] );
+ }
+
+ /**
+ * Test conversion from bytes.
+ */
+ public void testFromBytes()
+ {
+ byte[] val = new byte[]{0x34, 0x12};
+ final ZipShort zipShort = new ZipShort( val );
+ assertEquals( "value from bytes", 0x1234, zipShort.getValue() );
+ }
+
+ /**
+ * Test the contract of the equals method.
+ */
+ public void testEquals()
+ {
+ final ZipShort zipShort = new ZipShort( 0x1234 );
+ final ZipShort zipShort2 = new ZipShort( 0x1234 );
+ final ZipShort zipShort3 = new ZipShort( 0x5678 );
+
+ assertTrue( "reflexive", zipShort.equals( zipShort ) );
+
+ assertTrue( "works", zipShort.equals( zipShort2 ) );
+ assertTrue( "works, part two", !zipShort.equals( zipShort3 ) );
+
+ assertTrue( "symmetric", zipShort2.equals( zipShort ) );
+
+ assertTrue( "null handling", !zipShort.equals( null ) );
+ assertTrue( "non ZipShort handling", !zipShort.equals( new Integer( 0x1234 ) ) );
+ }
+
+ /**
+ * Test sign handling.
+ */
+ public void testSign()
+ {
+ final ZipShort zipShort = new ZipShort( new byte[]{(byte)0xFF, (byte)0xFF} );
+ assertEquals( 0x0000FFFF, zipShort.getValue() );
+ }
+}