Package de.aristaflow.adept2.util.io
Class RereadableContent
java.lang.Object
de.aristaflow.adept2.util.io.RereadableContent
- All Implemented Interfaces:
Closeable,AutoCloseable
- Direct Known Subclasses:
FileContent,MemoryContent,WrappingContent
The
RereadableContent can be used when the content of an InputStream needs to be
processed multiple times. Depending on its eventual size the whole content of the input stream is
buffered in-memory - up to a certain threshold - or in a temporary file.
The RereadableContent as well as the provided input streams must be closed after use! This can be ensured by adhering to the following template:
try (RereadableContentBuilder rcb = new RereadableContentBuilder();
RereadableContent rc = rcb.data(inputStream).build())
{
...
try (InputStream is = rc.getInputStream())
{
...
}
...
try (InputStream is = rc.getInputStream())
{
...
}
...
}
If you want to fill the builder using an OutputStream make sure to fill and close
this before building:
try (RereadableContentBuilder rcb = new RereadableContentBuilder())
{
...
try (OutputStream os = rcb.getOutputStream())
{
...
}
...
try (RereadableContent rc = rcb.build())
{
...
}
}
You can also let the RereadableContent or the InputStreams get out of
the block structure. But make sure to Closeable.close() them all.
RereadableContent rc;
try (RereadableContentBuilder rcb = new RereadableContentBuilder())
{
...
try (OutputStream os = rcb.getOutputStream())
{
...
}
rc = rbc.build();
}
...
InputStream is1 = rc.getInputStream())
...
InputStream is2 = input.getInputStream())
...
// Just make sure to close them all (in arbitrary order).
is1.close();
...
rc.close();
...
is2.close();
...
All InputStream instances created by this class will be
AttributedInputStream also providing the size and
the SHA-512 hash of the stream data. The created streams will be
tracked. The RereadableContent will not be closed when at least one of its input
streams is still in use (has not been closed). It is ensured that closing will be done by the
last active input stream (or by the RereadableContent). Also all of these will close
in a cleanup to make sure that they will be really closed.
This class is thread-safe.
-
Nested Class Summary
Nested ClassesModifier and TypeClassDescriptionprotected static final classprotected static classThis class is an input stream that also provides theRereadableContentit has been created for. -
Field Summary
FieldsModifier and TypeFieldDescriptionprotected final Cleanup<IOException>The clean-up called as post-mortem action of thisRereadableContent.protected final Collection<Object>All streams that have been created by thisRereadableContentincluding itself are identified by an arbitraryObject.protected final CloseableThe final clean-up to be executed after all streams and thisRereadableContenthave been closed/cleaned up.static final StringThe name of thePathattribute providing the file containing the content in case of aFileContent.protected static final StringThe name of theLongattribute providing the size of the input stream in bytes.protected final byte[]The SHA-512 hash of the content.protected final longThe size of the content. -
Constructor Summary
ConstructorsModifierConstructorDescriptionprotectedRereadableContent(long size, byte[] sha512hash, Closeable finalCleanup) Creates a newRereadableContentfor the designated data.protectedRereadableContent(RereadableContent wrapped) Creates a newRereadableContentwrapping the designatedRereadableContentand creating a new input stream to keep the wrappedRereadableContentalive. -
Method Summary
Modifier and TypeMethodDescriptionfinal voidclose()Closes the underlying stream or deletes the underlying file if there is no unclosedgetInputStream().protected abstract InputStreamCreates a new input stream for the content.booleanGets an input stream for the data.byte[]Gets the SHA—512 hash of the content.longgetSize()Gets the size of the content.static LonggetSize(InputStream is) Gets the size of the designated input stream in case it is provided viaRRC_INPUT_STREAM_SIZE,nullotherwise.inthashCode()
-
Field Details
-
RRC_CONTENT_FILE
The name of thePathattribute providing the file containing the content in case of aFileContent. Otherwise this attribute will not be present.- See Also:
-
RRC_INPUT_STREAM_SIZE
The name of theLongattribute providing the size of the input stream in bytes.- See Also:
-
size
protected final long sizeThe size of the content. -
sha512hash
protected final byte[] sha512hashThe SHA-512 hash of the content. -
existingStreams
All streams that have been created by thisRereadableContentincluding itself are identified by an arbitraryObject. They have a clean-up task used forInputStream.close()as well as post-mortem action. The task removes theObjectand the last one in the collection performs cleaning up theRereadableContent, for instance deleting the temporary file. -
finalCleanup
The final clean-up to be executed after all streams and thisRereadableContenthave been closed/cleaned up. -
cleanup
The clean-up called as post-mortem action of thisRereadableContent. Since this is the same logic, it is also used byclose().
-
-
Constructor Details
-
RereadableContent
Creates a newRereadableContentfor the designated data.- Parameters:
size- The size of the content.sha512hash- The SHA-512 hash of the content.finalCleanup- The final clean-up to be executed after all streams and theRereadableContenthave been closed/cleaned up.
-
RereadableContent
Creates a newRereadableContentwrapping the designatedRereadableContentand creating a new input stream to keep the wrappedRereadableContentalive.- Parameters:
wrapped- The wrappedRereadableContent.- Throws:
IOException- If creating a new input stream from the designatedRereadableContentfails, anIOExceptionwill be thrown.
-
-
Method Details
-
getSize
public long getSize()Gets the size of the content.- Returns:
- The size of the content.
-
getSHA512Hash
public byte[] getSHA512Hash()Gets the SHA—512 hash of the content.- Returns:
- The SHA-512 hash of the content.
-
getInputStream
Gets an input stream for the data. This method may be called multiple times. The returned stream must be closed properly after use!
Closing will not affect theInputStream.- Returns:
- An input stream for the data. The caller is responsible for closing.
- Throws:
IOException- If there are problems creating a new input stream for the data or thisRereadableContenthas already been closed, anIOExceptionwill be thrown.
-
createInputStream
Creates a new input stream for the content.- Returns:
- A new input stream for the content. The caller is responsible for closing.
- Throws:
IOException- If there are problems creating a new input stream for the content, anIOExceptionwill be thrown.
-
close
Closes the underlying stream or deletes the underlying file if there is no unclosedgetInputStream(). If there are input streams of thisRereadableContentthat have not been closed yet, closing deferred until closing the last one of these input streams.- Specified by:
closein interfaceAutoCloseable- Specified by:
closein interfaceCloseable- Throws:
IOException- If closing or deleting fails, anIOExceptionwill be thrown.
-
equals
-
hashCode
public int hashCode() -
getSize
Gets the size of the designated input stream in case it is provided viaRRC_INPUT_STREAM_SIZE,nullotherwise.- Parameters:
is- The input stream for which to get the size (from the corresponding attribute).- Returns:
- The value of the size attribute of the designated input stream or
nullif not available.
-