1
0
mirror of https://github.com/netbox-community/netbox.git synced 2024-05-10 07:54:54 +00:00

all: fix error message on trying to delete protected models (references #3211)

This commit is contained in:
hellerve
2019-05-28 16:11:49 +02:00
parent 473dafc2c8
commit cc87d99017
2 changed files with 25 additions and 2 deletions

View File

@ -1,3 +1,5 @@
import json
from django.urls import reverse from django.urls import reverse
from netaddr import IPNetwork from netaddr import IPNetwork
from rest_framework import status from rest_framework import status
@ -870,6 +872,8 @@ class VLANTest(APITestCase):
self.vlan2 = VLAN.objects.create(vid=2, name='Test VLAN 2') self.vlan2 = VLAN.objects.create(vid=2, name='Test VLAN 2')
self.vlan3 = VLAN.objects.create(vid=3, name='Test VLAN 3') self.vlan3 = VLAN.objects.create(vid=3, name='Test VLAN 3')
self.prefix1 = Prefix.objects.create(prefix=IPNetwork('192.168.1.0/24'))
def test_get_vlan(self): def test_get_vlan(self):
url = reverse('ipam-api:vlan-detail', kwargs={'pk': self.vlan1.pk}) url = reverse('ipam-api:vlan-detail', kwargs={'pk': self.vlan1.pk})
@ -960,6 +964,20 @@ class VLANTest(APITestCase):
self.assertHttpStatus(response, status.HTTP_204_NO_CONTENT) self.assertHttpStatus(response, status.HTTP_204_NO_CONTENT)
self.assertEqual(VLAN.objects.count(), 2) self.assertEqual(VLAN.objects.count(), 2)
def test_delete_vlan_with_prefix(self):
self.prefix1.vlan = self.vlan1
self.prefix1.save()
url = reverse('ipam-api:vlan-detail', kwargs={'pk': self.vlan1.pk})
response = self.client.delete(url, **self.header)
# can't use assertHttpStatus here because we don't have response.data
self.assertEqual(response.status_code, 403)
content = json.loads(response.content.decode('utf-8'))
self.assertIn('detail', content)
self.assertTrue(content['detail'].startswith('You tried deleting a model that is protected by:'))
class ServiceTest(APITestCase): class ServiceTest(APITestCase):

View File

@ -1,6 +1,7 @@
from django.conf import settings from django.conf import settings
from django.db import ProgrammingError from django.db import ProgrammingError
from django.http import Http404, HttpResponseRedirect from django.http import Http404, HttpResponseRedirect, JsonResponse
from django.db.models import ProtectedError
from django.urls import reverse from django.urls import reverse
from .views import server_error from .views import server_error
@ -62,6 +63,11 @@ class ExceptionHandlingMiddleware(object):
if isinstance(exception, Http404): if isinstance(exception, Http404):
return return
elif isinstance(exception, ProtectedError):
models = '\n'.join('- {} ({})'.format(o, o._meta) for o in exception.protected_objects.all())
msg = 'You tried deleting a model that is protected by:\n{}'.format(models)
return JsonResponse({'detail': msg}, status=403)
# Determine the type of exception. If it's a common issue, return a custom error page with instructions. # Determine the type of exception. If it's a common issue, return a custom error page with instructions.
custom_template = None custom_template = None
if isinstance(exception, ProgrammingError): if isinstance(exception, ProgrammingError):
@ -70,7 +76,6 @@ class ExceptionHandlingMiddleware(object):
custom_template = 'exceptions/import_error.html' custom_template = 'exceptions/import_error.html'
elif isinstance(exception, PermissionError): elif isinstance(exception, PermissionError):
custom_template = 'exceptions/permission_error.html' custom_template = 'exceptions/permission_error.html'
# Return a custom error message, or fall back to Django's default 500 error handling # Return a custom error message, or fall back to Django's default 500 error handling
if custom_template: if custom_template:
return server_error(request, template_name=custom_template) return server_error(request, template_name=custom_template)