diff --git a/django/core/urlresolvers.py b/django/core/urlresolvers.py
index b634b56..1497d43 100644
--- a/django/core/urlresolvers.py
+++ b/django/core/urlresolvers.py
@@ -518,3 +518,17 @@ def get_urlconf(default=None):
     changed from the default one.
     """
     return getattr(_urlconfs, "value", default)
+
+def is_valid_path(path, urlconf=None):
+    """
+    Returns True if the given path resolves against the default URL resolver,
+    False otherwise.
+
+    This is a convenience method to make working with "is this a match?" cases
+    easier, avoiding unnecessarily indented try...except blocks.
+    """
+    try:
+        resolve(path, urlconf)
+        return True
+    except Resolver404:
+        return False
diff --git a/django/middleware/common.py b/django/middleware/common.py
index aaa094d..d894ec8 100644
--- a/django/middleware/common.py
+++ b/django/middleware/common.py
@@ -64,8 +64,8 @@ class CommonMiddleware(object):
         # trailing slash and there is no pattern for the current path
         if settings.APPEND_SLASH and (not old_url[1].endswith('/')):
             urlconf = getattr(request, 'urlconf', None)
-            if (not _is_valid_path(request.path_info, urlconf) and
-                    _is_valid_path("%s/" % request.path_info, urlconf)):
+            if (not urlresolvers.is_valid_path(request.path_info, urlconf) and
+                    urlresolvers.is_valid_path("%s/" % request.path_info, urlconf)):
                 new_url[1] = new_url[1] + '/'
                 if settings.DEBUG and request.method == 'POST':
                     raise RuntimeError((""
@@ -151,18 +151,3 @@ def _is_internal_request(domain, referer):
     """
     # Different subdomains are treated as different domains.
     return referer is not None and re.match("^https?://%s/" % re.escape(domain), referer)
-
-def _is_valid_path(path, urlconf=None):
-    """
-    Returns True if the given path resolves against the default URL resolver,
-    False otherwise.
-
-    This is a convenience method to make working with "is this a match?" cases
-    easier, avoiding unnecessarily indented try...except blocks.
-    """
-    try:
-        urlresolvers.resolve(path, urlconf)
-        return True
-    except urlresolvers.Resolver404:
-        return False
-
diff --git a/django/middleware/locale.py b/django/middleware/locale.py
index 2a71f3d..0ed8ec1 100644
--- a/django/middleware/locale.py
+++ b/django/middleware/locale.py
@@ -1,10 +1,13 @@
 "This is the locale selecting middleware that will look at accept headers"
 
-from django.core.urlresolvers import get_resolver, LocaleRegexURLResolver
+from django.conf import settings
+from django.core.urlresolvers import (is_valid_path, get_resolver,
+                                      LocaleRegexURLResolver)
 from django.http import HttpResponseRedirect
 from django.utils.cache import patch_vary_headers
 from django.utils import translation
 
+
 class LocaleMiddleware(object):
     """
     This is a very simple middleware that parses a request
@@ -23,14 +26,18 @@ class LocaleMiddleware(object):
 
     def process_response(self, request, response):
         language = translation.get_language()
-        translation.deactivate()
-
         if (response.status_code == 404 and
                 not translation.get_language_from_path(request.path_info)
-                    and self.is_language_prefix_patterns_used()):
-            return HttpResponseRedirect(
-                '/%s%s' % (language, request.get_full_path()))
+                and self.is_language_prefix_patterns_used()):
+            urlconf = getattr(request, 'urlconf', None)
+            language_path = '/%s%s' % (language, request.path_info)
+            if settings.APPEND_SLASH and not language_path.endswith('/'):
+                language_path = language_path + '/'
+            if is_valid_path(language_path, urlconf):
+                return HttpResponseRedirect(
+                    '/%s%s' % (language, request.get_full_path()))
 
+        translation.deactivate()
         patch_vary_headers(response, ('Accept-Language',))
         if 'Content-Language' not in response:
             response['Content-Language'] = language
diff --git a/tests/regressiontests/i18n/patterns/tests.py b/tests/regressiontests/i18n/patterns/tests.py
index 1cc4520..1216d0b 100644
--- a/tests/regressiontests/i18n/patterns/tests.py
+++ b/tests/regressiontests/i18n/patterns/tests.py
@@ -144,37 +144,29 @@ class URLRedirectTests(URLTestCaseBase):
 
     def test_en_redirect(self):
         response = self.client.get('/account/register/', HTTP_ACCEPT_LANGUAGE='en')
-        self.assertRedirects(response, 'http://testserver/en/account/register/')
+        self.assertRedirects(response, '/en/account/register/')
 
         response = self.client.get(response['location'])
         self.assertEqual(response.status_code, 200)
 
     def test_en_redirect_wrong_url(self):
         response = self.client.get('/profiel/registeren/', HTTP_ACCEPT_LANGUAGE='en')
-        self.assertEqual(response.status_code, 302)
-        self.assertEqual(response['location'], 'http://testserver/en/profiel/registeren/')
-
-        response = self.client.get(response['location'])
         self.assertEqual(response.status_code, 404)
 
     def test_nl_redirect(self):
         response = self.client.get('/profiel/registeren/', HTTP_ACCEPT_LANGUAGE='nl')
-        self.assertRedirects(response, 'http://testserver/nl/profiel/registeren/')
+        self.assertRedirects(response, '/nl/profiel/registeren/')
 
         response = self.client.get(response['location'])
         self.assertEqual(response.status_code, 200)
 
     def test_nl_redirect_wrong_url(self):
         response = self.client.get('/account/register/', HTTP_ACCEPT_LANGUAGE='nl')
-        self.assertEqual(response.status_code, 302)
-        self.assertEqual(response['location'], 'http://testserver/nl/account/register/')
-
-        response = self.client.get(response['location'])
         self.assertEqual(response.status_code, 404)
 
     def test_pt_br_redirect(self):
         response = self.client.get('/conta/registre-se/', HTTP_ACCEPT_LANGUAGE='pt-br')
-        self.assertRedirects(response, 'http://testserver/pt-br/conta/registre-se/')
+        self.assertRedirects(response, '/pt-br/conta/registre-se/')
 
         response = self.client.get(response['location'])
         self.assertEqual(response.status_code, 200)
@@ -187,17 +179,15 @@ class URLRedirectWithoutTrailingSlashTests(URLTestCaseBase):
     """
     def test_not_prefixed_redirect(self):
         response = self.client.get('/not-prefixed', HTTP_ACCEPT_LANGUAGE='en')
-        self.assertEqual(response.status_code, 301)
-        self.assertEqual(response['location'], 'http://testserver/not-prefixed/')
+        self.assertRedirects(response, '/not-prefixed/', 301)
 
     def test_en_redirect(self):
         response = self.client.get('/account/register', HTTP_ACCEPT_LANGUAGE='en')
-        self.assertEqual(response.status_code, 302)
-        self.assertEqual(response['location'], 'http://testserver/en/account/register')
+        # target status code of 301 because of CommonMiddleware redirecting
+        self.assertRedirects(response, '/en/account/register', 302, target_status_code=301)
 
         response = self.client.get(response['location'])
-        self.assertEqual(response.status_code, 301)
-        self.assertEqual(response['location'], 'http://testserver/en/account/register/')
+        self.assertRedirects(response, '/en/account/register/', 301)
 
 
 class URLRedirectWithoutTrailingSlashSettingTests(URLTestCaseBase):
@@ -208,20 +198,15 @@ class URLRedirectWithoutTrailingSlashSettingTests(URLTestCaseBase):
     @override_settings(APPEND_SLASH=False)
     def test_not_prefixed_redirect(self):
         response = self.client.get('/not-prefixed', HTTP_ACCEPT_LANGUAGE='en')
-        self.assertEqual(response.status_code, 302)
-        self.assertEqual(response['location'], 'http://testserver/en/not-prefixed')
-
-        response = self.client.get(response['location'])
         self.assertEqual(response.status_code, 404)
 
     @override_settings(APPEND_SLASH=False)
     def test_en_redirect(self):
-        response = self.client.get('/account/register', HTTP_ACCEPT_LANGUAGE='en')
-        self.assertEqual(response.status_code, 302)
-        self.assertEqual(response['location'], 'http://testserver/en/account/register')
+        response = self.client.get('/account/register-without-slash', HTTP_ACCEPT_LANGUAGE='en')
+        self.assertRedirects(response, '/en/account/register-without-slash', 302)
 
         response = self.client.get(response['location'])
-        self.assertEqual(response.status_code, 404)
+        self.assertEqual(response.status_code, 200)
 
 
 class URLResponseTests(URLTestCaseBase):
diff --git a/tests/regressiontests/i18n/patterns/urls/namespace.py b/tests/regressiontests/i18n/patterns/urls/namespace.py
index bf43949..3a2467b 100644
--- a/tests/regressiontests/i18n/patterns/urls/namespace.py
+++ b/tests/regressiontests/i18n/patterns/urls/namespace.py
@@ -7,4 +7,5 @@ view = TemplateView.as_view(template_name='dummy.html')
 
 urlpatterns = patterns('',
     url(_(r'^register/$'), view, name='register'),
+    url(_(r'^register-without-slash$'), view, name='register-without-slash'),
 )
