cancel
Showing results for 
Search instead for 
Did you mean: 

Head's Up! These forums are read-only. All users and content have migrated. Please join us at community.neo4j.com.

Cannot begin a transaction on a closed session

Hi All,

I am writing an insert operation into neo4j using neo4j driver for Node js. The first time, the function will run, and on calling the same function second time, it will throw error " Cannot begin a transaction on a closed session."

Here is the code snippet

let query='some query';
let param ={ some param};
try{
await session.writeTransaction( async txc =>{

       let result = await txc.run(query, param)
     
       if (result.records.length != 0) {
           console.log('operation is successful')
       } else {
       console.log('operation return nothing')

      }
   })      

} catch (error){
console.log('exception occure', error)
throw error
}finally{

   await session.close()

}

I have noticed, in finally I am closing the session, would that be an issue. If yes, then when to close the session and when to start a session?

1 ACCEPTED SOLUTION

lclay
Node Link

Hi,
The code you show doesn't actually display how the second query is coming through or instantiated.

Typically, you will want to create a new session within the same code execution as the query and the close statements. A typical workflow would be something like this...

Enter Function/Method
Create Session object
Run query(s) against Session object
Close Session object
Return from function method

View solution in original post

4 REPLIES 4

lclay
Node Link

Hi,
The code you show doesn't actually display how the second query is coming through or instantiated.

Typically, you will want to create a new session within the same code execution as the query and the close statements. A typical workflow would be something like this...

Enter Function/Method
Create Session object
Run query(s) against Session object
Close Session object
Return from function method

Thanks its solved the problem, i had created another file as config file, where i has inititalise graph db configuration.

2X_8_8578b1da7c4545da18a271ba65ce976d8b5533f7.png

So instead of exporting driver, i had created a session object const session = driver.session() and exported it.

So whenever my method was called, session was the old one, so it was throwing error.

import driver from './config'
async functionName(arg1, arg2) {

const session = driver.session()


let query;

  query = `create (p:Person{id:$arg1, name:$arg2}) return p`
}

let param = {
  id:arg1,
  name: arg2

}


try{
 await session.writeTransaction( async txc =>{

       let result = await txc.run(query, param)
    
       if (result.records.length != 0) {
           console.log('operation is successful')
       } else {
       
 console.log('query resturn nothing')
      }
   })

}catch(error){
console.log('exception occure', error)
throw error
}finally{

 await session.close()

}

}

The answer to that question is in when and where session is created and connected.

Under the hood, the Neo4j API provides a service for interacting with the database, with which transaction instances are created. Each transaction runs one and only one set of operations, then closes.

servicetransaction → command.

In the javascript driver, session is both a Promise, and an abstraction for the Neo4j service. That makes things a little more tricky if you're trying to create persistent objects, or make multiple async calls to a single instance of a thing which uses session.

First, I'd take a close look at the example from github:neo4j\neo4j-javascript-driver.

You'll need to close the session to resolve the promise which completes the transaction. Thus you'll need to create a new session on subsequent calls to the same code.

Rather than directly managing the transactions, I would advise trying to keep to the promise pattern in the example if you can.

Hi, I found you have to always instantiate a new session, just like you said, but you also have to do:

let result = await driver.session()
...
await session.close()

Here's a working snippet:

Execute Raw Queries here
async function executeCypherQuery(statement, params = {}) {
  try {
    let session = driver.session()
    const result = await session.run(statement, params);
    await session.close();
    return result;
  } catch (error) {
    throw error; // we are logging this error at the time of calling this method
  }
}