ZipMultiReportOutput.java revision 81f79203e4f68ec9588999debd6026a4f80d47d9
1/*******************************************************************************
2 * Copyright (c) 2009, 2010 Mountainminds GmbH & Co. KG and Contributors
3 * All rights reserved. This program and the accompanying materials
4 * are made available under the terms of the Eclipse Public License v1.0
5 * which accompanies this distribution, and is available at
6 * http://www.eclipse.org/legal/epl-v10.html
7 *
8 * Contributors:
9 *    Marc R. Hoffmann - initial API and implementation
10 *
11 * $Id: $
12 *******************************************************************************/
13package org.jacoco.report;
14
15import java.io.IOException;
16import java.io.OutputStream;
17import java.util.zip.ZipEntry;
18import java.util.zip.ZipOutputStream;
19
20/**
21 * Implementation of {@link IMultiReportOutput} that writes files into a
22 * {@link ZipOutputStream}.
23 *
24 * @author Marc R. Hoffmann
25 * @version $Revision: $
26 */
27public class ZipMultiReportOutput implements IMultiReportOutput {
28
29	private final ZipOutputStream zip;
30
31	private OutputStream currentEntry;
32
33	/**
34	 * Creates a new instance based on the given {@link ZipOutputStream}.
35	 *
36	 * @param zip
37	 *            stream to write file entries to
38	 */
39	public ZipMultiReportOutput(final ZipOutputStream zip) {
40		this.zip = zip;
41	}
42
43	public OutputStream createFile(final String path) throws IOException {
44		if (currentEntry != null) {
45			currentEntry.close();
46		}
47		final ZipEntry entry = new ZipEntry(path);
48		zip.putNextEntry(entry);
49		currentEntry = new EntryOutput();
50		return currentEntry;
51	}
52
53	private final class EntryOutput extends OutputStream {
54
55		private boolean closed = false;
56
57		@Override
58		public void write(final byte[] b, final int off, final int len)
59				throws IOException {
60			ensureNotClosed();
61			zip.write(b, off, len);
62		}
63
64		@Override
65		public void write(final byte[] b) throws IOException {
66			ensureNotClosed();
67			zip.write(b);
68		}
69
70		@Override
71		public void write(final int b) throws IOException {
72			ensureNotClosed();
73			zip.write(b);
74		}
75
76		@Override
77		public void flush() throws IOException {
78			ensureNotClosed();
79			zip.flush();
80		}
81
82		@Override
83		public void close() throws IOException {
84			if (!closed) {
85				closed = true;
86				zip.closeEntry();
87			}
88		}
89
90		private void ensureNotClosed() throws IOException {
91			if (closed) {
92				throw new IOException("Zip entry already closed.");
93			}
94		}
95
96	}
97
98}
99