orientjs icon indicating copy to clipboard operation
orientjs copied to clipboard

How to make long lived live queries?

Open dargolith opened this issue 6 years ago • 5 comments

When I start a live query everything works great, until after some time has passed. Then the live query stops working without any error messages (even if vertices are created, callback is not called).

Here is the function I've created which performs the liveQuery.

const dbConnectionData = {
  host: 'orientdb',
  port: 2424,
};

const dbData = {
  username: 'root',
  password: 'somepw',
  name: testdb',
  useToken: true,
};

/**
 * Performs an ongoing live query to the database.
 */
export const liveQuery = async (query, callback) => {
  const client = await OrientDBClient.connect(dbConnectionData);
  let session;
  try {
    session = await client.session(dbData);
  } catch (err) {
    await client.close();
    throw err;
  }
  const handle = session.liveQuery(query).on('data', callback);
  return {
    unsubscribe: async () => {
      try {
        await handle.unsubscribe();
      } finally {
        client.close();
      }
    },
  };
};

Then I just use it like:

...
const handle = await liveQuery('SELECT FROM V', handleLiveUpdate);
...

The callback does fire for a while, but then (not sure exactly after how long) it stops being triggered, even though it should.

I also get the following errors in the orientdb server log:

2019-01-24T00:10:10.927168888Z $ANSI{green {db="testdb"}} Error executing live query subscriber.
2019-01-24T00:10:10.927181088Z com.orientechnologies.orient.core.exception.OLiveQueryInterruptedException: Live query interrupted by socket close
2019-01-24T00:10:10.927186888Z  DB name="testdb"
2019-01-24T00:10:10.927192089Z  at com.orientechnologies.orient.server.OServerLiveQueryResultListener.sendEvent(OServerLiveQueryResultListener.java:36)
2019-01-24T00:10:10.927197589Z  at com.orientechnologies.orient.server.OServerLiveQueryResultListener.onCreate(OServerLiveQueryResultListener.java:42)
2019-01-24T00:10:10.927202989Z  at com.orientechnologies.orient.core.sql.executor.LiveQueryListenerImpl.onLiveResult(LiveQueryListenerImpl.java:150)
2019-01-24T00:10:10.927208189Z  at com.orientechnologies.orient.core.query.live.OLiveQueryQueueThreadV2.run(OLiveQueryQueueThreadV2.java:57)
2019-01-24T00:10:10.927220290Z Caused by: java.net.SocketException: Socket closed
2019-01-24T00:10:10.927225590Z  at java.net.SocketOutputStream.socketWrite(SocketOutputStream.java:118)
2019-01-24T00:10:10.927231090Z  at java.net.SocketOutputStream.write(SocketOutputStream.java:155)
2019-01-24T00:10:10.927236290Z  at java.io.BufferedOutputStream.flushBuffer(BufferedOutputStream.java:82)
2019-01-24T00:10:10.927241691Z  at java.io.BufferedOutputStream.flush(BufferedOutputStream.java:140)
2019-01-24T00:10:10.927246791Z  at java.io.DataOutputStream.flush(DataOutputStream.java:123)
2019-01-24T00:10:10.927251891Z  at com.orientechnologies.orient.enterprise.channel.binary.OChannelBinary.flush(OChannelBinary.java:332)
2019-01-24T00:10:10.927257291Z  at com.orientechnologies.orient.server.network.protocol.binary.ONetworkProtocolBinary.push(ONetworkProtocolBinary.java:876)
2019-01-24T00:10:10.927262691Z  at com.orientechnologies.orient.server.OServerLiveQueryResultListener.sendEvent(OServerLiveQueryResultListener.java:34)
2019-01-24T00:10:10.927268392Z  ... 3 more

Any suggestions on what might be wrong, or guidelines on how to perform an infinite live query? I want to publish all changes to a broker enabling clients to subscribe to certain updates in the stored data model.

dargolith avatar Jan 24 '19 01:01 dargolith

Hi @dargolith

it should last as long as the connection is alive. Did you restart the app or the server meanwhile?

After how many minutes/hours do you notice this behaviour? Thank

wolf4ood avatar Jan 24 '19 15:01 wolf4ood

Hi, sorry for the late answer. Been really busy.

It was a bit difficult to target the exact time it took to stop working. After a while I found that it had to do with the keep-alive of the underlying sockets somehow. If no data is sent for 15 minutes, the socket dies.

The workaround I did was to make an update operation to the database every 10 minutes to a dummy record, triggering the callback for the live subscription. I could then identify that the update was a dummy update and not do any actions.

Perhaps some heartbeat or something should exist for this? Not sure where though.

It is probably also undesired that the orientdb service can't clean up those broken sockets but continues to write error log entries for each time the live query should have been triggered. In addition, it would be nice if orientjs could detect that the socket goes down (the subscription just silently dies now it seems).

dargolith avatar Feb 01 '19 13:02 dargolith

@dargolith thanks let me try to reproduce it

wolf4ood avatar Feb 14 '19 16:02 wolf4ood

Hi, same issue here using java client. LiveQuery seems ok and then stops working for an unknown reason. No error notification on client and one "live query interrupted by socket close" on server logs.

xavierdenis avatar Aug 22 '19 12:08 xavierdenis

hey @wolf4ood It happens to me too. any update on why it happens or a workaround? thanks
Anat

bulanan avatar Jul 13 '20 09:07 bulanan