Ticket #15619: ticket15619-2.diff

File ticket15619-2.diff, 16.0 KB (added by ashchristopher, 3 years ago)

Updated code, fixed regression tests and added new regression tests.

  • django/contrib/admin/sites.py

    diff --git a/django/contrib/admin/sites.py b/django/contrib/admin/sites.py
    old mode 100644
    new mode 100755
    index 9bb9f4a..d10230f
    a b class AdminSite(object): 
    293293        This should *not* assume the user is already logged in.
    294294        """
    295295        from django.contrib.auth.views import logout
    296         defaults = {
    297             'current_app': self.name,
    298             'extra_context': extra_context or {},
    299         }
    300         if self.logout_template is not None:
    301             defaults['template_name'] = self.logout_template
    302         return logout(request, **defaults)
     296
     297        if request.method == "POST":
     298            defaults = {
     299                'current_app': self.name,
     300                'extra_context': extra_context or {},
     301            }
     302
     303            if self.logout_template is not None:
     304                defaults['template_name'] = self.logout_template
     305
     306            return logout(request, **defaults)
     307        else:
     308            context = {
     309                'title' : _('Are you sure?'),
     310            }
     311            return TemplateResponse(request, 'admin/logout_confirmation.html', context)
     312       
    303313
    304314    @never_cache
    305315    def login(self, request, extra_context=None):
  • django/contrib/admin/templates/admin/base.html

    diff --git a/django/contrib/admin/templates/admin/base.html b/django/contrib/admin/templates/admin/base.html
    old mode 100644
    new mode 100755
    index 4b3c429..4482bb8
    a b  
    77<!--[if lte IE 7]><link rel="stylesheet" type="text/css" href="{% block stylesheet_ie %}{% static "admin/css/ie.css" %}{% endblock %}" /><![endif]-->
    88{% if LANGUAGE_BIDI %}<link rel="stylesheet" type="text/css" href="{% block stylesheet_rtl %}{% static "admin/css/rtl.css" %}{% endblock %}" />{% endif %}
    99<script type="text/javascript">window.__admin_media_prefix__ = "{% filter escapejs %}{% static "admin/" %}{% endfilter %}";</script>
     10<script type="text/javascript" src="{% static "admin/js/jquery.min.js" %}"></script>
     11<script type="text/javascript" src="{% static "admin/js/jquery.init.js" %}"></script>
     12<script id="admin-logout-template" defer type="text/html">
     13    <form id="logout-form" action="{% url 'admin:logout' %}" method="post">{% csrf_token %}</form>
     14</script>
     15<script type="text/javascript">
     16    (function($) {
     17        $(document).ready(function() {
     18            $('a[href="{% url 'admin:logout' %}"]').click(function(ev) {
     19                ev.preventDefault();
     20                $('body').append($('#admin-logout-template').html());
     21                $('#logout-form').submit();
     22            });
     23        });
     24    })(django.jQuery);
     25</script>
     26
    1027{% block extrahead %}{% endblock %}
    1128{% block blockbots %}<meta name="robots" content="NONE,NOARCHIVE" />{% endblock %}
    1229</head>
  • new file django/contrib/admin/templates/admin/logout_confirmation.html

    diff --git a/django/contrib/admin/templates/admin/logout_confirmation.html b/django/contrib/admin/templates/admin/logout_confirmation.html
    new file mode 100755
    index 0000000..17f08c5
    - +  
     1{% extends "admin/base_site.html" %}
     2{% load i18n %}
     3
     4{% block breadcrumbs %}
     5    <div class="breadcrumbs">
     6        <a href="../">{% trans "Home" %}</a> &rsaquo;
     7    </div>
     8{% endblock %}
     9
     10
     11
     12{% block content %}
     13    <p>{% blocktrans %}Are you sure you want to logout?{% endblocktrans %}</p>
     14    <form action="" method="post">
     15        {% csrf_token %}
     16        <div>
     17            <input type="hidden" name="post" value="yes" />
     18            <input type="submit" value="{% trans "Yes, I'm sure" %}" />
     19        </div>
     20    </form>
     21{% endblock %}
     22 No newline at end of file
  • tests/regressiontests/admin_views/tests.py

    diff --git a/tests/regressiontests/admin_views/tests.py b/tests/regressiontests/admin_views/tests.py
    old mode 100644
    new mode 100755
    index 22b65a6..348e2af
    a b class CustomModelAdminTest(AdminViewBasicTest): 
    618618        self.assertTrue('Hello from a custom login template' in request.content)
    619619
    620620    def testCustomAdminSiteLogoutTemplate(self):
    621         request = self.client.get('/test_admin/admin2/logout/')
     621        request = self.client.post('/test_admin/admin2/logout/')
    622622        self.assertIsInstance(request, TemplateResponse)
    623623        self.assertTemplateUsed(request, 'custom_admin/logout.html')
    624624        self.assertTrue('Hello from a custom logout template' in request.content)
    class AdminViewPermissionsTest(TestCase): 
    745745        login = self.client.post('/test_admin/admin/', self.super_login)
    746746        self.assertRedirects(login, '/test_admin/admin/')
    747747        self.assertFalse(login.context)
    748         self.client.get('/test_admin/admin/logout/')
     748        self.client.post('/test_admin/admin/logout/')
    749749
    750750        # Test if user enters e-mail address
    751751        request = self.client.get('/test_admin/admin/')
    class AdminViewPermissionsTest(TestCase): 
    767767        login = self.client.post('/test_admin/admin/', self.adduser_login)
    768768        self.assertRedirects(login, '/test_admin/admin/')
    769769        self.assertFalse(login.context)
    770         self.client.get('/test_admin/admin/logout/')
     770        self.client.post('/test_admin/admin/logout/')
    771771
    772772        # Change User
    773773        request = self.client.get('/test_admin/admin/')
    class AdminViewPermissionsTest(TestCase): 
    775775        login = self.client.post('/test_admin/admin/', self.changeuser_login)
    776776        self.assertRedirects(login, '/test_admin/admin/')
    777777        self.assertFalse(login.context)
    778         self.client.get('/test_admin/admin/logout/')
     778        self.client.post('/test_admin/admin/logout/')
    779779
    780780        # Delete User
    781781        request = self.client.get('/test_admin/admin/')
    class AdminViewPermissionsTest(TestCase): 
    783783        login = self.client.post('/test_admin/admin/', self.deleteuser_login)
    784784        self.assertRedirects(login, '/test_admin/admin/')
    785785        self.assertFalse(login.context)
    786         self.client.get('/test_admin/admin/logout/')
     786        self.client.post('/test_admin/admin/logout/')
    787787
    788788        # Regular User should not be able to login.
    789789        request = self.client.get('/test_admin/admin/')
    class AdminViewPermissionsTest(TestCase): 
    828828        post = self.client.post('/test_admin/admin/admin_views/article/add/', add_dict)
    829829        self.assertEqual(post.status_code, 403)
    830830        self.assertEqual(Article.objects.all().count(), 3)
    831         self.client.get('/test_admin/admin/logout/')
     831        self.client.post('/test_admin/admin/logout/')
    832832
    833833        # Add user may login and POST to add view, then redirect to admin root
    834834        self.client.get('/test_admin/admin/')
    class AdminViewPermissionsTest(TestCase): 
    843843        self.assertEqual(Article.objects.all().count(), 4)
    844844        self.assertEqual(len(mail.outbox), 1)
    845845        self.assertEqual(mail.outbox[0].subject, 'Greetings from a created object')
    846         self.client.get('/test_admin/admin/logout/')
     846        self.client.post('/test_admin/admin/logout/')
    847847
    848848        # Super can add too, but is redirected to the change list view
    849849        self.client.get('/test_admin/admin/')
    class AdminViewPermissionsTest(TestCase): 
    855855        post = self.client.post('/test_admin/admin/admin_views/article/add/', add_dict)
    856856        self.assertRedirects(post, '/test_admin/admin/admin_views/article/')
    857857        self.assertEqual(Article.objects.all().count(), 5)
    858         self.client.get('/test_admin/admin/logout/')
     858        self.client.post('/test_admin/admin/logout/')
    859859
    860860        # 8509 - if a normal user is already logged in, it is possible
    861861        # to change user into the superuser without error
    class AdminViewPermissionsTest(TestCase): 
    883883        self.assertEqual(request.status_code, 403)
    884884        post = self.client.post('/test_admin/admin/admin_views/article/1/', change_dict)
    885885        self.assertEqual(post.status_code, 403)
    886         self.client.get('/test_admin/admin/logout/')
     886        self.client.post('/test_admin/admin/logout/')
    887887
    888888        # change user can view all items and edit them
    889889        self.client.get('/test_admin/admin/')
    class AdminViewPermissionsTest(TestCase): 
    907907        self.assertEqual(request.status_code, 200)
    908908        self.assertTrue('Please correct the errors below.' in post.content,
    909909                        'Plural error message not found in response to post with multiple errors.')
    910         self.client.get('/test_admin/admin/logout/')
     910        self.client.post('/test_admin/admin/logout/')
    911911
    912912        # Test redirection when using row-level change permissions. Refs #11513.
    913913        RowLevelChangePermissionModel.objects.create(id=1, name="odd id")
    class AdminViewPermissionsTest(TestCase): 
    924924            request = self.client.post('/test_admin/admin/admin_views/rowlevelchangepermissionmodel/2/', {'name': 'changed'})
    925925            self.assertEqual(RowLevelChangePermissionModel.objects.get(id=2).name, 'changed')
    926926            self.assertRedirects(request, '/test_admin/admin/')
    927             self.client.get('/test_admin/admin/logout/')
     927            self.client.post('/test_admin/admin/logout/')
    928928        for login_dict in [self.joepublic_login, self.no_username_login]:
    929929            self.client.post('/test_admin/admin/', login_dict)
    930930            request = self.client.get('/test_admin/admin/admin_views/rowlevelchangepermissionmodel/1/')
    class AdminViewPermissionsTest(TestCase): 
    941941            self.assertEqual(RowLevelChangePermissionModel.objects.get(id=2).name, 'changed')
    942942            self.assertEqual(request.status_code, 200)
    943943            self.assertContains(request, 'login-form')
    944             self.client.get('/test_admin/admin/logout/')
     944            self.client.post('/test_admin/admin/logout/')
    945945
    946946    def testConditionallyShowAddSectionLink(self):
    947947        """
    class AdminViewPermissionsTest(TestCase): 
    10041004        request = self.client.get('/test_admin/admin/admin_views/customarticle/%d/history/' % article_pk)
    10051005        self.assertTemplateUsed(request, 'custom_admin/object_history.html')
    10061006
    1007         self.client.get('/test_admin/admin/logout/')
     1007        self.client.post('/test_admin/admin/logout/')
    10081008
    10091009    def testDeleteView(self):
    10101010        """Delete view should restrict access and actually delete items."""
    class AdminViewPermissionsTest(TestCase): 
    10191019        post = self.client.post('/test_admin/admin/admin_views/article/1/delete/', delete_dict)
    10201020        self.assertEqual(post.status_code, 403)
    10211021        self.assertEqual(Article.objects.all().count(), 3)
    1022         self.client.get('/test_admin/admin/logout/')
     1022        self.client.post('/test_admin/admin/logout/')
    10231023
    10241024        # Delete user can delete
    10251025        self.client.get('/test_admin/admin/')
    class AdminViewPermissionsTest(TestCase): 
    10381038        article_ct = ContentType.objects.get_for_model(Article)
    10391039        logged = LogEntry.objects.get(content_type=article_ct, action_flag=DELETION)
    10401040        self.assertEqual(logged.object_id, u'1')
    1041         self.client.get('/test_admin/admin/logout/')
     1041        self.client.post('/test_admin/admin/logout/')
    10421042
    10431043    def testDisabledPermissionsWhenLoggedIn(self):
    10441044        self.client.login(username='super', password='secret')
    class SecureViewTests(TestCase): 
    13391339        login = self.client.post('/test_admin/admin/secure-view/', self.super_login)
    13401340        self.assertRedirects(login, '/test_admin/admin/secure-view/')
    13411341        self.assertFalse(login.context)
    1342         self.client.get('/test_admin/admin/logout/')
     1342        self.client.post('/test_admin/admin/logout/')
    13431343        # make sure the view removes test cookie
    13441344        self.assertEqual(self.client.session.test_cookie_worked(), False)
    13451345
    class SecureViewTests(TestCase): 
    13631363        login = self.client.post('/test_admin/admin/secure-view/', self.adduser_login)
    13641364        self.assertRedirects(login, '/test_admin/admin/secure-view/')
    13651365        self.assertFalse(login.context)
    1366         self.client.get('/test_admin/admin/logout/')
     1366        self.client.post('/test_admin/admin/logout/')
    13671367
    13681368        # Change User
    13691369        request = self.client.get('/test_admin/admin/secure-view/')
    class SecureViewTests(TestCase): 
    13711371        login = self.client.post('/test_admin/admin/secure-view/', self.changeuser_login)
    13721372        self.assertRedirects(login, '/test_admin/admin/secure-view/')
    13731373        self.assertFalse(login.context)
    1374         self.client.get('/test_admin/admin/logout/')
     1374        self.client.post('/test_admin/admin/logout/')
    13751375
    13761376        # Delete User
    13771377        request = self.client.get('/test_admin/admin/secure-view/')
    class SecureViewTests(TestCase): 
    13791379        login = self.client.post('/test_admin/admin/secure-view/', self.deleteuser_login)
    13801380        self.assertRedirects(login, '/test_admin/admin/secure-view/')
    13811381        self.assertFalse(login.context)
    1382         self.client.get('/test_admin/admin/logout/')
     1382        self.client.post('/test_admin/admin/logout/')
    13831383
    13841384        # Regular User should not be able to login.
    13851385        request = self.client.get('/test_admin/admin/secure-view/')
    class AdminViewListEditable(TestCase): 
    15021502        # 4 action inputs (3 regular checkboxes, 1 checkbox to select all)
    15031503        # main form submit button = 1
    15041504        # search field and search submit button = 2
    1505         # CSRF field = 1
     1505        # CSRF field = 1 + 1 (the logout form has a CSRF field and is on every page in the admin.)
    15061506        # field to track 'select all' across paginated views = 1
    15071507        # 6 + 3 + 4 + 1 + 2 + 1 + 1 = 18 inputs
    1508         self.assertEqual(response.content.count("<input"), 18)
     1508        self.assertEqual(response.content.count("<input"), 19)
    15091509        # 1 select per object = 3 selects
    15101510        self.assertEqual(response.content.count("<select"), 4)
    15111511
    class NeverCacheTests(TestCase): 
    26902690
    26912691    def testLogout(self):
    26922692        "Check the never-cache status of logout view"
    2693         response = self.client.get('/test_admin/admin/logout/')
     2693        response = self.client.post('/test_admin/admin/logout/')
    26942694        self.assertEqual(get_max_age(response), 0)
    26952695
    26962696    def testPasswordChange(self):
    class ReadonlyTest(TestCase): 
    27482748        self.assertEqual(response.status_code, 200)
    27492749        self.assertNotContains(response, 'name="posted"')
    27502750        # 3 fields + 2 submit buttons + 4 inline management form fields, + 2
    2751         # hidden fields for inlines + 1 field for the inline + 2 empty form
    2752         self.assertEqual(response.content.count("<input"), 14)
     2751        # hidden fields for inlines + 1 field for the inline + 2 empty form + 1
     2752        # input for csrf token on logout form in js.
     2753        self.assertEqual(response.content.count("<input"), 15)
    27532754        self.assertContains(response, formats.localize(datetime.date.today()))
    27542755        self.assertContains(response,
    27552756            "<label>Awesomeness level:</label>")
    class AdminCustomSaveRelatedTests(TestCase): 
    32223223
    32233224        self.assertEqual('Josh Stone', Parent.objects.latest('id').name)
    32243225        self.assertEqual([u'Catherine Stone', u'Paul Stone'], children_names)
     3226
     3227
     3228class AdminViewLogoutTest(TestCase):
     3229    fixtures = ['admin-views-users.xml', ]
     3230
     3231    def setUp(self):
     3232        self.client.login(username='super', password='secret')
     3233
     3234    def tearDown(self):
     3235        self.client.logout()
     3236
     3237    def test_logout_attempt_using_get(self):
     3238        response = self.client.get('/test_admin/admin/logout/')
     3239        self.assertEqual(response.status_code, 200)
     3240        # since we are issuing a GET request we should be rendering
     3241        # the confirmation template
     3242        self.assertTemplateUsed(response, 'admin/logout_confirmation.html')
     3243       
     3244    def test_logout_attempt_using_post(self):
     3245        # 15619 - you must POST to the logout view to actually logout.
     3246        response = self.client.post('/test_admin/admin/logout/')
     3247        self.assertEqual(response.status_code, 200)
     3248        # since we are issuing a POST request we should be logging out the
     3249        # user immediatly.
     3250        self.assertTemplateUsed(response, 'registration/logged_out.html')
     3251
Back to Top