Repository: DataDog/dd-trace-py

Issue:
Is it compatible with django 2.0?



Discussion:

+1
Thanks for reporting that! One of our next steps is to update our compatibility list so that we know what we support and what not. In case we don't support something, we'll provide a proper fix.

Resolving patch:
diff --git a/ddtrace/contrib/django/compat.py b/ddtrace/contrib/django/compat.py
new file mode 100644
--- /dev/null
+++ b/ddtrace/contrib/django/compat.py
@@ -0,0 +1,9 @@
+import django
+
+
+if django.VERSION >= (2,):
+    def user_is_authenticated(user):
+        return user.is_authenticated
+else:
+    def user_is_authenticated(user):
+        return user.is_authenticated()
diff --git a/ddtrace/contrib/django/middleware.py b/ddtrace/contrib/django/middleware.py
--- a/ddtrace/contrib/django/middleware.py
+++ b/ddtrace/contrib/django/middleware.py
@@ -2,6 +2,7 @@
 
 # project
 from .conf import settings
+from .compat import user_is_authenticated
 
 from ...ext import http
 from ...contrib import func_name
@@ -134,7 +135,7 @@ def _set_auth_tags(span, request):
         return span
 
     if hasattr(user, 'is_authenticated'):
-        span.set_tag('django.user.is_authenticated', user.is_authenticated())
+        span.set_tag('django.user.is_authenticated', user_is_authenticated(user))
 
     uid = getattr(user, 'pk', None)
     if uid:


Test patch:
diff --git a/tests/contrib/django/app/settings.py b/tests/contrib/django/app/settings.py
--- a/tests/contrib/django/app/settings.py
+++ b/tests/contrib/django/app/settings.py
@@ -69,7 +69,7 @@
     },
 ]
 
-if django.VERSION >= (1, 10):
+if (1, 10) <= django.VERSION < (2, 0):
     MIDDLEWARE = [
         'django.contrib.sessions.middleware.SessionMiddleware',
         'django.middleware.common.CommonMiddleware',
@@ -82,6 +82,21 @@
 
         'tests.contrib.django.app.middlewares.CatchExceptionMiddleware',
     ]
+
+# Django 2.0 has different defaults
+if django.VERSION >= (2, 0):
+    MIDDLEWARE = [
+        'django.contrib.sessions.middleware.SessionMiddleware',
+        'django.middleware.common.CommonMiddleware',
+        'django.middleware.csrf.CsrfViewMiddleware',
+        'django.contrib.auth.middleware.AuthenticationMiddleware',
+        'django.contrib.messages.middleware.MessageMiddleware',
+        'django.middleware.clickjacking.XFrameOptionsMiddleware',
+        'django.middleware.security.SecurityMiddleware',
+
+        'tests.contrib.django.app.middlewares.CatchExceptionMiddleware',
+    ]
+
 # Always add the legacy conf to make sure we handle it properly
 # Pre 1.10 style
 MIDDLEWARE_CLASSES = [
diff --git a/tests/contrib/django/compat.py b/tests/contrib/django/compat.py
new file mode 100644
--- /dev/null
+++ b/tests/contrib/django/compat.py
@@ -0,0 +1,4 @@
+try:
+    from django.core.urlresolvers import reverse
+except ImportError:
+    from django.urls import reverse
diff --git a/tests/contrib/django/test_cache_views.py b/tests/contrib/django/test_cache_views.py
--- a/tests/contrib/django/test_cache_views.py
+++ b/tests/contrib/django/test_cache_views.py
@@ -3,9 +3,8 @@
 # 3rd party
 from nose.tools import eq_, ok_
 
-from django.core.urlresolvers import reverse
-
 # testing
+from .compat import reverse
 from .utils import DjangoTraceTestCase
 
 
diff --git a/tests/contrib/django/test_middleware.py b/tests/contrib/django/test_middleware.py
--- a/tests/contrib/django/test_middleware.py
+++ b/tests/contrib/django/test_middleware.py
@@ -2,7 +2,6 @@
 from nose.tools import eq_
 
 from django.test import modify_settings
-from django.core.urlresolvers import reverse
 
 # project
 from ddtrace.constants import SAMPLING_PRIORITY_KEY
@@ -10,6 +9,7 @@
 from ddtrace.contrib.django import TraceMiddleware
 
 # testing
+from .compat import reverse
 from .utils import DjangoTraceTestCase, override_ddtrace_settings
 
 
diff --git a/tests/contrib/djangorestframework/app/settings.py b/tests/contrib/djangorestframework/app/settings.py
--- a/tests/contrib/djangorestframework/app/settings.py
+++ b/tests/contrib/djangorestframework/app/settings.py
@@ -55,6 +55,20 @@
         'tests.contrib.django.app.middlewares.CatchExceptionMiddleware',
     ]
 
+# Django 2.0 has different defaults
+if django.VERSION >= (2, 0):
+    MIDDLEWARE = [
+        'django.contrib.sessions.middleware.SessionMiddleware',
+        'django.middleware.common.CommonMiddleware',
+        'django.middleware.csrf.CsrfViewMiddleware',
+        'django.contrib.auth.middleware.AuthenticationMiddleware',
+        'django.contrib.messages.middleware.MessageMiddleware',
+        'django.middleware.clickjacking.XFrameOptionsMiddleware',
+        'django.middleware.security.SecurityMiddleware',
+
+        'tests.contrib.django.app.middlewares.CatchExceptionMiddleware',
+    ]
+
 # Always add the legacy conf to make sure we handle it properly
 # Pre 1.10 style
 MIDDLEWARE_CLASSES = [