use of org.apache.sis.storage.ConcurrentWriteException in project sis by apache.
the class StaxDataStore method createWriter.
/**
* Creates a new XML stream writer for writing the XML document.
* If another {@code XMLStreamWriter} has already been created before this method call,
* whether this method will succeed in creating a new writer depends on the storage type
* (e.g. file or output stream).
*
* @param target the writer which will store the {@code XMLStreamWriter} reference.
* @return a new writer for writing the XML data.
* @throws DataStoreException if the output type is not recognized or the data store is closed.
* @throws XMLStreamException if an error occurred while opening the XML file.
* @throws IOException if an error occurred while preparing the output stream.
*/
final synchronized XMLStreamWriter createWriter(final StaxStreamWriter target) throws DataStoreException, XMLStreamException, IOException {
Object outputOrFile = storage;
if (outputOrFile == null) {
throw new DataStoreClosedException(getLocale(), getFormatName(), StandardOpenOption.WRITE);
}
switch(state) {
default:
throw new AssertionError(state);
case READING:
throw new ConcurrentReadException(getLocale(), getDisplayName());
case WRITING:
throw new ConcurrentWriteException(getLocale(), getDisplayName());
// Stream already at the data start; nothing to do.
case START:
break;
case FINISHED:
{
if (reset())
break;
throw new ForwardOnlyStorageException(getLocale(), getDisplayName(), StandardOpenOption.WRITE);
}
}
/*
* If the storage given by the user was not one of OutputStream, Writer or other type recognized
* by OutputType, then maybe that storage was a Path, File or URL, in which case the constructor
* should have opened an InputStream (not an OutputStream) for it. In some cases (e.g. reading a
* channel opened on a file), the input stream can be converted to an output stream.
*/
AutoCloseable output = stream;
OutputType type = storageToWriter;
if (type == null) {
type = OutputType.STREAM;
output = IOUtilities.toOutputStream(output);
if (output == null) {
throw new UnsupportedStorageException(getLocale(), getFormatName(), storage, StandardOpenOption.WRITE);
}
outputOrFile = output;
if (output != stream) {
stream = output;
mark();
}
}
XMLStreamWriter writer = type.create(this, outputOrFile);
if (indentation >= 0) {
writer = new FormattedWriter(writer, indentation);
}
target.stream = output;
state = WRITING;
return writer;
}
use of org.apache.sis.storage.ConcurrentWriteException in project sis by apache.
the class StaxDataStore method createReader.
/**
* Creates a new XML stream reader for reading the document from its position at {@code StaxDataStore}
* creation time. If another {@code XMLStreamReader} has already been created before this method call,
* whether this method will succeed in creating a new reader depends on the storage type (e.g. file or
* input stream) or on whether the previous reader has been closed.
*
* @param target the reader which will store the {@code XMLStreamReader} reference.
* @return a new reader for reading the XML data.
* @throws DataStoreException if the input type is not recognized or the data store is closed.
* @throws XMLStreamException if an error occurred while opening the XML file.
* @throws IOException if an error occurred while preparing the input stream.
* @throws Exception if another kind of error occurred while closing a previous stream.
*/
@SuppressWarnings("fallthrough")
final synchronized XMLStreamReader createReader(final StaxStreamReader target) throws Exception {
Object inputOrFile = storage;
if (inputOrFile == null) {
throw new DataStoreClosedException(getLocale(), getFormatName(), StandardOpenOption.READ);
}
AutoCloseable input = stream;
InputType type = storageToReader;
/*
* If the stream has already been used by a previous read operation, then we need to rewind
* it to the start position determined at construction time. It the stream does not support
* mark, then we can not re-read the data unless we know how to create new input streams.
*/
switch(state) {
default:
throw new AssertionError(state);
case WRITING:
throw new ConcurrentWriteException(getLocale(), getDisplayName());
// Stream already at the data start; nothing to do.
case START:
break;
case FINISHED:
{
// If we can reuse existing stream, nothing more to do.
if (reset())
break;
if (input != null) {
// Cleared first in case of error during 'close()' call.
stream = null;
input.close();
input = null;
}
// Fall through for trying to create a new input stream.
}
case READING:
{
/*
* If the input stream is in use, or if we finished to use it but were unable to reset its position,
* then we need to create a new input stream (except if the input was a DOM in memory, which we can
* share). The 'target' StaxStreamReader will be in charge of closing that stream.
*/
if (type != InputType.NODE) {
final String name = getDisplayName();
if (channelFactory == null) {
throw new ForwardOnlyStorageException(getLocale(), name, StandardOpenOption.READ);
}
inputOrFile = input = channelFactory.inputStream(name, listeners);
type = InputType.STREAM;
if (stream == null) {
stream = input;
state = START;
mark();
}
}
break;
}
}
/*
* At this point we verified there is no write operation in progress and that the input stream (if not null)
* is available for our use. Now we need to build a XMLStreamReader from that input. This is InputType work,
* but that type may be null if the storage given by the user was not an InputStream, Reader or other types
* recognized by InputType. In such case there is two possibilities:
*
* - It may be an OutputStream, Writer or other types recognized by OutputType.
* - It may be a Path, File, URL or URI, which are intentionally not handled by Input/OutputType.
*/
if (type == null) {
if (storageToWriter != null) {
final Closeable snapshot = storageToWriter.snapshot(inputOrFile);
if (snapshot != null) {
// Do not set state to READING since the input in this block is a copy of data.
final XMLStreamReader reader = storageToWriter.inputType.create(this, snapshot);
target.stream = snapshot;
return reader;
}
}
/*
* Maybe that storage was a Path, File or URL, in which case the constructor should have opened an
* InputStream for it. If not, then this was an unsupported storage type. However the input stream
* may have been converted to an output stream during a write operation, in which case we need to
* convert it back to an input stream.
*/
type = InputType.STREAM;
input = IOUtilities.toInputStream(input);
if (input == null) {
throw new UnsupportedStorageException(getLocale(), getFormatName(), storage, StandardOpenOption.READ);
}
inputOrFile = input;
if (input != stream) {
stream = input;
mark();
}
}
final XMLStreamReader reader = type.create(this, inputOrFile);
target.stream = input;
state = READING;
return reader;
}
Aggregations