use of org.exist.util.LockException in project exist by eXist-db.
the class MutableCollection method storeDocument.
@Override
public void storeDocument(final Txn transaction, final DBBroker broker, final XmldbURI name, final InputSource source, @Nullable MimeType mimeType, @Nullable final Date createdDate, @Nullable final Date lastModifiedDate, @Nullable final Permission permission, @Nullable final DocumentType documentType, @Nullable final XMLReader xmlReader) throws EXistException, PermissionDeniedException, SAXException, LockException, IOException {
if (mimeType == null) {
mimeType = MimeType.BINARY_TYPE;
}
if (mimeType.isXMLType()) {
// Store XML Document
final BiConsumer2E<XMLReader, IndexInfo, SAXException, EXistException> validatorFn = (xmlReader1, validateIndexInfo) -> {
validateIndexInfo.setReader(xmlReader1, null);
try {
xmlReader1.parse(source);
} catch (final SAXException e) {
throw new SAXException("The XML parser reported a problem: " + e.getMessage(), e);
} catch (final IOException e) {
throw new EXistException(e);
}
};
final BiConsumer2E<XMLReader, IndexInfo, SAXException, EXistException> parserFn = (xmlReader1, storeIndexInfo) -> {
try {
storeIndexInfo.setReader(xmlReader1, null);
xmlReader1.parse(source);
} catch (final IOException e) {
throw new EXistException(e);
}
};
storeXmlDocument(transaction, broker, name, mimeType, createdDate, lastModifiedDate, permission, documentType, xmlReader, validatorFn, parserFn);
} else {
// Store Binary Document
try (final InputStream is = source.getByteStream()) {
if (is == null) {
throw new IOException("storeDocument received a null InputStream when trying to store a Binary Document");
}
addBinaryResource(transaction, broker, name, is, mimeType.getName(), -1, createdDate, lastModifiedDate, permission);
}
}
}
use of org.exist.util.LockException in project exist by eXist-db.
the class MutableCollection method setPath.
@Override
public final void setPath(XmldbURI path, final boolean updateChildren) {
path = path.toCollectionPathURI();
// TODO : see if the URI resolves against DBBroker.TEMP_COLLECTION
this.isTempCollection = path.getRawCollectionPath().equals(XmldbURI.TEMP_COLLECTION);
this.path = path;
if (updateChildren) {
for (final Map.Entry<String, DocumentImpl> docEntry : documents.entrySet()) {
final XmldbURI docUri = path.append(docEntry.getKey());
try (final ManagedDocumentLock documentLock = lockManager.acquireDocumentWriteLock(docUri)) {
final DocumentImpl doc = docEntry.getValue();
// this will invalidate the cached `uri` in DocumentImpl
doc.setCollection(this);
} catch (final LockException e) {
LOG.error(e.getMessage(), e);
throw new IllegalStateException(e);
}
}
}
}
use of org.exist.util.LockException in project exist by eXist-db.
the class Configurator method save.
public static DocumentImpl save(final Configurable instance, final DBBroker broker, final Collection collection, final XmldbURI uri) throws IOException, ConfigurationException {
final StringWriter writer = new StringWriter();
final SAXSerializer serializer = new SAXSerializer(writer, null);
try {
serializer.startDocument();
serialize(instance, serializer);
serializer.endDocument();
} catch (final SAXException saxe) {
throw new ConfigurationException(saxe.getMessage(), saxe);
}
final String data = writer.toString();
if (data == null || data.length() == 0) {
return null;
}
FullXmldbURI fullURI = null;
final BrokerPool pool = broker.getBrokerPool();
final TransactionManager transact = pool.getTransactionManager();
LOG.info("Storing configuration {}/{}", collection.getURI(), uri);
final SecurityManager securityManager = pool.getSecurityManager();
try {
final Subject systemSubject = securityManager.getSystemSubject();
broker.pushSubject(systemSubject);
Txn txn = broker.getCurrentTransaction();
final boolean txnInProgress = txn != null;
if (!txnInProgress) {
txn = transact.beginTransaction();
}
try {
txn.acquireCollectionLock(() -> pool.getLockManager().acquireCollectionWriteLock(collection.getURI()));
fullURI = getFullURI(pool, collection.getURI().append(uri));
saving.add(fullURI);
final Permission systemResourcePermission = PermissionFactory.getDefaultResourcePermission(pool.getSecurityManager());
systemResourcePermission.setOwner(systemSubject);
systemResourcePermission.setGroup(systemSubject.getDefaultGroup());
systemResourcePermission.setMode(Permission.DEFAULT_SYSTEM_RESOURCE_PERM);
broker.storeDocument(txn, uri, new StringInputSource(data), MimeType.XML_TYPE, null, null, systemResourcePermission, null, null, collection);
broker.saveCollection(txn, collection);
if (!txnInProgress) {
transact.commit(txn);
}
} catch (final EXistException | PermissionDeniedException | SAXException | LockException e) {
if (!txnInProgress) {
transact.abort(txn);
}
throw e;
} finally {
if (!txnInProgress) {
txn.close();
}
}
saving.remove(fullURI);
broker.flush();
broker.sync(Sync.MAJOR);
return collection.getDocument(broker, uri.lastSegment());
} catch (final EXistException | PermissionDeniedException | SAXException | LockException e) {
LOG.error(e);
if (fullURI != null) {
saving.remove(fullURI);
}
throw new IOException(e);
} finally {
broker.popSubject();
}
}
use of org.exist.util.LockException in project exist by eXist-db.
the class NodeIterator method next.
/**
* Returns the next node in document order.
*/
@Override
public IStoredNode next() {
try (final ManagedLock<ReentrantLock> domFileLock = lockManager.acquireBtreeReadLock(db.getLockName())) {
db.setOwnerObject(broker);
IStoredNode nextNode = null;
if (gotoNextPosition()) {
long backLink = 0;
do {
final DOMFile.DOMFilePageHeader pageHeader = page.getPageHeader();
// Next value larger than length of the current page?
if (offset >= pageHeader.getDataLength()) {
// Load next page in chain
long nextPageNum = pageHeader.getNextDataPage();
if (nextPageNum == Page.NO_PAGE) {
SanityCheck.TRACE("bad link to next " + page.page.getPageInfo() + "; previous: " + pageHeader.getPreviousDataPage() + "; offset = " + offset + "; lastTupleID = " + lastTupleID);
if (LOG.isDebugEnabled()) {
LOG.debug(db.debugPageContents(page));
}
// TODO : throw exception here ? -pb
return null;
}
pageNum = nextPageNum;
page = db.getDOMPage(nextPageNum);
db.addToBuffer(page);
offset = 0;
}
// Extract the tuple ID
lastTupleID = ByteConversion.byteToShort(page.data, offset);
offset += DOMFile.LENGTH_TID;
// Check if this is just a link to a relocated node
if (ItemId.isLink(lastTupleID)) {
// Skip this
offset += DOMFile.LENGTH_FORWARD_LOCATION;
// Continue the iteration
continue;
}
// Read data length
short vlen = ByteConversion.byteToShort(page.data, offset);
offset += DOMFile.LENGTH_DATA_LENGTH;
if (vlen < 0) {
LOG.error("Got negative length{} at offset {}!!!", vlen, offset);
if (LOG.isDebugEnabled()) {
LOG.debug(db.debugPageContents(page));
}
// TODO : throw an exception right now ?
}
if (ItemId.isRelocated(lastTupleID)) {
// Found a relocated node. Read the original address
backLink = ByteConversion.byteToLong(page.data, offset);
offset += DOMFile.LENGTH_ORIGINAL_LOCATION;
}
// Overflow page? Load the overflow value
if (vlen == DOMFile.OVERFLOW) {
vlen = DOMFile.LENGTH_OVERFLOW_LOCATION;
final long overflow = ByteConversion.byteToLong(page.data, offset);
offset += DOMFile.LENGTH_OVERFLOW_LOCATION;
try {
final byte[] overflowValue = db.getOverflowValue(overflow);
nextNode = StoredNode.deserialize(overflowValue, 0, overflowValue.length, doc, useNodePool);
} catch (final Exception e) {
LOG.warn("Exception while loading overflow value: {}; originating page: {}", e.getMessage(), page.page.getPageInfo());
// TODO : rethrow exception ? -pb
}
// Normal node
} else {
try {
nextNode = StoredNode.deserialize(page.data, offset, vlen, doc, useNodePool);
offset += vlen;
} catch (final Exception e) {
LOG.error("Error while deserializing node: {}", e.getMessage(), e);
LOG.error("Reading from offset: {}; len = {}", offset, vlen);
if (LOG.isDebugEnabled()) {
LOG.debug(db.debugPageContents(page));
}
throw new RuntimeException(e);
}
}
if (nextNode == null) {
LOG.error("illegal node on page {}; tid = {}; next = {}; prev = {}; offset = {}; len = {}", page.getPageNum(), ItemId.getId(lastTupleID), page.getPageHeader().getNextDataPage(), page.getPageHeader().getPreviousDataPage(), offset - vlen, page.getPageHeader().getDataLength());
if (LOG.isDebugEnabled()) {
LOG.debug(db.debugPageContents(page));
}
// TODO : throw an exception here ? -pb
return null;
}
if (ItemId.isRelocated(lastTupleID)) {
nextNode.setInternalAddress(backLink);
} else {
nextNode.setInternalAddress(StorageAddress.createPointer((int) pageNum, ItemId.getId(lastTupleID)));
}
nextNode.setOwnerDocument(doc);
} while (nextNode == null);
}
return nextNode;
} catch (final LockException e) {
LOG.warn("Failed to acquire read lock on {}", FileUtils.fileName(db.getFile()));
// TODO : throw exception here ? -pb
return null;
} catch (final BTreeException | IOException e) {
LOG.error(e.getMessage(), e);
// TODO : re-throw exception ? -pb
}
return null;
}
use of org.exist.util.LockException in project exist by eXist-db.
the class RawNodeIterator method next.
@Override
public Value next() {
Value nextValue = null;
try (final ManagedLock<ReentrantLock> domFileLock = lockManager.acquireBtreeReadLock(db.getLockName())) {
db.setOwnerObject(broker);
long backLink = 0;
do {
final DOMFile.DOMFilePageHeader pageHeader = page.getPageHeader();
// Next value larger than length of the current page?
if (offset >= pageHeader.getDataLength()) {
// Load next page in chain
long nextPage = pageHeader.getNextDataPage();
if (nextPage == Paged.Page.NO_PAGE) {
SanityCheck.TRACE("Bad link to next page " + page.page.getPageInfo() + "; previous: " + pageHeader.getPreviousDataPage() + "; offset = " + offset + "; lastTupleID = " + lastTupleID);
// TODO : throw exception here ? -pb
return null;
}
pageNum = nextPage;
page = db.getDOMPage(nextPage);
db.addToBuffer(page);
offset = 0;
}
// Extract the tuple id
lastTupleID = ByteConversion.byteToShort(page.data, offset);
offset += DOMFile.LENGTH_TID;
// Check if this is just a link to a relocated node
if (ItemId.isLink(lastTupleID)) {
// Skip this
offset += DOMFile.LENGTH_FORWARD_LOCATION;
continue;
}
// Read data length
short valueLength = ByteConversion.byteToShort(page.data, offset);
offset += DOMFile.LENGTH_DATA_LENGTH;
if (valueLength < 0) {
LOG.error("Got negative length{} at offset {}!!!", valueLength, offset);
LOG.debug(db.debugPageContents(page));
// TODO : throw an exception right now ?
}
if (ItemId.isRelocated(lastTupleID)) {
// found a relocated node. Read the original address
backLink = ByteConversion.byteToLong(page.data, offset);
offset += DOMFile.LENGTH_ORIGINAL_LOCATION;
}
// Overflow page? load the overflow value
if (valueLength == DOMFile.OVERFLOW) {
valueLength = DOMFile.LENGTH_OVERFLOW_LOCATION;
final long overflow = ByteConversion.byteToLong(page.data, offset);
offset += DOMFile.LENGTH_OVERFLOW_LOCATION;
try {
final byte[] odata = db.getOverflowValue(overflow);
nextValue = new Value(odata);
} catch (final Exception e) {
LOG.error("Exception while loading overflow value: {}; originating page: {}", e.getMessage(), page.page.getPageInfo());
}
// normal node
} else {
try {
nextValue = new Value(page.data, offset, valueLength);
offset += valueLength;
} catch (final Exception e) {
LOG.error("Error while deserializing node: {}", e.getMessage(), e);
LOG.error("Reading from offset: {}; len = {}", offset, valueLength);
LOG.debug(db.debugPageContents(page));
throw new RuntimeException(e);
}
}
if (nextValue == null) {
LOG.error("illegal node on page {}; tupleID = {}; next = {}; prev = {}; offset = {}; len = {}", page.getPageNum(), ItemId.getId(lastTupleID), page.getPageHeader().getNextDataPage(), page.getPageHeader().getPreviousDataPage(), offset - valueLength, page.getPageHeader().getDataLength());
// TODO : throw exception here ? -pb
return null;
}
if (ItemId.isRelocated(lastTupleID)) {
nextValue.setAddress(backLink);
} else {
nextValue.setAddress(StorageAddress.createPointer((int) pageNum, ItemId.getId(lastTupleID)));
}
} while (nextValue == null);
return nextValue;
} catch (final LockException e) {
LOG.error("Failed to acquire read lock on {}", FileUtils.fileName(db.getFile()));
// TODO : throw exception here ? -pb
return null;
}
}
Aggregations