Add connection Class

This commit is contained in:
vrde 2016-11-29 13:57:51 +01:00 committed by Sylvain Bellemare
parent 9615ac22ae
commit 53fb9f3d5f
5 changed files with 96 additions and 0 deletions

View File

@ -15,6 +15,7 @@ config = {
'threads': None, # if none, the value will be cpu_count * 2 + 1
},
'database': {
'backend': 'rethinkdb',
'host': os.environ.get('BIGCHAINDB_DATABASE_HOST', 'localhost'),
'port': 28015,
'name': 'bigchain',

View File

@ -0,0 +1 @@
from bigchaindb.backend.connection import connect # noqa

View File

@ -0,0 +1,15 @@
from importlib import import_module
BACKENDS = {
'rethinkdb': 'bigchaindb.backend.rethinkdb.connection.RethinkDBConnection'
}
def connect(backend, host, port, dbname):
module_name, _, class_name = BACKENDS[backend].rpartition('.')
Class = getattr(import_module(module_name), class_name)
return Class(host, port, dbname)
class Connection:
pass

View File

@ -0,0 +1,64 @@
import time
import logging
import rethinkdb as r
import bigchaindb
from bigchaindb.backend.connection import Connection
logger = logging.getLogger(__name__)
class RethinkDBConnection(Connection):
"""This class is a proxy to run queries against the database,
it is:
- lazy, since it creates a connection only when needed
- resilient, because before raising exceptions it tries
more times to run the query or open a connection.
"""
def __init__(self, host=None, port=None, db=None, max_tries=3):
"""Create a new Connection instance.
Args:
host (str, optional): the host to connect to.
port (int, optional): the port to connect to.
db (str, optional): the database to use.
max_tries (int, optional): how many tries before giving up.
"""
self.host = host or bigchaindb.config['database']['host']
self.port = port or bigchaindb.config['database']['port']
self.db = db or bigchaindb.config['database']['name']
self.max_tries = max_tries
self.conn = None
def run(self, query):
"""Run a query.
Args:
query: the RethinkDB query.
"""
if self.conn is None:
self._connect()
for i in range(self.max_tries):
try:
return query.run(self.conn)
except r.ReqlDriverError as exc:
if i + 1 == self.max_tries:
raise
else:
self._connect()
def _connect(self):
for i in range(self.max_tries):
try:
self.conn = r.connect(host=self.host, port=self.port,
db=self.db)
except r.ReqlDriverError as exc:
if i + 1 == self.max_tries:
raise
else:
time.sleep(2**i)

View File

@ -0,0 +1,15 @@
def test_get_connection_returns_the_correct_instance():
from bigchaindb.backend import connect
from bigchaindb.backend.connection import Connection
from bigchaindb.backend.rethinkdb.connection import RethinkDBConnection
config = {
'backend': 'rethinkdb',
'host': 'localhost',
'port': 28015,
'dbname': 'test'
}
conn = connect(**config)
assert isinstance(conn, Connection)
assert isinstance(conn, RethinkDBConnection)