The basic concept is that you are getting a deadlock due to an open transaction 
holding a lock.

I don't have enough scope of your code to say where exactly,
but use of 'multi statement transactions' (which is what the Transaction object 
represents) is an 'advanced' feature even when short lived in the scope of one 
function.  The code snippets shown have many places where transactions could be 
conceivably 'lost' or held open for longer duration than expected.  I would not 
recommend caching Transaction objects, its very difficult to guarantee the 
lifecycle if they the object references are stored anywhere but as local 
variables or parameters.  Even more difficult with Java and other GC based 
languages.

Reading this guide will help understanding the correct use of multistatement 
transactions

https://docs.marklogic.com/guide/app-dev/transactions

I recommend first isolating the code so that transactions are not cached,
ideally not used at all unless absolutely needed.

The code snippet as shown doesn't need a transaction, document writes are 
always transactional and will be handled properly in the server. For 
programmers with experience with  other databases this can be counter-intuitive.

Explicitly creating Transitions creates a 'multi statement' transaction which 
is much more complex to manage properly, especially  in a client/server 
environment where the server has no ability to manage exceptions, references 
etc for you.




-----------------------------------------------------------------------------
David Lee
Lead Engineer
MarkLogic Corporation
[email protected]
Phone: +1 812-482-5224
Cell:  +1 812-630-7622
www.marklogic.com<http://www.marklogic.com/>

From: [email protected] 
[mailto:[email protected]] On Behalf Of 
[email protected]
Sent: Tuesday, August 18, 2015 8:05 AM
To: [email protected]
Subject: Re: [MarkLogic Dev General] Server Message: SVC-EXTIME: 
xdmp:lock-for-update("/docs/0f04c4fb-6058-4758-92eb-f9cfa2ea18bc") -- Time 
limit exceeded.

Hi Team,
Just want add few more info. We are sometimes getting below errors as well.

Java Layer:
com.marklogic.client.FailedRequestException: Local message: transaction 
rollback failed: Bad Request. Server Message: XDMP-NOTXN: 
xdmp:xa-complete1(xs:unsignedLong("5231619190085809367"), 
xs:unsignedLong("13101616944000907690"), fn:false()) -- No transaction with 
identifier 13101616944000907690
       at 
com.marklogic.client.impl.JerseyServices.completeTransaction(JerseyServices.java:1488)
       at 
com.marklogic.client.impl.JerseyServices.rollbackTransaction(JerseyServices.java:1420)
       at 
com.marklogic.client.impl.TransactionImpl.rollback(TransactionImpl.java:70)


MarkLogic Log:
2015-08-18 15:39:24.551 Info: REST-ContentStore: Status 500: XDMP-NOTXN: 
xdmp:invoke("/MarkLogic/rest-api/lib/transaction-runner-update.xqy", 
(as:QName("", "method"), "PUT", as:QName("", "headers"), ...), <options 
xmlns="xdmp:eval"><transaction-id>13101616944000907690</transaction-id></options>)
 -- No transaction with identifier 13101616944000907690
2015-08-18 15:39:25.347 Info: REST-ContentStore: Status 500: XDMP-NOTXN: 
xdmp:xa-complete1(xs:unsignedLong("5231619190085809367"), 
xs:unsignedLong("13101616944000907690"), fn:false()) -- No transaction with 
identifier 13101616944000907690

Regards,
Abhinav
From: Mishra, Abhinav Kumar (Cognizant)
Sent: Tuesday, August 18, 2015 12:24 PM
To: [email protected]<mailto:[email protected]>
Subject: Server Message: SVC-EXTIME: 
xdmp:lock-for-update("/docs/0f04c4fb-6058-4758-92eb-f9cfa2ea18bc") -- Time 
limit exceeded.

Hi Team,
We are running into an issue, where in we are getting exception from MarkLogic 
as given below:

"write failed: Internal Server Error. Server Message: SVC-EXTIME: 
xdmp:lock-for-update("/docs/0f04c4fb-6058-4758-92eb-f9cfa2ea18bc") -- Time 
limit exceeded."

But In MarkLogic logs I don't see any log for the above statement. I have 
enabled log to debug mode on MarkLogic as well. We are not sure what is the 
exact reason of this failure.
I would really appreciate if you can provide some clues.

Now let me explain what we are doing..

We are saving xml documents to MarkLogic from a java based application. We have 
used MarkLogic' s OOTB REST Java Client API. It will internally use 
"/documents" service via PUT request.
I have highlighted the RESTServices.putDocument(..) method below which will 
actually put the documents to MarkLogic.
We are opening the transaction, saving document to MarkLogic and then closing 
the transaction.


Code snippet:

   //rest-user has all the privileges required to load the documents in 
MarkLogic.
      DatabaseClient client = DatabaseClientFactory.newClient("<somehost>", 
8004,rest-user, rest-user-password, Authentication.DIGEST);
      Transaction transaction = client.openTransaction();

        try {
          //Here we are sending following parameters from outside, "[String 
path, InputStream is, Transaction transaction, String collection]"
        //Where, path="/docs/0f04c4fb-6058-4758-92eb-f9cfa2ea18bc"
     // InputStream will have the xml document as a stream
    // transaction is the implementation of com.marklogic.clinet.Transaction
    // collection = "doc-versions"


         TransactionPoolableFactory transactionFactory = new 
TransactionPoolableFactory();
         GenericKeyedObjectPool<Transaction, DatabaseClient> transactionPool = 
new GenericKeyedObjectPool<Transaction, DatabaseClient>(transactionFactory);
         transactionPool.setTestOnReturn(true);
            DatabaseClient client = transactionPool.borrowObject(transaction);
            InputStreamHandle handle = new InputStreamHandle(is);
            DocumentMetadataHandle metadata = new DocumentMetadataHandle();
            metadata.getCollections().addAll(collection);
            DocumentManager<XMLReadHandle, XMLWriteHandle> docMgr = 
client.newXMLDocumentManager();
            docMgr.write(path, metadata, handle, transaction);
           transactionPool.returnObject(transaction, client);

       transaction.commit();
        try {
            DatabaseClient client = transactionPool.borrowObject(transaction);
            transactionPool.invalidateObject(transaction, client);
        } catch (Exception e) {
            throw new MarkLogicException(e.getMessage(), e);
        }

        } catch (Exception e) {
            e.printStackTrace();

                transaction.rollback();
        try {
            DatabaseClient client = transactionPool.borrowObject(transaction);
            transactionPool.invalidateObject(transaction, client);
       } catch (Exception e) {
            throw new MarkLogicException(e.getMessage(), e);
        }
        }


The highlighted "write" method is the implementation of DocumentManager 
interface, see the snippet below:

Interface:
package com.marklogic.client.document;

import com.marklogic.client.FailedRequestException;
import com.marklogic.client.ForbiddenUserException;
import com.marklogic.client.ResourceNotFoundException;
import com.marklogic.client.Transaction;
import com.marklogic.client.io.Format;
import com.marklogic.client.io.marker.AbstractReadHandle;
import com.marklogic.client.io.marker.AbstractWriteHandle;
import com.marklogic.client.io.marker.DocumentMetadataReadHandle;
import com.marklogic.client.io.marker.DocumentMetadataWriteHandle;
import com.marklogic.client.io.marker.DocumentPatchHandle;
import com.marklogic.client.util.RequestLogger;
import java.util.Set;

public abstract interface DocumentManager<R extends AbstractReadHandle, W 
extends AbstractWriteHandle> {
.....
.....
public abstract void write(String paramString,
                                                DocumentMetadataWriteHandle 
paramDocumentMetadataWriteHandle,
                                                W paramW, Transaction 
paramTransaction)
                                                throws 
ResourceNotFoundException, ForbiddenUserException,
                                                FailedRequestException;

.....
.....
....
.
}

Implementation:

package com.marklogic.client.impl;

import com.marklogic.client.DatabaseClientFactory.HandleFactoryRegistry;
import com.marklogic.client.FailedRequestException;
import com.marklogic.client.ForbiddenUserException;
import com.marklogic.client.ResourceNotFoundException;
import com.marklogic.client.Transaction;
import com.marklogic.client.document.DocumentDescriptor;
import com.marklogic.client.document.DocumentManager;
import com.marklogic.client.document.DocumentManager.Metadata;
import com.marklogic.client.document.DocumentMetadataPatchBuilder;
import com.marklogic.client.document.DocumentUriTemplate;
import com.marklogic.client.document.ServerTransform;
import com.marklogic.client.io.Format;
import com.marklogic.client.io.marker.AbstractReadHandle;
import com.marklogic.client.io.marker.AbstractWriteHandle;
import com.marklogic.client.io.marker.ContentHandle;
import com.marklogic.client.io.marker.DocumentMetadataReadHandle;
import com.marklogic.client.io.marker.DocumentMetadataWriteHandle;
import com.marklogic.client.io.marker.DocumentPatchHandle;
import com.marklogic.client.util.RequestParameters;
import java.util.HashSet;
import java.util.Set;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

abstract class DocumentManagerImpl<R extends AbstractReadHandle, W extends 
AbstractWriteHandle>
                                extends AbstractLoggingManager implements 
DocumentManager<R, W> {
                private static final Logger logger = LoggerFactory
                                                
.getLogger(DocumentManagerImpl.class);
                private final Set<DocumentManager.Metadata> processedMetadata;
                private RESTServices services;
                private Format contentFormat;
                private DatabaseClientFactory.HandleFactoryRegistry 
handleRegistry;
                private ServerTransform readTransform;
                private ServerTransform writeTransform;
                private String forestName;

                DocumentManagerImpl(RESTServices services, Format 
contentFormat) {
                                HashSet metadata = new HashSet();
                                metadata.add(DocumentManager.Metadata.ALL);
                                this.processedMetadata = metadata;

                                this.services = services;
                                this.contentFormat = contentFormat;
                }

                RESTServices getServices() {
                                return this.services;
                }

                void setServices(RESTServices services) {
                                this.services = services;
                }

                DatabaseClientFactory.HandleFactoryRegistry getHandleRegistry() 
{
                                return this.handleRegistry;
                }

.....
.....
....
.

public void write(String uri, DocumentMetadataWriteHandle metadataHandle,
                                                W contentHandle, Transaction 
transaction)
                                                throws 
ResourceNotFoundException, ForbiddenUserException,
                                                FailedRequestException {
                                write(uri, metadataHandle, contentHandle, null, 
transaction,
                                                                
getWriteParams());
                }

.....
.....
public void write(DocumentDescriptor desc,
                                                DocumentMetadataWriteHandle 
metadataHandle, W contentHandle,
                                                ServerTransform transform, 
Transaction transaction,
                                                RequestParameters extraParams) 
throws ResourceNotFoundException,
                                                ForbiddenUserException, 
FailedRequestException {
                                if (desc == null) {
                                                throw new 
IllegalArgumentException(
                                                                                
"Writing document with null identifier");
                                }
                                if (logger.isInfoEnabled()) {
                                                logger.info("Writing content 
for {}", desc.getUri());
                                }
                                if (metadataHandle != null) {
                                                HandleImplementation 
metadataBase = HandleAccessor.checkHandle(
                                                                                
metadataHandle, "metadata");
                                                Format metadataFormat = 
metadataBase.getFormat();
                                                if ((metadataFormat == null)
                                                                                
|| ((metadataFormat != Format.JSON) && (metadataFormat != Format.XML))) {
                                                                if 
(logger.isWarnEnabled())
                                                                                
logger.warn("Unsupported metadata format {}, using XML",
                                                                                
                                metadataFormat.name());
                                                                
metadataBase.setFormat(Format.XML);
                                                }
                                }

                                checkContentFormat(contentHandle);

                                this.services.putDocument(
                                                                
this.requestLogger,
                                                                desc,
                                                                (transaction == 
null) ? null : transaction.getTransactionId(),
                                                                (metadataHandle 
!= null) ? this.processedMetadata : null,
                                                                
mergeTransformParameters((transform != null) ? transform
                                                                                
                : getWriteTransform(), extraParams), metadataHandle,
                                                                contentHandle);
                }
....
.

}

Regards,
Abhinav
This e-mail and any files transmitted with it are for the sole use of the 
intended recipient(s) and may contain confidential and privileged information. 
If you are not the intended recipient(s), please reply to the sender and 
destroy all copies of the original message. Any unauthorized review, use, 
disclosure, dissemination, forwarding, printing or copying of this email, 
and/or any action taken in reliance on the contents of this e-mail is strictly 
prohibited and may be unlawful. Where permitted by applicable law, this e-mail 
and other e-mail communications sent to and from Cognizant e-mail addresses may 
be monitored.
_______________________________________________
General mailing list
[email protected]
Manage your subscription at: 
http://developer.marklogic.com/mailman/listinfo/general

Reply via email to