From e599f9bb5cbe895213457e18a3234b330326c269 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Daniel=20G=C3=B3mez-S=C3=A1nchez?= Date: Fri, 12 Aug 2016 12:27:58 +0200 Subject: [PATCH 1/5] fix #430 --- .../java/htsjdk/tribble/index/AbstractIndex.java | 17 +++++--- src/main/java/htsjdk/tribble/index/Index.java | 8 ++++ .../java/htsjdk/tribble/index/IndexFactory.java | 14 +------ .../htsjdk/tribble/index/tabix/TabixIndex.java | 1 + .../htsjdk/tribble/index/IndexFactoryTest.java | 46 ++++++++++++++++++++++ 5 files changed, 68 insertions(+), 18 deletions(-) diff --git a/src/main/java/htsjdk/tribble/index/AbstractIndex.java b/src/main/java/htsjdk/tribble/index/AbstractIndex.java index 42bce732d..121859e35 100644 --- a/src/main/java/htsjdk/tribble/index/AbstractIndex.java +++ b/src/main/java/htsjdk/tribble/index/AbstractIndex.java @@ -343,13 +343,20 @@ public void write(final LittleEndianOutputStream stream) throws IOException { } @Override - public void writeBasedOnFeatureFile(final File featureFile) throws IOException { - if (!featureFile.isFile()) return; + public void write(final File idxFile) throws IOException { final LittleEndianOutputStream idxStream = - new LittleEndianOutputStream(new BufferedOutputStream(new FileOutputStream(Tribble.indexFile(featureFile)))); - write(idxStream); - idxStream.close(); + new LittleEndianOutputStream(new BufferedOutputStream(new FileOutputStream(idxFile))); + try { + write(idxStream); + } finally { + idxStream.close(); + } + } + @Override + public void writeBasedOnFeatureFile(final File featureFile) throws IOException { + if (!featureFile.isFile()) return; + write(Tribble.indexFile(featureFile)); } public void read(final LittleEndianInputStream dis) throws IOException { diff --git a/src/main/java/htsjdk/tribble/index/Index.java b/src/main/java/htsjdk/tribble/index/Index.java index 252bc95e5..ca6cc60d3 100644 --- a/src/main/java/htsjdk/tribble/index/Index.java +++ b/src/main/java/htsjdk/tribble/index/Index.java @@ -70,6 +70,14 @@ public void write(LittleEndianOutputStream stream) throws IOException; /** + * Writes the index into a file. + * + * @param idxFile Where to write the index. + * @throws IOException if the index is unable to write to the specified file + */ + public void write(final File idxFile) throws IOException; + + /** * Write an appropriately named and located Index file based on the name and location of the featureFile. * If featureFile is not a normal file, the index will silently not be written. * @param featureFile diff --git a/src/main/java/htsjdk/tribble/index/IndexFactory.java b/src/main/java/htsjdk/tribble/index/IndexFactory.java index a588220dc..4b239c588 100644 --- a/src/main/java/htsjdk/tribble/index/IndexFactory.java +++ b/src/main/java/htsjdk/tribble/index/IndexFactory.java @@ -41,16 +41,13 @@ import htsjdk.tribble.index.tabix.TabixIndexCreator; import htsjdk.tribble.readers.PositionalBufferedStream; import htsjdk.tribble.util.LittleEndianInputStream; -import htsjdk.tribble.util.LittleEndianOutputStream; import htsjdk.tribble.util.ParsingUtils; import htsjdk.tribble.util.TabixUtils; import java.io.BufferedInputStream; -import java.io.BufferedOutputStream; import java.io.File; import java.io.FileInputStream; import java.io.FileNotFoundException; -import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.lang.reflect.Constructor; @@ -290,16 +287,7 @@ public static LinearIndex createLinearIndex(final File inputFile, final FeatureC * @throws IOException */ public static void writeIndex(final Index idx, final File idxFile) throws IOException { - LittleEndianOutputStream stream = null; - try { - stream = new LittleEndianOutputStream(new BufferedOutputStream(new FileOutputStream(idxFile))); - idx.write(stream); - } - finally { - if(stream != null) { - stream.close(); - } - } + idx.write(idxFile); } /** diff --git a/src/main/java/htsjdk/tribble/index/tabix/TabixIndex.java b/src/main/java/htsjdk/tribble/index/tabix/TabixIndex.java index 9ab05d42e..b4a53b783 100644 --- a/src/main/java/htsjdk/tribble/index/tabix/TabixIndex.java +++ b/src/main/java/htsjdk/tribble/index/tabix/TabixIndex.java @@ -201,6 +201,7 @@ public TabixFormat getFormatSpec() { * * @param tabixFile Where to write the index. */ + @Override public void write(final File tabixFile) { final LittleEndianOutputStream los = new LittleEndianOutputStream(new BlockCompressedOutputStream(tabixFile)); try { diff --git a/src/test/java/htsjdk/tribble/index/IndexFactoryTest.java b/src/test/java/htsjdk/tribble/index/IndexFactoryTest.java index ba64998d3..939493fdb 100644 --- a/src/test/java/htsjdk/tribble/index/IndexFactoryTest.java +++ b/src/test/java/htsjdk/tribble/index/IndexFactoryTest.java @@ -25,11 +25,14 @@ import htsjdk.samtools.SAMSequenceDictionary; import htsjdk.samtools.SAMSequenceRecord; +import htsjdk.samtools.util.IOUtil; import htsjdk.tribble.TestUtils; import htsjdk.tribble.TribbleException; import htsjdk.tribble.bed.BEDCodec; +import htsjdk.tribble.index.linear.LinearIndex; import htsjdk.tribble.index.tabix.TabixFormat; import htsjdk.tribble.index.tabix.TabixIndex; +import htsjdk.tribble.util.LittleEndianOutputStream; import htsjdk.variant.vcf.VCFCodec; import htsjdk.variant.vcf.VCFFileReader; import org.testng.Assert; @@ -37,6 +40,8 @@ import org.testng.annotations.Test; import java.io.File; +import java.io.IOException; +import java.io.OutputStream; import java.util.List; /** @@ -112,4 +117,45 @@ public void testCreateTabixIndexOnBlockCompressed() { "Tabix indexed (bgzipped) VCF does not contain sequence: " + samSequenceRecord.getSequenceName()); } } + + @Test + public void testWriteIndex() throws Exception { + // temp directory for this test + final File tempDir = IOUtil.createTempDir("writeIndex", null); + + final OutputStream nullOutputStrem = new OutputStream() { + @Override + public void write(int b) throws IOException { + + } + }; + + // LINEAR INDEX + final File inputFileVcf = + new File("src/test/resources/htsjdk/tribble/tabix/testTabixIndex.vcf"); + final LinearIndex linearIndex = + IndexFactory.createLinearIndex(inputFileVcf, new VCFCodec()); + // write to a file + final File tempLineraIndex = new File(tempDir, "linearIndex.idx"); + Assert.assertFalse(tempLineraIndex.exists()); + linearIndex.write(tempLineraIndex); + Assert.assertTrue(tempLineraIndex.exists()); + // write to an stream does not thrown an error + linearIndex.write(new LittleEndianOutputStream(nullOutputStrem)); + + // TABIX INDEX + final File inputFileVcfGz = + new File("src/test/resources/htsjdk/tribble/tabix/testTabixIndex.vcf.gz"); + final TabixIndex tabixIndexVcfGz = + IndexFactory + .createTabixIndex(inputFileVcfGz, new VCFCodec(), TabixFormat.VCF, null); + // wirte to a file + final File tempTabixIndex = new File(tempDir, "tabixIndex.tbi"); + Assert.assertFalse(tempTabixIndex.exists()); + tabixIndexVcfGz.write(tempTabixIndex); + Assert.assertTrue(tempTabixIndex.exists()); + // write to an stream does not thrown an error + tabixIndexVcfGz.write(new LittleEndianOutputStream(nullOutputStrem)); + + } } From 39a45ce452d405ee29b9a34eecab1f7fd0111ee1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Daniel=20G=C3=B3mez-S=C3=A1nchez?= Date: Thu, 15 Sep 2016 18:12:46 +0200 Subject: [PATCH 2/5] re-format line --- src/main/java/htsjdk/tribble/index/AbstractIndex.java | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/main/java/htsjdk/tribble/index/AbstractIndex.java b/src/main/java/htsjdk/tribble/index/AbstractIndex.java index 121859e35..9617d5f00 100644 --- a/src/main/java/htsjdk/tribble/index/AbstractIndex.java +++ b/src/main/java/htsjdk/tribble/index/AbstractIndex.java @@ -344,8 +344,7 @@ public void write(final LittleEndianOutputStream stream) throws IOException { @Override public void write(final File idxFile) throws IOException { - final LittleEndianOutputStream idxStream = - new LittleEndianOutputStream(new BufferedOutputStream(new FileOutputStream(idxFile))); + final LittleEndianOutputStream idxStream = new LittleEndianOutputStream(new BufferedOutputStream(new FileOutputStream(idxFile))); try { write(idxStream); } finally { From ae7fcefe0e66b158eb684fa7b377cbd21cb87065 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Daniel=20G=C3=B3mez-S=C3=A1nchez?= Date: Fri, 16 Sep 2016 10:20:56 +0200 Subject: [PATCH 3/5] try-with-resources and IOException --- src/main/java/htsjdk/tribble/index/AbstractIndex.java | 5 +---- src/main/java/htsjdk/tribble/index/tabix/TabixIndex.java | 8 ++------ src/test/java/htsjdk/tribble/index/tabix/TabixIndexTest.java | 3 ++- 3 files changed, 5 insertions(+), 11 deletions(-) diff --git a/src/main/java/htsjdk/tribble/index/AbstractIndex.java b/src/main/java/htsjdk/tribble/index/AbstractIndex.java index 9617d5f00..47e31ccef 100644 --- a/src/main/java/htsjdk/tribble/index/AbstractIndex.java +++ b/src/main/java/htsjdk/tribble/index/AbstractIndex.java @@ -344,11 +344,8 @@ public void write(final LittleEndianOutputStream stream) throws IOException { @Override public void write(final File idxFile) throws IOException { - final LittleEndianOutputStream idxStream = new LittleEndianOutputStream(new BufferedOutputStream(new FileOutputStream(idxFile))); - try { + try(final LittleEndianOutputStream idxStream = new LittleEndianOutputStream(new BufferedOutputStream(new FileOutputStream(idxFile)))) { write(idxStream); - } finally { - idxStream.close(); } } diff --git a/src/main/java/htsjdk/tribble/index/tabix/TabixIndex.java b/src/main/java/htsjdk/tribble/index/tabix/TabixIndex.java index b4a53b783..044cefe61 100644 --- a/src/main/java/htsjdk/tribble/index/tabix/TabixIndex.java +++ b/src/main/java/htsjdk/tribble/index/tabix/TabixIndex.java @@ -202,13 +202,9 @@ public TabixFormat getFormatSpec() { * @param tabixFile Where to write the index. */ @Override - public void write(final File tabixFile) { - final LittleEndianOutputStream los = new LittleEndianOutputStream(new BlockCompressedOutputStream(tabixFile)); - try { + public void write(final File tabixFile) throws IOException { + try(final LittleEndianOutputStream los = new LittleEndianOutputStream(new BlockCompressedOutputStream(tabixFile))) { write(los); - los.close(); - } catch (final IOException e) { - throw new TribbleException("Exception writing " + tabixFile.getAbsolutePath(), e); } } diff --git a/src/test/java/htsjdk/tribble/index/tabix/TabixIndexTest.java b/src/test/java/htsjdk/tribble/index/tabix/TabixIndexTest.java index 557a3987d..6981b8751 100644 --- a/src/test/java/htsjdk/tribble/index/tabix/TabixIndexTest.java +++ b/src/test/java/htsjdk/tribble/index/tabix/TabixIndexTest.java @@ -37,6 +37,7 @@ import org.testng.annotations.Test; import java.io.File; +import java.io.IOException; import java.util.Iterator; public class TabixIndexTest { @@ -71,7 +72,7 @@ public void readWriteTest(final File tabixFile) throws Exception { } @Test - public void testQueryProvidedItemsAmount() { + public void testQueryProvidedItemsAmount() throws IOException { final String VCF = "src/test/resources/htsjdk/tribble/tabix/YRI.trio.2010_07.indel.sites.vcf"; // Note that we store only compressed files final File plainTextVcfInputFile = new File(VCF); From c03e36da3f91c7665eeae549675d97a1985d61f7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Daniel=20G=C3=B3mez-S=C3=A1nchez?= Date: Fri, 16 Sep 2016 10:21:45 +0200 Subject: [PATCH 4/5] deprecated IndexFactory.writeIndex() --- src/main/java/htsjdk/tribble/index/IndexFactory.java | 2 ++ src/test/java/htsjdk/tribble/FeatureReaderTest.java | 2 +- 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/src/main/java/htsjdk/tribble/index/IndexFactory.java b/src/main/java/htsjdk/tribble/index/IndexFactory.java index 4b239c588..3cd1b7958 100644 --- a/src/main/java/htsjdk/tribble/index/IndexFactory.java +++ b/src/main/java/htsjdk/tribble/index/IndexFactory.java @@ -285,7 +285,9 @@ public static LinearIndex createLinearIndex(final File inputFile, final FeatureC * @param idx * @param idxFile * @throws IOException + * @deprecated use {@link Index#write(File)} instead */ + @Deprecated public static void writeIndex(final Index idx, final File idxFile) throws IOException { idx.write(idxFile); } diff --git a/src/test/java/htsjdk/tribble/FeatureReaderTest.java b/src/test/java/htsjdk/tribble/FeatureReaderTest.java index ac3405939..d62693c19 100644 --- a/src/test/java/htsjdk/tribble/FeatureReaderTest.java +++ b/src/test/java/htsjdk/tribble/FeatureReaderTest.java @@ -134,7 +134,7 @@ public void testBedNames(final File featureFile, final IndexFactory.IndexType in idxFile.delete(); } final Index idx = IndexFactory.createIndex(featureFile, codec, indexType); - IndexFactory.writeIndex(idx, idxFile); + idx.write(idxFile); idxFile.deleteOnExit(); } // else let's just hope the index exists, and if so use it From 6dda2e5a2d25fa66dd57188b39f003d0e24c0abc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Daniel=20G=C3=B3mez-S=C3=A1nchez?= Date: Fri, 16 Sep 2016 11:02:25 +0200 Subject: [PATCH 5/5] updated test --- .../htsjdk/tribble/index/IndexFactoryTest.java | 41 ------------------- src/test/java/htsjdk/tribble/index/IndexTest.java | 47 ++++++++++++++++++++++ 2 files changed, 47 insertions(+), 41 deletions(-) diff --git a/src/test/java/htsjdk/tribble/index/IndexFactoryTest.java b/src/test/java/htsjdk/tribble/index/IndexFactoryTest.java index 939493fdb..016049f32 100644 --- a/src/test/java/htsjdk/tribble/index/IndexFactoryTest.java +++ b/src/test/java/htsjdk/tribble/index/IndexFactoryTest.java @@ -117,45 +117,4 @@ public void testCreateTabixIndexOnBlockCompressed() { "Tabix indexed (bgzipped) VCF does not contain sequence: " + samSequenceRecord.getSequenceName()); } } - - @Test - public void testWriteIndex() throws Exception { - // temp directory for this test - final File tempDir = IOUtil.createTempDir("writeIndex", null); - - final OutputStream nullOutputStrem = new OutputStream() { - @Override - public void write(int b) throws IOException { - - } - }; - - // LINEAR INDEX - final File inputFileVcf = - new File("src/test/resources/htsjdk/tribble/tabix/testTabixIndex.vcf"); - final LinearIndex linearIndex = - IndexFactory.createLinearIndex(inputFileVcf, new VCFCodec()); - // write to a file - final File tempLineraIndex = new File(tempDir, "linearIndex.idx"); - Assert.assertFalse(tempLineraIndex.exists()); - linearIndex.write(tempLineraIndex); - Assert.assertTrue(tempLineraIndex.exists()); - // write to an stream does not thrown an error - linearIndex.write(new LittleEndianOutputStream(nullOutputStrem)); - - // TABIX INDEX - final File inputFileVcfGz = - new File("src/test/resources/htsjdk/tribble/tabix/testTabixIndex.vcf.gz"); - final TabixIndex tabixIndexVcfGz = - IndexFactory - .createTabixIndex(inputFileVcfGz, new VCFCodec(), TabixFormat.VCF, null); - // wirte to a file - final File tempTabixIndex = new File(tempDir, "tabixIndex.tbi"); - Assert.assertFalse(tempTabixIndex.exists()); - tabixIndexVcfGz.write(tempTabixIndex); - Assert.assertTrue(tempTabixIndex.exists()); - // write to an stream does not thrown an error - tabixIndexVcfGz.write(new LittleEndianOutputStream(nullOutputStrem)); - - } } diff --git a/src/test/java/htsjdk/tribble/index/IndexTest.java b/src/test/java/htsjdk/tribble/index/IndexTest.java index 8104a0803..aa179a9a2 100644 --- a/src/test/java/htsjdk/tribble/index/IndexTest.java +++ b/src/test/java/htsjdk/tribble/index/IndexTest.java @@ -1,13 +1,23 @@ package htsjdk.tribble.index; +import htsjdk.samtools.util.IOUtil; +import htsjdk.tribble.FeatureCodec; import htsjdk.tribble.TestUtils; +import htsjdk.tribble.Tribble; +import htsjdk.tribble.bed.BEDCodec; import htsjdk.tribble.index.linear.LinearIndex; +import htsjdk.tribble.index.tabix.TabixFormat; +import htsjdk.tribble.index.tabix.TabixIndex; +import htsjdk.tribble.util.LittleEndianOutputStream; +import htsjdk.tribble.util.TabixUtils; +import htsjdk.variant.vcf.VCFCodec; import org.testng.Assert; import org.testng.annotations.DataProvider; import org.testng.annotations.Test; import java.io.File; import java.io.IOException; +import java.io.OutputStream; import java.util.ArrayList; import java.util.List; @@ -47,4 +57,41 @@ public void testMassiveQuery(final int start, final int mid, final int mid2, fin Assert.assertTrue(allSize >= Math.max(leftSize,rightSize), "Expected size of joint query " + allSize + " to be at least >= max of left " + leftSize + " and right queries " + rightSize); } + + + @DataProvider(name = "writeIndexData") + public Object[][] writeIndexData() { + return new Object[][]{ + {new File("src/test/resources/htsjdk/tribble/tabix/testTabixIndex.vcf"), IndexFactory.IndexType.LINEAR, new VCFCodec()}, + {new File("src/test/resources/htsjdk/tribble/tabix/testTabixIndex.vcf.gz"), IndexFactory.IndexType.TABIX, new VCFCodec()}, + {new File("src/test/resources/htsjdk/tribble/test.bed"), IndexFactory.IndexType.LINEAR, new BEDCodec()} + }; + } + + private final static OutputStream nullOutputStrem = new OutputStream() { + @Override + public void write(int b) throws IOException { } + }; + + @Test(dataProvider = "writeIndexData") + public void testWriteIndex(final File inputFile, final IndexFactory.IndexType type, final FeatureCodec codec) throws Exception { + // temp index file for this test + final File tempIndex = File.createTempFile("index", (type == IndexFactory.IndexType.TABIX) ? TabixUtils.STANDARD_INDEX_EXTENSION : Tribble.STANDARD_INDEX_EXTENSION); + tempIndex.delete(); + tempIndex.deleteOnExit(); + // create the index + final Index index = IndexFactory.createIndex(inputFile, codec, type); + Assert.assertFalse(tempIndex.exists()); + // write the index to a file + index.write(tempIndex); + Assert.assertTrue(tempIndex.exists()); + // load the generated index + final Index loadedIndex = IndexFactory.loadIndex(tempIndex.getAbsolutePath()); + // tess that the sequences and properties are the same + Assert.assertEquals(loadedIndex.getSequenceNames(), index.getSequenceNames()); + Assert.assertEquals(loadedIndex.getProperties(), index.getProperties()); + // test that write to a stream does not blows ip + index.write(new LittleEndianOutputStream(nullOutputStrem)); + } + }