diff --git a/.gitmodules b/.gitmodules
new file mode 100644
index 0000000000000000000000000000000000000000..72ec77d0e2fe3500a744426881989b1566b57b9f
--- /dev/null
+++ b/.gitmodules
@@ -0,0 +1,3 @@
+[submodule "askbot"]
+	path = askbot
+	url = git@github.com:MITx/askbot-devel.git
diff --git a/askbot b/askbot
new file mode 160000
index 0000000000000000000000000000000000000000..1c3381046c78e055439ba1c78e0df48410fcc13e
--- /dev/null
+++ b/askbot
@@ -0,0 +1 @@
+Subproject commit 1c3381046c78e055439ba1c78e0df48410fcc13e
diff --git a/lms/djangoapps/courseware/tests/tests.py b/lms/djangoapps/courseware/tests/tests.py
index 24cc9eac00a0b924d8ad4fbf3c6ce8356fef566e..8e9d13f8d5ad24d2d598df19b2345b968f3430cb 100644
--- a/lms/djangoapps/courseware/tests/tests.py
+++ b/lms/djangoapps/courseware/tests/tests.py
@@ -1,4 +1,9 @@
+import copy
 import json
+import os
+
+from pprint import pprint
+
 from django.test import TestCase
 from django.test.client import Client
 from mock import patch, Mock
@@ -14,7 +19,6 @@ from xmodule.modulestore.django import modulestore
 import xmodule.modulestore.django
 from xmodule.modulestore import Location
 from xmodule.modulestore.xml_importer import import_from_xml
-import copy
 
 
 def parse_json(response):
@@ -32,14 +36,32 @@ def registration(email):
     return Registration.objects.get(user__email=email)
 
 
-TEST_DATA_MODULESTORE = copy.deepcopy(settings.MODULESTORE)
-# TODO (vshnayder): test the real courses
-TEST_DATA_DIR = 'common/test/data'
-TEST_DATA_MODULESTORE['default']['OPTIONS']['fs_root'] = path(TEST_DATA_DIR)
+# A bit of a hack--want mongo modulestore for these tests, until
+# jump_to works with the xmlmodulestore or we have an even better solution
+# NOTE: this means this test requires mongo to be running.
 
-@override_settings(MODULESTORE=TEST_DATA_MODULESTORE)
-class IntegrationTestCase(TestCase):
-    '''Check that all objects in all accessible courses will load properly'''
+def mongo_store_config(data_dir):
+    return {
+    'default': {
+        'ENGINE': 'xmodule.modulestore.mongo.MongoModuleStore',
+        'OPTIONS': {
+            'default_class': 'xmodule.raw_module.RawDescriptor',
+            'host': 'localhost',
+            'db': 'xmodule',
+            'collection': 'modulestore',
+            'fs_root': data_dir,
+        }
+    }
+}
+
+TEST_DATA_DIR = settings.COMMON_TEST_DATA_ROOT
+TEST_DATA_MODULESTORE = mongo_store_config(TEST_DATA_DIR)
+
+REAL_DATA_DIR = settings.GITHUB_REPO_ROOT
+REAL_DATA_MODULESTORE = mongo_store_config(REAL_DATA_DIR)
+
+class ActivateLoginTestCase(TestCase):
+    '''Check that we can activate and log in'''
 
     def setUp(self):
         email = 'view@test.com'
@@ -47,9 +69,6 @@ class IntegrationTestCase(TestCase):
         self.create_account('viewtest', email, password)
         self.activate_user(email)
         self.login(email, password)
-        xmodule.modulestore.django._MODULESTORES = {}
-        xmodule.modulestore.django.modulestore().collection.drop()
-
 
     # ============ User creation and login ==============
 
@@ -107,15 +126,22 @@ class IntegrationTestCase(TestCase):
         # Now make sure that the user is now actually activated
         self.assertTrue(user(email).is_active)
 
-    # ============ Page loading ==============
+    def test_activate_login(self):
+        '''The setup function does all the work'''
+        pass
+
 
-    def check_pages_load(self, test_course_name):
-        import_from_xml(modulestore(), TEST_DATA_DIR, [test_course_name])
+class PageLoader(ActivateLoginTestCase):
+    ''' Base class that adds a function to load all pages in a modulestore '''
+
+    def check_pages_load(self, course_name, data_dir, modstore):
+        print "Checking course {0} in {1}".format(course_name, data_dir)
+        import_from_xml(modstore, data_dir, [course_name])
 
         n = 0
         num_bad = 0
         all_ok = True
-        for descriptor in modulestore().get_items(
+        for descriptor in modstore.get_items(
                 Location(None, None, None, None, None)):
             n += 1
             print "Checking ", descriptor.location.url()
@@ -129,16 +155,54 @@ class IntegrationTestCase(TestCase):
                 all_ok = False
                 num_bad += 1
             print msg
-            self.assertTrue(all_ok)
+            self.assertTrue(all_ok)  # fail fast
 
         print "{0}/{1} good".format(n - num_bad, n)
+        self.assertTrue(all_ok)
+
 
+@override_settings(MODULESTORE=TEST_DATA_MODULESTORE)
+class TestCoursesLoadTestCase(PageLoader):
+    '''Check that all pages in test courses load properly'''
+
+    def setUp(self):
+        ActivateLoginTestCase.setUp(self)
+        xmodule.modulestore.django._MODULESTORES = {}
+        xmodule.modulestore.django.modulestore().collection.drop()
 
     def test_toy_course_loads(self):
-        self.check_pages_load('toy')
+        self.check_pages_load('toy', TEST_DATA_DIR, modulestore())
 
     def test_full_course_loads(self):
-        self.check_pages_load('full')
+        self.check_pages_load('full', TEST_DATA_DIR, modulestore())
+
+
+    # ========= TODO: check ajax interaction here too?
+
+
+@override_settings(MODULESTORE=REAL_DATA_MODULESTORE)
+class RealCoursesLoadTestCase(PageLoader):
+    '''Check that all pages in real courses load properly'''
+
+    def setUp(self):
+        ActivateLoginTestCase.setUp(self)
+        xmodule.modulestore.django._MODULESTORES = {}
+        xmodule.modulestore.django.modulestore().collection.drop()
+
+    # TODO: Disabled test for now..  Fix once things are cleaned up.
+    def Xtest_real_courses_loads(self):
+        '''See if any real courses are available at the REAL_DATA_DIR.
+        If they are, check them.'''
+
+        # TODO: adjust staticfiles_dirs
+        if not os.path.isdir(REAL_DATA_DIR):
+            # No data present.  Just pass.
+            return
+
+        courses = [course_dir for course_dir in os.listdir(REAL_DATA_DIR)
+                   if os.path.isdir(REAL_DATA_DIR / course_dir)]
+        for course in courses:
+            self.check_pages_load(course, REAL_DATA_DIR, modulestore())
 
 
     # ========= TODO: check ajax interaction here too?
diff --git a/lms/envs/common.py b/lms/envs/common.py
index c9b44bca4038ab78799d85334b66585fad79215b..c071e61bb47734defad2f76d614f5129ba275baa 100644
--- a/lms/envs/common.py
+++ b/lms/envs/common.py
@@ -61,7 +61,7 @@ PROJECT_ROOT = path(__file__).abspath().dirname().dirname()  # /mitx/lms
 REPO_ROOT = PROJECT_ROOT.dirname()
 COMMON_ROOT = REPO_ROOT / "common"
 ENV_ROOT = REPO_ROOT.dirname()  # virtualenv dir /mitx is in
-ASKBOT_ROOT = ENV_ROOT / "askbot-devel"
+ASKBOT_ROOT = REPO_ROOT / "askbot"
 COURSES_ROOT = ENV_ROOT / "data"
 
 # FIXME: To support multiple courses, we should walk the courses dir at startup
diff --git a/lms/envs/test.py b/lms/envs/test.py
index ef63063b51feacf38c5b0aeeb5d6e21320e69a64..e6fedcb373ab272d059f8d81e305ea7c7697f098 100644
--- a/lms/envs/test.py
+++ b/lms/envs/test.py
@@ -12,15 +12,18 @@ from .logsettings import get_logger_config
 import os
 from path import path
 
-INSTALLED_APPS = [
-    app
-    for app
-    in INSTALLED_APPS
-    if not app.startswith('askbot')
-]
+# can't test start dates with this True, but on the other hand,
+# can test everything else :)
+MITX_FEATURES['DISABLE_START_DATES'] = True
+
+# Need wiki for courseware views to work. TODO (vshnayder): shouldn't need it.
+WIKI_ENABLED = True
+
+# Makes the tests run much faster...
+SOUTH_TESTS_MIGRATE = False # To disable migrations and use syncdb instead
 
 # Nose Test Runner
-INSTALLED_APPS += ['django_nose']
+INSTALLED_APPS += ('django_nose',)
 NOSE_ARGS = ['--cover-erase', '--with-xunit', '--with-xcoverage', '--cover-html',
              '--cover-inclusive', '--cover-html-dir',
              os.environ.get('NOSE_COVER_HTML_DIR', 'cover_html')]
@@ -35,12 +38,6 @@ STATIC_ROOT = TEST_ROOT / "staticfiles"
 
 COURSES_ROOT = TEST_ROOT / "data"
 DATA_DIR = COURSES_ROOT
-MAKO_TEMPLATES['course'] = [DATA_DIR]
-MAKO_TEMPLATES['sections'] = [DATA_DIR / 'sections']
-MAKO_TEMPLATES['custom_tags'] = [DATA_DIR / 'custom_tags']
-MAKO_TEMPLATES['main'] = [PROJECT_ROOT / 'templates',
-                          DATA_DIR / 'info',
-                          DATA_DIR / 'problems']
 
 LOGGING = get_logger_config(TEST_ROOT / "log",
                             logging_env="dev",
@@ -48,6 +45,9 @@ LOGGING = get_logger_config(TEST_ROOT / "log",
                             debug=True)
 
 COMMON_TEST_DATA_ROOT = COMMON_ROOT / "test" / "data"
+# Where the content data is checked out.  This may not exist on jenkins.
+GITHUB_REPO_ROOT = ENV_ROOT / "data"
+
 
 # TODO (cpennington): We need to figure out how envs/test.py can inject things
 # into common.py so that we don't have to repeat this sort of thing
diff --git a/lms/envs/test_mongo.py b/lms/envs/test_mongo.py
deleted file mode 100644
index cbf9209c9666296119a04451285e925b33890a36..0000000000000000000000000000000000000000
--- a/lms/envs/test_mongo.py
+++ /dev/null
@@ -1,113 +0,0 @@
-"""
-This config file runs the test environment, but with mongo as the datastore
-"""
-from .common import *
-
-from .logsettings import get_logger_config
-import os
-from path import path
-
-# can't testing start dates with this True, but on the other hand,
-# can test everything else :)
-MITX_FEATURES['DISABLE_START_DATES'] = True
-
-WIKI_ENABLED = True
-
-GITHUB_REPO_ROOT = ENV_ROOT / "data"
-
-MODULESTORE = {
-    'default': {
-        'ENGINE': 'xmodule.modulestore.mongo.MongoModuleStore',
-        'OPTIONS': {
-            'default_class': 'xmodule.raw_module.RawDescriptor',
-            'host': 'localhost',
-            'db': 'xmodule',
-            'collection': 'modulestore',
-            'fs_root': GITHUB_REPO_ROOT,
-        }
-    }
-}
-
-
-# Nose Test Runner
-INSTALLED_APPS += ('django_nose',)
-NOSE_ARGS = ['--cover-erase', '--with-xunit', '--with-xcoverage', '--cover-html',
-             '--cover-inclusive', '--cover-html-dir',
-             os.environ.get('NOSE_COVER_HTML_DIR', 'cover_html')]
-for app in os.listdir(PROJECT_ROOT / 'djangoapps'):
-    NOSE_ARGS += ['--cover-package', app]
-TEST_RUNNER = 'django_nose.NoseTestSuiteRunner'
-
-
-TEST_ROOT = path("test_root")
-# Want static files in the same dir for running on jenkins.
-STATIC_ROOT = TEST_ROOT / "staticfiles"
-
-
-
-LOGGING = get_logger_config(TEST_ROOT / "log",
-                            logging_env="dev",
-                            tracking_filename="tracking.log",
-                            debug=True)
-
-DATABASES = {
-    'default': {
-        'ENGINE': 'django.db.backends.sqlite3',
-        'NAME': PROJECT_ROOT / "db" / "mitx.db",
-    }
-}
-
-CACHES = {
-    # This is the cache used for most things. Askbot will not work without a
-    # functioning cache -- it relies on caching to load its settings in places.
-    # In staging/prod envs, the sessions also live here.
-    'default': {
-        'BACKEND': 'django.core.cache.backends.locmem.LocMemCache',
-        'LOCATION': 'mitx_loc_mem_cache',
-        'KEY_FUNCTION': 'util.memcache.safe_key',
-    },
-
-    # The general cache is what you get if you use our util.cache. It's used for
-    # things like caching the course.xml file for different A/B test groups.
-    # We set it to be a DummyCache to force reloading of course.xml in dev.
-    # In staging environments, we would grab VERSION from data uploaded by the
-    # push process.
-    'general': {
-        'BACKEND': 'django.core.cache.backends.dummy.DummyCache',
-        'KEY_PREFIX': 'general',
-        'VERSION': 4,
-        'KEY_FUNCTION': 'util.memcache.safe_key',
-    }
-}
-
-# Dummy secret key for dev
-SECRET_KEY = '85920908f28904ed733fe576320db18cabd7b6cd'
-
-# Makes the tests run much faster...
-SOUTH_TESTS_MIGRATE = False # To disable migrations and use syncdb instead
-
-############################ FILE UPLOADS (ASKBOT) #############################
-DEFAULT_FILE_STORAGE = 'django.core.files.storage.FileSystemStorage'
-MEDIA_ROOT = TEST_ROOT / "uploads"
-MEDIA_URL = "/static/uploads/"
-STATICFILES_DIRS.append(("uploads", MEDIA_ROOT))
-
-new_staticfiles_dirs = []
-# Strip out any static files that aren't in the repository root
-# so that the tests can run with only the mitx directory checked out
-for static_dir in STATICFILES_DIRS:
-    # Handle both tuples and non-tuple directory definitions
-    try:
-        _, data_dir = static_dir
-    except ValueError:
-        data_dir = static_dir
-
-    if data_dir.startswith(REPO_ROOT):
-        new_staticfiles_dirs.append(static_dir)
-STATICFILES_DIRS = new_staticfiles_dirs
-
-FILE_UPLOAD_TEMP_DIR = PROJECT_ROOT / "uploads"
-FILE_UPLOAD_HANDLERS = (
-    'django.core.files.uploadhandler.MemoryFileUploadHandler',
-    'django.core.files.uploadhandler.TemporaryFileUploadHandler',
-)