Repository: django-cms/django-cms

Issue:
Add setting to not show the CMS Toolbar for anonymous users
[This line](https://github.com/divio/django-cms/blob/develop/cms/middleware/toolbar.py#L69) lets anonymous users see the CMS toolbar to login when `?edit` is added.

I wish there was a setting to disable showing the toolbar for anonymous users. My concern is that a link containing `?edit` (e.g. [a link like this](http://divio.ch/en/?edit)) will inadvertently spread around and visitors will be confused by the toolbar showing up. Developers may also wish to additionally protect their login form, reduce attack surface against XSS, hide the identity of their CMS etc.

If you feel like this is a reasonable feature request and worth a setting, I'm happy to provide a PR.



Discussion:
I think a setting to disable the toolbar login is acceptable, but it should be off by default, as otherwise it's not possible to login from the frontend, which is a feature we want to be enabled by default


Resolving patch:
diff --git a/cms/middleware/toolbar.py b/cms/middleware/toolbar.py
--- a/cms/middleware/toolbar.py
+++ b/cms/middleware/toolbar.py
@@ -60,13 +60,14 @@ def process_request(self, request):
         edit_off = get_cms_setting('CMS_TOOLBAR_URL__EDIT_OFF')
         build = get_cms_setting('CMS_TOOLBAR_URL__BUILD')
         disable = get_cms_setting('CMS_TOOLBAR_URL__DISABLE')
+        anonymous_on = get_cms_setting('TOOLBAR_ANONYMOUS_ON')
 
         if disable in request.GET:
             request.session['cms_toolbar_disabled'] = True
         if edit_on in request.GET:  # If we actively enter edit mode, we should show the toolbar in any case
             request.session['cms_toolbar_disabled'] = False
 
-        if request.user.is_staff or request.user.is_anonymous():
+        if request.user.is_staff or (anonymous_on and request.user.is_anonymous()):
             if edit_on in request.GET and not request.session.get('cms_edit', False):
                 if not request.session.get('cms_edit', False):
                     menu_pool.clear()
diff --git a/cms/utils/conf.py b/cms/utils/conf.py
--- a/cms/utils/conf.py
+++ b/cms/utils/conf.py
@@ -55,6 +55,7 @@ def wrapper():
     'UNIHANDECODE_DEFAULT_DECODER': 'diacritic',
     'MAX_PAGE_PUBLISH_REVERSIONS': 10,
     'MAX_PAGE_HISTORY_REVERSIONS': 15,
+    'TOOLBAR_ANONYMOUS_ON': True,
     'TOOLBAR_URL__EDIT_ON': 'edit',
     'TOOLBAR_URL__EDIT_OFF': 'edit_off',
     'TOOLBAR_URL__BUILD': 'build',


Test patch:
diff --git a/cms/tests/toolbar.py b/cms/tests/toolbar.py
--- a/cms/tests/toolbar.py
+++ b/cms/tests/toolbar.py
@@ -310,6 +310,13 @@ def test_show_toolbar_login_anonymous(self):
         self.assertEqual(response.status_code, 200)
         self.assertContains(response, 'cms_form-login')
 
+    @override_settings(CMS_TOOLBAR_ANONYMOUS_ON=False)
+    def test_hide_toolbar_login_anonymous_setting(self):
+        create_page("toolbar-page", "nav_playground.html", "en", published=True)
+        response = self.client.get('/en/?%s' % get_cms_setting('CMS_TOOLBAR_URL__EDIT_ON'))
+        self.assertEqual(response.status_code, 200)
+        self.assertNotContains(response, 'cms_form-login')
+
     def test_hide_toolbar_login_nonstaff(self):
         create_page("toolbar-page", "nav_playground.html", "en", published=True)
         with self.login_user_context(self.get_nonstaff()):