2016-05-16 4 views
3

Ich verwende Titan Transaktions-API, um Transaktionen in meinem Code zu behandeln. Es funktioniert gut,Probleme bei der Behandlung von asynchronen Transaktionen in TitanDB mit Scala Future

hier ist mein Code:

Synchrone Übertragung:

def syncTransaction()={ 

    val transaction = titanGraph.newTransaction 

    // doing some modification and query , creation vertex 

    transaction.commit() 
} 

ich oben Methode für 1000 anzurufenden Rekord persistence.It fein arbeitet.

Asynchronous Transaktion:

def aysncTransaction()= Future{ 

    val transaction = titanGraph.newTransaction 

    // doing some modification and query , creation vertex 

    transaction.commit() 
    } 

oben Code Wenn in Scala Zukunft (Scala Zukunft verwendet für nicht blockierende und asynchrone Codeausführung) gewickelt ist es wirft folgende Ausnahme:

[ERROR] - [2016-05-16 14:01:04,849] -   [com.thinkaurelius.titan.graphdb.database.StandardTitanGraph] Could not commit transaction [2] due to exception 
com.thinkaurelius.titan.diskstorage.locking.PermanentLockingException: Local lock contention 
    at com.thinkaurelius.titan.diskstorage.locking.AbstractLocker.writeLock(AbstractLocker.java:313) ~[titan-core-1.1.0-SNAPSHOT.jar:na] 
    at com.thinkaurelius.titan.diskstorage.locking.consistentkey.ExpectedValueCheckingStore.acquireLock(ExpectedValueCheckingStore.java:89) ~[titan-core-1.1.0-SNAPSHOT.jar:na] 
    at com.thinkaurelius.titan.diskstorage.keycolumnvalue.KCVSProxy.acquireLock(KCVSProxy.java:40) ~[titan-core-1.1.0-SNAPSHOT.jar:na] 
    at com.thinkaurelius.titan.diskstorage.BackendTransaction.acquireIndexLock(BackendTransaction.java:240) ~[titan-core-1.1.0-SNAPSHOT.jar:na] 
    at com.thinkaurelius.titan.graphdb.database.StandardTitanGraph.prepareCommit(StandardTitanGraph.java:554) ~[titan-core-1.1.0-SNAPSHOT.jar:na] 
    at com.thinkaurelius.titan.graphdb.database.StandardTitanGraph.commit(StandardTitanGraph.java:683) ~[titan-core-1.1.0-SNAPSHOT.jar:na] 
    at com.thinkaurelius.titan.graphdb.transaction.StandardTitanTx.commit(StandardTitanTx.java:1352) [titan-core-1.1.0-SNAPSHOT.jar:na] 
    at com.freebird.titan.connect.GraphFactory$class.withTransaction(GraphFactory.scala:25) [classes/:na] 
    at com.freebird.oag.ingestion.TitanDBPersistentActorImpl.withTransaction(TitanDBPersistentActor.scala:25) [classes/:na] 
    at com.freebird.titan.connect.GraphFactory$$anonfun$withAsyncTransaction$1.apply(GraphFactory.scala:17) [classes/:na] 
    at scala.concurrent.impl.Future$PromiseCompletingRunnable.liftedTree1$1(Future.scala:24) [scala-library-2.11.7.jar:na] 
    at scala.concurrent.impl.Future$PromiseCompletingRunnable.run(Future.scala:24) [scala-library-2.11.7.jar:na] 
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) [na:1.8.0_77] 
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) [na:1.8.0_77] 
    at java.lang.Thread.run(Thread.java:745) [na:1.8.0_77] 

kann jeder Bitte sag mir, was ich hier falsch mache. Jede Hilfe wird geschätzt. Danke

Antwort

-1

Ich benutze keine dieser Tools (neben Scala), aber ich würde vermuten, dass dies ein ähnliches Problem mit Code ist, der eigentlich nicht gezeigt wird und wie 'NewTransaction' tatsächlich funktioniert. Gibt es implizit, dass titanGraph verwendet? Ist titanGraph Objekt eine Sitzung? Gibt es ein ähnliches Sitzungskonzept?

Wenn das so ist, dann können Sitzungen oder sitzungsähnliche (wie Verbindungen) Futures nicht kreuzen, weil Sie den Job im Wesentlichen einem anderen Thread geben und eine Menge Session wie Magie tatsächlich mit dem Threadlocal der JVM passiert.

EDIT: Mit Blick auf die Stack-Trace sieht es auch aus wie die parallelen Transaktionen (Sperrkonflikt) passieren, da es in eine Zukunft verpackt ist, da sie jetzt in der Zukunft parallel laufen können , während vorher, ohne die Zukunft, sie seriell liefen.

0

Meiner Erfahrung nach tritt dies auf, weil mehr als ein Thread denselben Scheitelpunkt oder dieselbe Kante mutiert. Vom Titan Docs:

PermanentLockingException (Local Lock-Conten): Ein weiterer örtlicher Thread hat bereits eine widersprüchliche Sperre erteilt worden.

Ich würde empfehlen zu tun, was Titan empfiehlt, die Transaktion einfach mehrmals wiederholt werden soll. Dies variiert natürlich von einem Anwendungsfall zum anderen. bilden wieder die Titan Docs:

try { 
    if (g.V().has("name", name).iterator().hasNext()) 
    throw new IllegalArgumentException("Username already taken: " + name) 
    user = graph.addVertex() 
    user.property("name", name) 
    graph.tx().commit() 
} catch (Exception e) { 
    //Recover, retry, or return error message 
    println(e.getMessage()) 
} 

Titan selbst gesagt haben:

Tatsächlich Transaktionen wird schließlich in ausreichend großen Systeme versagen.

Verwandte Themen