diff --git a/common/lib/xmodule/xmodule/modulestore/split_mongo/mongo_connection.py b/common/lib/xmodule/xmodule/modulestore/split_mongo/mongo_connection.py index b28e3f77a6..027e8c8a93 100644 --- a/common/lib/xmodule/xmodule/modulestore/split_mongo/mongo_connection.py +++ b/common/lib/xmodule/xmodule/modulestore/split_mongo/mongo_connection.py @@ -2,6 +2,7 @@ Segregation of pymongo functions from the data modeling mechanisms for split modulestore. """ import re +from mongodb_proxy import autoretry_read, MongoProxy import pymongo import time @@ -68,50 +69,28 @@ def structure_to_mongo(structure): return new_structure -def autoretry_read(wait=0.1, retries=5): - """ - Automatically retry a read-only method in the case of a pymongo - AutoReconnect exception. - - See http://emptysqua.re/blog/save-the-monkey-reliably-writing-to-mongodb/ - for a discussion of this technique. - """ - def decorate(fn): - @wraps(fn) - def wrapper(*args, **kwargs): - for attempt in xrange(retries): - try: - return fn(*args, **kwargs) - break - except AutoReconnect: - # Reraise if we failed on our last attempt - if attempt == retries - 1: - raise - - if wait: - time.sleep(wait) - return wrapper - return decorate - - class MongoConnection(object): """ Segregation of pymongo functions from the data modeling mechanisms for split modulestore. """ def __init__( - self, db, collection, host, port=27017, tz_aware=True, user=None, password=None, asset_collection=None, **kwargs + self, db, collection, host, port=27017, tz_aware=True, user=None, password=None, + asset_collection=None, retry_wait_time=0.1, **kwargs ): """ Create & open the connection, authenticate, and provide pointers to the collections """ - self.database = pymongo.database.Database( - pymongo.MongoClient( - host=host, - port=port, - tz_aware=tz_aware, - **kwargs + self.database = MongoProxy( + pymongo.database.Database( + pymongo.MongoClient( + host=host, + port=port, + tz_aware=tz_aware, + **kwargs + ), + db ), - db + wait_time=retry_wait_time ) # Remove when adding official Split support for asset metadata storage. @@ -142,7 +121,6 @@ class MongoConnection(object): else: raise HeartbeatFailure("Can't connect to {}".format(self.database.name)) - @autoretry_read() def get_structure(self, key): """ Get the structure from the persistence mechanism whose id is the given key @@ -195,7 +173,6 @@ class MongoConnection(object): """ self.structures.insert(structure_to_mongo(structure)) - @autoretry_read() def get_course_index(self, key, ignore_case=False): """ Get the course_index from the persistence mechanism whose id is the given key @@ -212,7 +189,6 @@ class MongoConnection(object): } return self.course_index.find_one(query) - @autoretry_read() def find_matching_course_indexes(self, branch=None, search_targets=None): """ Find the course_index matching particular conditions. @@ -271,14 +247,12 @@ class MongoConnection(object): 'run': course_index['run'], }) - @autoretry_read() def get_definition(self, key): """ Get the definition from the persistence mechanism whose id is the given key """ return self.definitions.find_one({'_id': key}) - @autoretry_read() def get_definitions(self, definitions): """ Retrieve all definitions listed in `definitions`. diff --git a/common/lib/xmodule/xmodule/modulestore/split_mongo/split.py b/common/lib/xmodule/xmodule/modulestore/split_mongo/split.py index d37945ecef..0b3882ede0 100644 --- a/common/lib/xmodule/xmodule/modulestore/split_mongo/split.py +++ b/common/lib/xmodule/xmodule/modulestore/split_mongo/split.py @@ -56,6 +56,7 @@ import datetime import logging from contracts import contract, new_contract from importlib import import_module +from mongodb_proxy import autoretry_read from path import path from pytz import UTC from bson.objectid import ObjectId @@ -72,7 +73,6 @@ from xmodule.modulestore.exceptions import InsufficientSpecificationError, Versi from xmodule.modulestore import ( inheritance, ModuleStoreWriteBase, ModuleStoreEnum, BulkOpsRecord, BulkOperationsMixin ) -from xmodule.modulestore.mongodb_proxy import autoretry_read from ..exceptions import ItemNotFoundError from .caching_descriptor_system import CachingDescriptorSystem diff --git a/common/lib/xmodule/xmodule/modulestore/tests/test_split_w_old_mongo.py b/common/lib/xmodule/xmodule/modulestore/tests/test_split_w_old_mongo.py index 637de2c782..bab04573e4 100644 --- a/common/lib/xmodule/xmodule/modulestore/tests/test_split_w_old_mongo.py +++ b/common/lib/xmodule/xmodule/modulestore/tests/test_split_w_old_mongo.py @@ -70,9 +70,9 @@ class SplitWMongoCourseBoostrapper(unittest.TestCase): Remove the test collections, close the db connection """ split_db = self.split_mongo.db - split_db.drop_collection(split_db.course_index) - split_db.drop_collection(split_db.structures) - split_db.drop_collection(split_db.definitions) + split_db.drop_collection(split_db.course_index.proxied_object) + split_db.drop_collection(split_db.structures.proxied_object) + split_db.drop_collection(split_db.definitions.proxied_object) def tear_down_mongo(self): """