Cannot connect to Aura DB from Python with Neo4j example.py file

I'm trying to connect to Aura using the provided example file of neo4j: Neo4j Aura. I'm able to connect from the browser but when trying the example file I get the following error: Unable to retrieve routing information

what should I do?

This is the full code:

from neo4j import GraphDatabase
import logging
from neo4j.exceptions import ServiceUnavailable

class App:

    def __init__(self, uri, user, password):
        self.driver = GraphDatabase.driver(uri, auth=(user, password))

    def close(self):
        # Don't forget to close the driver connection when you are finished with it
        self.driver.close()

    def create_friendship(self, person1_name, person2_name):
        with self.driver.session() as session:
            # Write transactions allow the driver to handle retries and transient errors
            result = session.write_transaction(
                self._create_and_return_friendship, person1_name, person2_name)
            for row in result:
                print("Created friendship between: {p1}, {p2}".format(p1=row['p1'], p2=row['p2']))

    @staticmethod
    def _create_and_return_friendship(tx, person1_name, person2_name):
        # To learn more about the Cypher syntax, see https://neo4j.com/docs/cypher-manual/current/
        # The Reference Card is also a good resource for keywords https://neo4j.com/docs/cypher-refcard/current/
        query = (
            "CREATE (p1:Person { name: $person1_name }) "
            "CREATE (p2:Person { name: $person2_name }) "
            "CREATE (p1)-[:KNOWS]->(p2) "
            "RETURN p1, p2"
        )
        result = tx.run(query, person1_name=person1_name, person2_name=person2_name)
        try:
            return [{"p1": row["p1"]["name"], "p2": row["p2"]["name"]}
                    for row in result]
        # Capture any errors along with the query and data for traceability
        except ServiceUnavailable as exception:
            logging.error("{query} raised an error: \n {exception}".format(
                query=query, exception=exception))
            raise

    def find_person(self, person_name):
        with self.driver.session() as session:
            result = session.read_transaction(self._find_and_return_person, person_name)
            for row in result:
                print("Found person: {row}".format(row=row))

    @staticmethod
    def _find_and_return_person(tx, person_name):
        query = (
            "MATCH (p:Person) "
            "WHERE p.name = $person_name "
            "RETURN p.name AS name"
        )
        result = tx.run(query, person_name=person_name)
        return [row["name"] for row in result]


if __name__ == "__main__":
    # Aura queries use an encrypted connection using the "neo4j+s" URI scheme
    uri = "neo4j+s://<Bolt url for Neo4j Aura database>"
    user = "<Username for Neo4j Aura database>"
    password = "<Password for Neo4j Aura database>"
    app = App(uri, user, password)
    app.create_friendship("Alice", "David")
    app.find_person("Alice")
    app.close()`Preformatted text`

Is there any firewall blocking traffic between you and Neo4j Aura? The most common source of this error is problems with the network between you and the Aura instance. The full output of the script might also help

Hi David,

I am getting the above error and I guess the reason is that I am connecting through SSL connection. "encrypted=False" does not help here because the example uses uri "neo4j+s://".
Is there any workaround here? BTW, because I am using free aura I think I can't change the DB configuration.

Thanks!

1 Like

Hi, I'm looking over the instructions too and don't understand this part, can anyone explain: "You will need to import GraphDatabase and basic_auth in order to make a connection to your Neo4j Aura instance."

Also, in setting up Aura I selected to have it populated with movie data. To use the above code should I have selected to have a blank database setup? What should I do in this case if it is true? Can I delete the database somehow and start over?

2 Likes

Simple connection test using the provided docs results in the

Neo4jError: Could not perform discovery. No routing servers available. Known routing table: RoutingTable[database=default database, expirationTime=0, currentTime=1650494093987, routers=[], readers=[], writers=[]]

In my case, I am using the nodeJs example and running it from an aws lambda. I tried using both of the provided database templates. No dice for either of them.

I am unclear on what to do next. Getting signed up and hooked in with the web console was a breeze. I thought that if i could connect with the web console, then it would be equally as easy to connect using the driver :confused:

I swear everytime I reach my wits end and post on a forum, I solve it myself a few minutes later!

I realized that marketing docs are not equal to full dev docs, so went to the respective driver repo and saw that you may specify a database.

Upon changing the init code just slightly to include a valid database that is created by their provisioning, it works!

  driver = neo4j.driver(url, neo4j.auth.basic(user, pass))
  session = driver.session({
    database: 'neo4j'
  })

Update: I reran the function this morning with no changes to my code and the issue is back.

Neo4jError: Could not perform discovery. No routing servers available. Known routing table: RoutingTable[database=neo4j, expirationTime=1650559211472, currentTime=1650559394477, routers=[], readers=[], writers=[]]\n\n

After messing around with this for awhile, I have realized that this is just poor error handling that leads to the error for multiple different reasons.

This configuration is more stable, but still generates the error at times if I send too many transactions, though its not consistent. It starts choking around 4k randomly.

  driver = neo4j.driver(url, neo4j.auth.basic(user, pass))
  session = driver.session({
    database: 'neo4j',
    encrypted: 'ENCRYPTION_ON',
    trust: 'TRUST_ALL_CERTIFICATES'
  })
 let myData = [...] // over 4k
  let neoRes = await session.writeTransaction(tx => {
    let newRecords = myData.map(query => tx.run(query.cql, query.params))

    return Promise.all(newRecords)
  })