Exist: History trigger fails

Created on 31 Jan 2014  路  10Comments  路  Source: eXist-db/exist

Current (pull #128) develop branch:

| General | |
| --- | --- |
| Uptime: | PT49M2.568S |
| eXist Version: | 2.1 |
| eXist Build: | 20140131 |
| eXist Home: | C:exist |
| SVN Revision: | |
| Operating System: | Windows 7 6.1 amd64 |
| File encoding: | UTF-8 |

| Java | |
| --- | --- |
| Vendor: | Oracle Corporation |
| Version: | 1.7.0_51 |
| Implementation: | Java HotSpot(TM) 64-Bit Server VM |
| Installation: | C:Javajre7 |
| Temp file path: | C:existtoolsjetty/tmp |

| Memory Usage | |
| --- | --- |
| Max. Memory: | 932352K |
| Current Total: | 357376K |
| Free: | 153699K |

Added a HistoryTrigger and received a Stack Overflow error:

2014-01-31 09:41:13,555 [eXistThread-61] DEBUG (RpcConnection.java [handleException]:124) -  
java.lang.StackOverflowError
    at sun.misc.Unsafe.putInt(Native Method)
    at java.nio.DirectByteBuffer.putInt(Unknown Source)
    at java.nio.DirectByteBuffer.putInt(Unknown Source)
    at org.exist.storage.btree.UpdateValueLoggable.write(UpdateValueLoggable.java:73)
    at org.exist.storage.journal.Journal.writeToLog(Journal.java:244)
    at org.exist.storage.btree.BTree.writeToLog(BTree.java:759)
    at org.exist.storage.btree.BTree.access$2(BTree.java:757)
    at org.exist.storage.btree.BTree$BTreeNode.addValue(BTree.java:1424)
    at org.exist.storage.btree.BTree$BTreeNode.addValue(BTree.java:1414)
    at org.exist.storage.btree.BTree$BTreeNode.access$0(BTree.java:1406)
    at org.exist.storage.btree.BTree.addValue(BTree.java:272)
    at org.exist.storage.index.BFile.update(BFile.java:986)
    at org.exist.storage.index.BFile.update(BFile.java:934)
    at org.exist.storage.index.BFile.put(BFile.java:692)
    at org.exist.storage.NativeBroker.saveCollection(NativeBroker.java:1646)
    at org.exist.collections.triggers.HistoryTrigger.makeCopy(HistoryTrigger.java:101)
    at org.exist.collections.triggers.HistoryTrigger.beforeCopyDocument(HistoryTrigger.java:143)
    at org.exist.collections.triggers.DocumentTriggersVisitor.beforeCopyDocument(DocumentTriggersVisitor.java:86)
    at org.exist.storage.NativeBroker.copyResource(NativeBroker.java:2509)
    at org.exist.collections.triggers.HistoryTrigger.makeCopy(HistoryTrigger.java:102)
    at org.exist.collections.triggers.HistoryTrigger.beforeCopyDocument(HistoryTrigger.java:143)
    at org.exist.collections.triggers.DocumentTriggersVisitor.beforeCopyDocument(DocumentTriggersVisitor.java:86)
    at org.exist.storage.NativeBroker.copyResource(NativeBroker.java:2509)
    at org.exist.collections.triggers.HistoryTrigger.makeCopy(HistoryTrigger.java:102)
    at org.exist.collections.triggers.HistoryTrigger.beforeCopyDocument(HistoryTrigger.java:143)
    at org.exist.collections.triggers.DocumentTriggersVisitor.beforeCopyDocument(DocumentTriggersVisitor.java:86)
    at org.exist.storage.NativeBroker.copyResource(NativeBroker.java:2509)
    at org.exist.collections.triggers.HistoryTrigger.makeCopy(HistoryTrigger.java:102)
    at org.exist.collections.triggers.HistoryTrigger.beforeCopyDocument(HistoryTrigger.java:143)
    at org.exist.collections.triggers.DocumentTriggersVisitor.beforeCopyDocument(DocumentTriggersVisitor.java:86)
    at org.exist.storage.NativeBroker.copyResource(NativeBroker.java:2509)
    at org.exist.collections.triggers.HistoryTrigger.makeCopy(HistoryTrigger.java:102)
    at org.exist.collections.triggers.HistoryTrigger.beforeCopyDocument(HistoryTrigger.java:143)
    at org.exist.collections.triggers.DocumentTriggersVisitor.beforeCopyDocument(DocumentTriggersVisitor.java:86)
    at org.exist.storage.NativeBroker.copyResource(NativeBroker.java:2509)
    at org.exist.collections.triggers.HistoryTrigger.makeCopy(HistoryTrigger.java:102)
    at org.exist.collections.triggers.HistoryTrigger.beforeCopyDocument(HistoryTrigger.java:143)
    at org.exist.collections.triggers.DocumentTriggersVisitor.beforeCopyDocument(DocumentTriggersVisitor.java:86)
    at org.exist.storage.NativeBroker.copyResource(NativeBroker.java:2509)
    at org.exist.collections.triggers.HistoryTrigger.makeCopy(HistoryTrigger.java:102)
    at org.exist.collections.triggers.HistoryTrigger.beforeCopyDocument(HistoryTrigger.java:143)
    at 
.
.
.
org.exist.collections.triggers.DocumentTriggersVisitor.beforeCopyDocument(DocumentTriggersVisitor.java:86)
    at org.exist.storage.NativeBroker.copyResource(NativeBroker.java:2509)
    at org.exist.collections.triggers.HistoryTrigger.makeCopy(HistoryTrigger.java:102)
    at org.exist.collections.triggers.HistoryTrigger.beforeCopyDocument(HistoryTrigger.java:143)
    at org.exist.collections.triggers.DocumentTriggersVisitor.beforeCopyDocument(DocumentTriggersVisitor.java:86)
    at org.exist.storage.NativeBroker.copyResource(NativeBroker.java:2509)
    at org.exist.collections.triggers.HistoryTrigger.makeCopy(HistoryTrigger.java:102)
bug

All 10 comments

Do you take test or steps that/to reproduce issue?

I just made a change to the documentation within an XML Schema and saved the schema from within oXygenXML. oXygen is configured to communicate with eXist through XML RPC.

I see that you use versioning ... to give you anything back you must provide much more information.

I switched to versioning due to the history bug. This is how to configure the history trigger:

http://exist-db.org/exist/apps/doc/triggers.xml#D2.2.8.3

<collection xmlns='http://exist-db.org/collection-config/1.0'>
     <triggers>
       <trigger class="org.exist.collections.triggers.HistoryTrigger"/>
     </triggers>
</collection>

@lcahlander, I can't reproduce this by information you provide -(

Hi,
I have this issue, too.
my config is (/db/system/config/db/collection.xconf):

<collection xmlns='http://exist-db.org/collection-config/1.0'>
     <triggers>
       <trigger class="org.exist.collections.triggers.HistoryTrigger"/>
     </triggers>
</collection>

when i change a document and save it, receive error (mentioned at top of page) and logs are:

2015-08-03 18:58:55,171 [eXistThread-32] ERROR (XmlRpcErrorLogger.java [log]:36) - Failed to invoke method moveResource in class org.exist.xmlrpc.RpcConnection: null 
org.apache.xmlrpc.common.XmlRpcInvocationException: Failed to invoke method moveResource in class org.exist.xmlrpc.RpcConnection: null
    at org.apache.xmlrpc.server.ReflectiveXmlRpcHandler.invoke(ReflectiveXmlRpcHandler.java:129) ~[xmlrpc-server-3.1.3.jar:3.1.3]
    at org.apache.xmlrpc.server.ReflectiveXmlRpcHandler.execute(ReflectiveXmlRpcHandler.java:106) ~[xmlrpc-server-3.1.3.jar:3.1.3]
    at org.apache.xmlrpc.server.XmlRpcServerWorker.execute(XmlRpcServerWorker.java:46) ~[xmlrpc-server-3.1.3.jar:3.1.3]
    at org.apache.xmlrpc.server.XmlRpcServer.execute(XmlRpcServer.java:86) ~[xmlrpc-server-3.1.3.jar:3.1.3]
    at org.apache.xmlrpc.server.XmlRpcStreamServer.execute(XmlRpcStreamServer.java:200) [xmlrpc-server-3.1.3.jar:3.1.3]
    at org.apache.xmlrpc.webserver.XmlRpcServletServer.execute(XmlRpcServletServer.java:112) [xmlrpc-server-3.1.3.jar:3.1.3]
    at org.apache.xmlrpc.webserver.XmlRpcServlet.doPost(XmlRpcServlet.java:196) [xmlrpc-server-3.1.3.jar:3.1.3]
    at org.exist.xmlrpc.RpcServlet.doPost(RpcServlet.java:67) [exist.jar:?]
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:755) [servlet-api-3.0.jar:?]
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:848) [servlet-api-3.0.jar:?]
    at org.eclipse.jetty.servlet.ServletHolder.handle(ServletHolder.java:684) [jetty-servlet-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.servlet.ServletHandler.doHandle(ServletHandler.java:503) [jetty-servlet-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:137) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.security.SecurityHandler.handle(SecurityHandler.java:575) [jetty-security-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.session.SessionHandler.doHandle(SessionHandler.java:231) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.handler.ContextHandler.doHandle(ContextHandler.java:1086) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.servlet.ServletHandler.doScope(ServletHandler.java:429) [jetty-servlet-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.session.SessionHandler.doScope(SessionHandler.java:193) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.handler.ContextHandler.doScope(ContextHandler.java:1020) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:135) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.Dispatcher.forward(Dispatcher.java:229) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.Dispatcher.forward(Dispatcher.java:103) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.exist.http.urlrewrite.Forward.doRewrite(Forward.java:50) [exist-optional.jar:?]
    at org.exist.http.urlrewrite.XQueryURLRewrite.service(XQueryURLRewrite.java:223) [exist-optional.jar:?]
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:848) [servlet-api-3.0.jar:?]
    at org.eclipse.jetty.servlet.ServletHolder.handle(ServletHolder.java:684) [jetty-servlet-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.servlet.ServletHandler.doHandle(ServletHandler.java:503) [jetty-servlet-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:137) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.security.SecurityHandler.handle(SecurityHandler.java:533) [jetty-security-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.session.SessionHandler.doHandle(SessionHandler.java:231) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.handler.ContextHandler.doHandle(ContextHandler.java:1086) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.servlet.ServletHandler.doScope(ServletHandler.java:429) [jetty-servlet-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.session.SessionHandler.doScope(SessionHandler.java:193) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.handler.ContextHandler.doScope(ContextHandler.java:1020) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:135) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.handler.HandlerCollection.handle(HandlerCollection.java:154) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.handler.HandlerWrapper.handle(HandlerWrapper.java:116) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.Server.handle(Server.java:370) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.AbstractHttpConnection.handleRequest(AbstractHttpConnection.java:494) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.AbstractHttpConnection.content(AbstractHttpConnection.java:982) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.AbstractHttpConnection$RequestHandler.content(AbstractHttpConnection.java:1043) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.http.HttpParser.parseNext(HttpParser.java:865) [jetty-http-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.http.HttpParser.parseAvailable(HttpParser.java:240) [jetty-http-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.server.AsyncHttpConnection.handle(AsyncHttpConnection.java:82) [jetty-server-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.io.nio.SelectChannelEndPoint.handle(SelectChannelEndPoint.java:696) [jetty-io-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.io.nio.SelectChannelEndPoint$1.run(SelectChannelEndPoint.java:53) [jetty-io-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.util.thread.QueuedThreadPool.runJob(QueuedThreadPool.java:608) [jetty-util-8.1.17.v20150415.jar:8.1.17.v20150415]
    at org.eclipse.jetty.util.thread.QueuedThreadPool$3.run(QueuedThreadPool.java:543) [jetty-util-8.1.17.v20150415.jar:8.1.17.v20150415]
    at java.lang.Thread.run(Thread.java:745) [?:1.8.0_51]
Caused by: java.lang.StackOverflowError
    at java.lang.StringCoding.deref(StringCoding.java:63) ~[?:1.8.0_51]
    at java.lang.StringCoding.encode(StringCoding.java:330) ~[?:1.8.0_51]
    at java.lang.String.getBytes(String.java:906) ~[?:1.8.0_51]
    at java.io.UnixFileSystem.getSpace(Native Method) ~[?:1.8.0_51]
    at java.io.File.getUsableSpace(File.java:1885) ~[?:1.8.0_51]
    at org.exist.storage.BrokerPool.isReadOnly(BrokerPool.java:1324) ~[exist.jar:?]
    at org.exist.storage.NativeBroker.copyResource(NativeBroker.java:2396) ~[exist.jar:?]
    at org.exist.collections.triggers.HistoryTrigger.makeCopy(HistoryTrigger.java:102) ~[exist.jar:?]
    at org.exist.collections.triggers.HistoryTrigger.beforeCopyDocument(HistoryTrigger.java:143) ~[exist.jar:?]
    at org.exist.collections.triggers.DocumentTriggers.beforeCopyDocument(DocumentTriggers.java:282) ~[exist.jar:?]
    at org.exist.storage.NativeBroker.copyResource(NativeBroker.java:2455) ~[exist.jar:?]
    at org.exist.collections.triggers.HistoryTrigger.makeCopy(HistoryTrigger.java:102) ~[exist.jar:?]
    at org.exist.collections.triggers.HistoryTrigger.beforeCopyDocument(HistoryTrigger.java:143) ~[exist.jar:?]
    at org.exist.collections.triggers.DocumentTriggers.beforeCopyDocument(DocumentTriggers.java:282) ~[exist.jar:?]
    at org.exist.storage.NativeBroker.copyResource(NativeBroker.java:2455) ~[exist.jar:?]
    at org.exist.collections.triggers.HistoryTrigger.makeCopy(HistoryTrigger.java:102) ~[exist.jar:?]
    at org.exist.collections.triggers.HistoryTrigger.beforeCopyDocument(HistoryTrigger.java:143) ~[exist.jar:?]

...

    at org.exist.collections.triggers.DocumentTriggers.beforeCopyDocument(DocumentTriggers.java:282) ~[exist.jar:?]
    at org.exist.storage.NativeBroker.copyResource(NativeBroker.java:2455) ~[exist.jar:?]
    at org.exist.collections.triggers.HistoryTrigger.makeCopy(HistoryTrigger.java:102) ~[exist.jar:?]
    at org.exist.collections.triggers.HistoryTrigger.beforeCopyDocument(HistoryTrigger.java:143) ~[exist.jar:?]
    at org.exist.collections.triggers.DocumentTriggers.beforeCopyDocument(DocumentTriggers.java:282) ~[exist.jar:?]
    at org.exist.storage.NativeBroker.copyResource(NativeBroker.java:2455) ~[exist.jar:?]
    at org.exist.collections.triggers.HistoryTrigger.makeCopy(HistoryTrigger.java:102) ~[exist.jar:?]

however, it make a history collection whit in the /db/history/db/salam/sss.xml (sss.xml is name of changed doc that after change has been marked as empty collection.)

my eXist-db info:
ver: 2.2, 3.0RC1
os: fedora 20, fedora 21, fedora 22 (all of them are 64bit)
I Have this issue for a long time.
please help me for fix it. thanks

The following line fascinates me:

Caused by: java.lang.StackOverflowError
    at java.lang.StringCoding.deref(StringCoding.java:63) ~[?:1.8.0_51]
    at java.lang.StringCoding.encode(StringCoding.java:330) ~[?:1.8.0_51]
    at java.lang.String.getBytes(String.java:906) ~[?:1.8.0_51]
    at java.io.UnixFileSystem.getSpace(Native Method) ~[?:1.8.0_51]
    at java.io.File.getUsableSpace(File.java:1885) ~[?:1.8.0_51]
    at org.exist.storage.BrokerPool.isReadOnly(BrokerPool.java:1324) ~[exist.jar:?]

is your database set to readonly due to a diskspace issue?

    at org.exist.collections.triggers.HistoryTrigger.makeCopy(HistoryTrigger.java:102) ~[exist.jar:?]
    at org.exist.collections.triggers.HistoryTrigger.beforeCopyDocument(HistoryTrigger.java:143) ~[exist.jar:?]
    at org.exist.collections.triggers.DocumentTriggers.beforeCopyDocument(DocumentTriggers.java:282) ~[exist.jar:?]
    at org.exist.storage.NativeBroker.copyResource(NativeBroker.java:2455) ~[exist.jar:?]

hmmmm

I don't have diskspace issue, because when I disable HistoryTrigger feature, all transactions will done very well. I think HistoryTrigger cause this.

Does the HistoryTrigger work on your db without error?

The HistoryTrigger causes a java.lang.StackOverflow because it includes a beforeCopyDocument method AND attempts to copy the modified document. This causes infinite recursion.

The simple fix is to comment out the makeCopy call in the beforeCopyDocument method (line 144).

This attached test demonstrates the overflow error.
HistoryTrigger-test.txt

On 3.0RC2 the script does not give the problem; probably solved by @shabanovd and @adamretter in the following PRs

another good reason to get 3.0 released....

Was this page helpful?
0 / 5 - 0 ratings