From 079613d4e790029d8163d3f6e60c9ebcdb921124 Mon Sep 17 00:00:00 2001
From: Paul Marillonnet <pmarillonnet@entrouvert.com>
Date: Thu, 24 Jan 2019 11:40:48 +0100
Subject: [PATCH] python3: use django.utils.six url-parsing functions (#31139)

---
 src/authentic2/backends/ldap_backend.py         | 6 +++---
 src/authentic2/cors.py                          | 2 +-
 src/authentic2/disco_service/disco_responder.py | 5 ++---
 src/authentic2/idp/saml/backend.py              | 4 ++--
 src/authentic2/idp/saml/saml2_endpoints.py      | 8 ++++----
 src/authentic2/middleware.py                    | 2 +-
 src/authentic2/models.py                        | 2 +-
 src/authentic2/saml/common.py                   | 3 +--
 src/authentic2/utils.py                         | 9 ++++-----
 src/authentic2/views.py                         | 1 -
 src/authentic2_auth_oidc/utils.py               | 2 +-
 src/authentic2_idp_cas/managers.py              | 2 +-
 src/authentic2_idp_oidc/utils.py                | 2 +-
 tests/conftest.py                               | 2 +-
 tests/test_admin.py                             | 3 +--
 tests/test_all.py                               | 2 +-
 tests/test_auth_oidc.py                         | 2 +-
 tests/test_cas.py                               | 4 +---
 tests/test_idp_oidc.py                          | 2 +-
 tests/test_idp_saml2.py                         | 2 +-
 tests/test_login.py                             | 2 +-
 tests/test_manager.py                           | 2 +-
 tests/test_registration.py                      | 2 +-
 tests/test_views.py                             | 3 +--
 tests/utils.py                                  | 2 +-
 25 files changed, 34 insertions(+), 42 deletions(-)

diff --git a/src/authentic2/backends/ldap_backend.py b/src/authentic2/backends/ldap_backend.py
index ae692903..0f0cf67a 100644
--- a/src/authentic2/backends/ldap_backend.py
+++ b/src/authentic2/backends/ldap_backend.py
@@ -14,7 +14,6 @@ except ImportError:
 import logging
 import random
 import base64
-import urllib
 import six
 import os
 
@@ -27,6 +26,7 @@ from django.core.exceptions import ImproperlyConfigured
 from django.conf import settings
 from django.contrib.auth.models import Group
 from django.utils.encoding import force_bytes, force_text
+from django.utils.six.moves.urllib import parse
 
 from authentic2.a2_rbac.models import Role
 
@@ -965,7 +965,7 @@ class LDAPBackend(object):
                 attribute, param = attribute.split(':')
                 quote = 'noquote' not in param.split(',')
             if quote:
-                decoded.append((attribute, urllib.unquote(value)))
+                decoded.append((attribute, parse.unquote(value)))
             else:
                 decoded.append((attribute, force_text(value)))
         filters = [filter_format(u'(%s=%s)', (a, b)) for a, b in decoded]
@@ -986,7 +986,7 @@ class LDAPBackend(object):
                 v = v[0]
             v = force_text(v)
             if quote:
-                v = urllib.quote(v)
+                v = parse.quote(v)
             l.append(v)
         return ' '.join(v for v in l)
 
diff --git a/src/authentic2/cors.py b/src/authentic2/cors.py
index a41b27f8..aae0ffd4 100644
--- a/src/authentic2/cors.py
+++ b/src/authentic2/cors.py
@@ -1,7 +1,7 @@
 from .decorators import SessionCache
-import urlparse
 
 from django.conf import settings
+from django.utils.six.moves.urllib import parse as urlparse
 
 from . import plugins, app_settings
 
diff --git a/src/authentic2/disco_service/disco_responder.py b/src/authentic2/disco_service/disco_responder.py
index 34006763..f5115892 100644
--- a/src/authentic2/disco_service/disco_responder.py
+++ b/src/authentic2/disco_service/disco_responder.py
@@ -7,8 +7,6 @@
 
 
 import logging
-import urlparse
-import urllib
 
 from xml.dom.minidom import parseString
 
@@ -17,6 +15,7 @@ from django.conf.urls import url
 from django.utils.translation import ugettext as _
 from django.core.urlresolvers import reverse
 from django.utils.http import urlquote
+from django.utils.six.moves.urllib import parse as urlparse
 
 from authentic2 import settings
 from authentic2.saml.common import error_page as base_error_page
@@ -123,7 +122,7 @@ def add_param_to_url(url, param_name, value):
     if query:
         qs = urlparse.parse_qs(query)
         qs[param_name] = [value]
-        query = urllib.urlencode(qs)
+        query = urlparse.urlencode(qs)
     else:
         query = '%s=%s' % (param_name, value)
     return urlparse.urlunparse((scheme, netloc, path, params, query, fragment))
diff --git a/src/authentic2/idp/saml/backend.py b/src/authentic2/idp/saml/backend.py
index 74b1711e..ec85dbef 100644
--- a/src/authentic2/idp/saml/backend.py
+++ b/src/authentic2/idp/saml/backend.py
@@ -1,5 +1,4 @@
 import logging
-import urllib
 import operator
 import random
 
@@ -7,6 +6,7 @@ from django.utils.translation import ugettext as _
 from django.core.urlresolvers import reverse
 from django.template.loader import render_to_string
 from django.db.models import Q
+from django.utils.six.moves.urllib.parse import quote
 
 import authentic2.saml.models as models
 import authentic2.idp.saml.saml2_endpoints as saml2_endpoints
@@ -121,7 +121,7 @@ class SamlBackend(object):
                     # add a nonce so this link is never cached
                     nonce = hex(random.getrandbits(128))
                     url = '{0}?provider_id={1}&nonce={2}'.format(
-                        url, urllib.quote(provider_id), nonce)
+                        url, quote(provider_id), nonce)
                     name = name or provider_id
                     code = render_to_string('idp/saml/logout_fragment.html', {
                         'needs_iframe': policy.needs_iframe_logout,
diff --git a/src/authentic2/idp/saml/saml2_endpoints.py b/src/authentic2/idp/saml/saml2_endpoints.py
index cda431dc..c59589d8 100644
--- a/src/authentic2/idp/saml/saml2_endpoints.py
+++ b/src/authentic2/idp/saml/saml2_endpoints.py
@@ -18,7 +18,6 @@
 
 import datetime
 import logging
-import urllib
 import xml.etree.cElementTree as ctree
 import hashlib
 import random
@@ -38,6 +37,7 @@ from django.views.decorators.http import require_POST
 from django.contrib.auth import BACKEND_SESSION_KEY, REDIRECT_FIELD_NAME
 from django.conf import settings
 from django.utils.encoding import smart_unicode
+from django.utils.six.moves.urllib.parse import quote, urlencode
 from django.contrib.auth import load_backend
 from django.shortcuts import render, redirect
 from django.contrib import messages
@@ -484,7 +484,7 @@ def sso(request):
                     server=login.server, autoload=True)
             if not provider_loaded:
                 add_url = reverse('admin:saml_libertyprovider_add_from_url')
-                add_url += '?' + urllib.urlencode({ 'entity_id': provider_id })
+                add_url += '?' + urlencode({ 'entity_id': provider_id })
                 return render(request,
                         'idp/saml/unknown_provider.html',
                         { 'entity_id': provider_id,
@@ -556,7 +556,7 @@ def need_login(request, login, nid_format, service):
 
 def get_url_with_nonce(request, function, nonce):
     url = reverse(function) + '?%s=%s' % (NONCE_FIELD_NAME, nonce)
-    return urllib.quote(url)
+    return quote(url)
 
 
 def need_consent_for_federation(request, login, nid_format):
@@ -571,7 +571,7 @@ def need_consent_for_federation(request, login, nid_format):
     except ObjectDoesNotExist:
         pass
     if not display_name:
-        display_name = urllib.quote(login.request.issuer.content)
+        display_name = quote(login.request.issuer.content)
     url = '%s?%s=%s&next=%s&provider_id=%s' \
         % (reverse('a2-consent-federation'), NONCE_FIELD_NAME,
             nonce, get_url_with_nonce(request, continue_sso, nonce),
diff --git a/src/authentic2/middleware.py b/src/authentic2/middleware.py
index 3393fb37..f09e911b 100644
--- a/src/authentic2/middleware.py
+++ b/src/authentic2/middleware.py
@@ -1,4 +1,3 @@
-import urlparse
 import logging
 import datetime
 import random
@@ -12,6 +11,7 @@ except ImportError:
 from django.conf import settings
 from django.contrib import messages
 from django.utils.translation import ugettext as _
+from django.utils.six.moves.urllib import parse as urlparse
 from django.shortcuts import render
 
 from . import app_settings, utils, plugins
diff --git a/src/authentic2/models.py b/src/authentic2/models.py
index 11461264..2080fc02 100644
--- a/src/authentic2/models.py
+++ b/src/authentic2/models.py
@@ -1,11 +1,11 @@
 import time
-import urlparse
 import uuid
 from django.utils.http import urlquote
 from django.conf import settings
 from django.db import models
 from django.db.models.query import Q
 from django.utils.translation import ugettext_lazy as _
+from django.utils.six.moves.urllib import parse as urlparse
 from django.core.exceptions import ValidationError, FieldDoesNotExist
 from django.contrib.contenttypes.models import ContentType
 
diff --git a/src/authentic2/saml/common.py b/src/authentic2/saml/common.py
index d1052c98..4a94e272 100644
--- a/src/authentic2/saml/common.py
+++ b/src/authentic2/saml/common.py
@@ -1,6 +1,4 @@
-import urlparse
 import os.path
-import urllib
 import httplib
 import logging
 import re
@@ -12,6 +10,7 @@ from authentic2.compat_lasso import lasso
 from django.conf import settings
 from django.http import HttpResponseRedirect, Http404, HttpResponse
 from django.shortcuts import render
+from django.utils.six.moves.urllib import parse as urlparse
 from django.core.exceptions import ValidationError
 
 from authentic2.saml.models import (LibertyFederation, LibertyProvider,
diff --git a/src/authentic2/utils.py b/src/authentic2/utils.py
index 5f494844..3a759bcb 100644
--- a/src/authentic2/utils.py
+++ b/src/authentic2/utils.py
@@ -2,8 +2,6 @@ import inspect
 import random
 import time
 import logging
-import urllib
-import urlparse
 import uuid
 import datetime
 import copy
@@ -25,6 +23,7 @@ from django.forms.utils import ErrorList, to_current_timezone
 from django.utils import timezone
 from django.utils import html, http, six, encoding
 from django.utils.translation import ugettext as _, ungettext
+from django.utils.six.moves.urllib import parse as urlparse
 from django.shortcuts import resolve_url
 from django.template.loader import render_to_string, TemplateDoesNotExist
 from django.core.mail import send_mail
@@ -210,9 +209,9 @@ def get_backend_method(backend, method, parameters):
 
 def add_arg(url, key, value=None):
     '''Add a parameter to an URL'''
-    key = urllib.quote(key)
+    key = urlparse.quote(key)
     if value is not None:
-        add = '%s=%s' % (key, urllib.quote(value))
+        add = '%s=%s' % (key, urlparse.quote(value))
     else:
         add = key
     if '?' in url:
@@ -712,7 +711,7 @@ def build_reset_password_url(user, request=None, next_url=None, set_random_passw
     if request:
         reset_url = request.build_absolute_uri(reset_url)
     if next_url:
-        reset_url += '?' + urllib.urlencode({'next': next_url})
+        reset_url += '?' + urlparse.urlencode({'next': next_url})
     return reset_url, token
 
 
diff --git a/src/authentic2/views.py b/src/authentic2/views.py
index 0f8b4045..5c234fb5 100644
--- a/src/authentic2/views.py
+++ b/src/authentic2/views.py
@@ -2,7 +2,6 @@ import logging
 from authentic2.compat_lasso import lasso
 import thread
 import requests
-import urllib
 import re
 import collections
 
diff --git a/src/authentic2_auth_oidc/utils.py b/src/authentic2_auth_oidc/utils.py
index 6b5f1baf..1f2956e7 100644
--- a/src/authentic2_auth_oidc/utils.py
+++ b/src/authentic2_auth_oidc/utils.py
@@ -1,4 +1,3 @@
-import urlparse
 import datetime
 import base64
 import json
@@ -8,6 +7,7 @@ import requests
 from django.utils.timezone import utc
 from django.shortcuts import get_object_or_404
 from django.utils.translation import ugettext as _
+from django.utils.six.moves.urllib import parse as urlparse
 
 from authentic2.decorators import GlobalCache
 from authentic2.models import Attribute
diff --git a/src/authentic2_idp_cas/managers.py b/src/authentic2_idp_cas/managers.py
index 317ab0df..6bc0f220 100644
--- a/src/authentic2_idp_cas/managers.py
+++ b/src/authentic2_idp_cas/managers.py
@@ -1,9 +1,9 @@
-import urlparse
 from datetime import timedelta
 
 from django.db import models
 from django.db.models import query
 from django.utils.timezone import now
+from django.utils.six.moves.urllib import parse as urlparse
 
 
 class TicketQuerySet(query.QuerySet):
diff --git a/src/authentic2_idp_oidc/utils.py b/src/authentic2_idp_oidc/utils.py
index 5297d9f6..88e0dbf3 100644
--- a/src/authentic2_idp_oidc/utils.py
+++ b/src/authentic2_idp_oidc/utils.py
@@ -1,6 +1,5 @@
 import json
 import hashlib
-import urlparse
 import base64
 import uuid
 
@@ -10,6 +9,7 @@ from jwcrypto.jwt import JWT
 from django.core.exceptions import ImproperlyConfigured
 from django.conf import settings
 from django.utils.encoding import smart_bytes
+from django.utils.six.moves.urllib import parse as urlparse
 
 from authentic2 import hooks, crypto
 from authentic2.attributes_ng.engine import get_attributes
diff --git a/tests/conftest.py b/tests/conftest.py
index b5b5e78c..d18add5d 100644
--- a/tests/conftest.py
+++ b/tests/conftest.py
@@ -2,13 +2,13 @@
 
 import pytest
 import mock
-import urlparse
 
 import django_webtest
 
 from django.contrib.auth import get_user_model
 from django_rbac.utils import get_ou_model, get_role_model
 from django.conf import settings
+from django.utils.six.moves.urllib import parse as urlparse
 
 from pytest_django.migrations import DisableMigrations
 
diff --git a/tests/test_admin.py b/tests/test_admin.py
index ba48ccac..90955bd8 100644
--- a/tests/test_admin.py
+++ b/tests/test_admin.py
@@ -1,9 +1,8 @@
 # -*- coding: utf-8 -*-
 
-from urlparse import urlparse
-
 from authentic2.custom_user.models import User
 from authentic2.models import Attribute
+from django.utils.six.moves.urllib.parse import urlparse
 
 import utils
 
diff --git a/tests/test_all.py b/tests/test_all.py
index 98ad6d16..71f2278e 100644
--- a/tests/test_all.py
+++ b/tests/test_all.py
@@ -1,6 +1,5 @@
 # -*- coding: utf-8 -*-
 import json
-import urlparse
 import base64
 
 import pytest
@@ -14,6 +13,7 @@ from django.core.serializers.json import DjangoJSONEncoder
 from django.contrib.auth import get_user_model
 from django.contrib.contenttypes.models import ContentType
 from django.utils.translation import ugettext as _
+from django.utils.six.moves.urllib import parse as urlparse
 
 from rest_framework import test
 from rest_framework import status
diff --git a/tests/test_auth_oidc.py b/tests/test_auth_oidc.py
index 4dea423d..2420e4c0 100644
--- a/tests/test_auth_oidc.py
+++ b/tests/test_auth_oidc.py
@@ -1,7 +1,6 @@
 # -*- coding: utf-8 -*-
 import datetime
 import pytest
-import urlparse
 import json
 import time
 
@@ -14,6 +13,7 @@ from django.utils.timezone import utc
 from django.core.urlresolvers import reverse
 from django.contrib.auth import get_user_model
 from django.utils.timezone import now
+from django.utils.six.moves.urllib import parse as urlparse
 
 from django_rbac.utils import get_ou_model
 
diff --git a/tests/test_cas.py b/tests/test_cas.py
index acb940d5..997393a0 100644
--- a/tests/test_cas.py
+++ b/tests/test_cas.py
@@ -1,8 +1,6 @@
-import urlparse
-
-
 from django.test.client import RequestFactory, Client
 from django.test.utils import override_settings
+from django.utils.six.moves.urllib import parse as urlparse
 
 
 from authentic2.compat import get_user_model
diff --git a/tests/test_idp_oidc.py b/tests/test_idp_oidc.py
index 82635eb0..514fea9d 100644
--- a/tests/test_idp_oidc.py
+++ b/tests/test_idp_oidc.py
@@ -1,4 +1,3 @@
-import urlparse
 import base64
 import json
 import datetime
@@ -16,6 +15,7 @@ from django.db import connection
 from django.db.migrations.executor import MigrationExecutor
 from django.utils.timezone import now
 from django.contrib.auth import get_user_model
+from django.utils.six.moves.urllib import parse as urlparse
 
 
 User = get_user_model()
diff --git a/tests/test_idp_saml2.py b/tests/test_idp_saml2.py
index 3e0748f2..cb2ebd44 100644
--- a/tests/test_idp_saml2.py
+++ b/tests/test_idp_saml2.py
@@ -3,7 +3,6 @@ import datetime
 import base64
 import unittest
 import StringIO
-import urlparse
 from lxml.html import parse
 
 from django.test import Client
@@ -12,6 +11,7 @@ from django.contrib.auth import get_user_model, REDIRECT_FIELD_NAME
 from django.core.urlresolvers import reverse
 from django.core.files import File
 from django.utils.translation import gettext as _
+from django.utils.six.moves.urllib import parse as urlparse
 
 from authentic2.saml import models as saml_models
 from authentic2.a2_rbac.models import Role, OrganizationalUnit
diff --git a/tests/test_login.py b/tests/test_login.py
index c5a22e5e..a736700e 100644
--- a/tests/test_login.py
+++ b/tests/test_login.py
@@ -15,8 +15,8 @@
 # along with this program.  If not, see <http://www.gnu.org/licenses/>.
 
 import pytest
-from urllib import quote
 
+from django.utils.six.moves.urllib.parse import quote
 from django.contrib.auth import get_user_model
 
 from utils import login
diff --git a/tests/test_manager.py b/tests/test_manager.py
index c23839b2..b5da74c6 100644
--- a/tests/test_manager.py
+++ b/tests/test_manager.py
@@ -2,7 +2,6 @@
 
 import pytest
 import json
-from urlparse import urlparse
 
 from django.core.urlresolvers import reverse
 from django.core import mail
@@ -13,6 +12,7 @@ from authentic2.a2_rbac.utils import get_default_ou
 
 from django_rbac.utils import get_ou_model, get_role_model
 from django.contrib.auth import get_user_model
+from django.utils.six.moves.urllib.parse import urlparse
 from utils import login, get_link_from_mail
 
 
diff --git a/tests/test_registration.py b/tests/test_registration.py
index a6a09cd5..a8e5b019 100644
--- a/tests/test_registration.py
+++ b/tests/test_registration.py
@@ -1,11 +1,11 @@
 # -*- coding: utf-8 -*-
 
 import re
-from urlparse import urlparse
 
 from django.core.urlresolvers import reverse
 from django.contrib.auth import get_user_model, REDIRECT_FIELD_NAME
 from django.utils.http import urlquote
+from django.utils.six.moves.urllib.parse import urlparse
 
 from authentic2 import utils, models
 
diff --git a/tests/test_views.py b/tests/test_views.py
index 6cab8874..1963564e 100644
--- a/tests/test_views.py
+++ b/tests/test_views.py
@@ -1,9 +1,8 @@
-from urlparse import urlparse
-
 from utils import login
 import pytest
 
 from django.core.urlresolvers import reverse
+from django.utils.six.moves.urllib.parse import urlparse
 
 from authentic2.custom_user.models import User
 
diff --git a/tests/utils.py b/tests/utils.py
index 277edf31..29e52ae1 100644
--- a/tests/utils.py
+++ b/tests/utils.py
@@ -1,6 +1,5 @@
 import re
 import base64
-import urlparse
 from contextlib import contextmanager
 
 from lxml import etree
@@ -10,6 +9,7 @@ from django.core.urlresolvers import reverse
 from django.conf import settings
 from django.utils.encoding import iri_to_uri
 from django.shortcuts import resolve_url
+from django.utils.six.moves.urllib import parse as urlparse
 
 from authentic2 import utils
 
-- 
2.20.1

