mirror of
https://github.com/netbox-community/netbox.git
synced 2024-05-10 07:54:54 +00:00
Rename ExportTemplate.content_types to object_types & use ObjectType proxy
This commit is contained in:
@ -216,7 +216,7 @@ class CustomLinkSerializer(ValidatedModelSerializer):
|
||||
|
||||
class ExportTemplateSerializer(ValidatedModelSerializer):
|
||||
url = serializers.HyperlinkedIdentityField(view_name='extras-api:exporttemplate-detail')
|
||||
content_types = ContentTypeField(
|
||||
object_types = ContentTypeField(
|
||||
queryset=ObjectType.objects.with_feature('export_templates'),
|
||||
many=True
|
||||
)
|
||||
@ -230,7 +230,7 @@ class ExportTemplateSerializer(ValidatedModelSerializer):
|
||||
class Meta:
|
||||
model = ExportTemplate
|
||||
fields = [
|
||||
'id', 'url', 'display', 'content_types', 'name', 'description', 'template_code', 'mime_type',
|
||||
'id', 'url', 'display', 'object_types', 'name', 'description', 'template_code', 'mime_type',
|
||||
'file_extension', 'as_attachment', 'data_source', 'data_path', 'data_file', 'data_synced', 'created',
|
||||
'last_updated',
|
||||
]
|
||||
|
@ -217,10 +217,10 @@ class ExportTemplateFilterSet(BaseFilterSet):
|
||||
method='search',
|
||||
label=_('Search'),
|
||||
)
|
||||
content_type_id = MultiValueNumberFilter(
|
||||
field_name='content_types__id'
|
||||
object_types_id = MultiValueNumberFilter(
|
||||
field_name='object_types__id'
|
||||
)
|
||||
content_types = ContentTypeFilter()
|
||||
object_types = ContentTypeFilter()
|
||||
data_source_id = django_filters.ModelMultipleChoiceFilter(
|
||||
queryset=DataSource.objects.all(),
|
||||
label=_('Data source (ID)'),
|
||||
@ -232,7 +232,7 @@ class ExportTemplateFilterSet(BaseFilterSet):
|
||||
|
||||
class Meta:
|
||||
model = ExportTemplate
|
||||
fields = ['id', 'content_types', 'name', 'description', 'data_synced']
|
||||
fields = ['id', 'object_types', 'name', 'description', 'data_synced']
|
||||
|
||||
def search(self, queryset, name, value):
|
||||
if not value.strip():
|
||||
|
@ -126,8 +126,8 @@ class CustomLinkImportForm(CSVModelForm):
|
||||
|
||||
|
||||
class ExportTemplateImportForm(CSVModelForm):
|
||||
content_types = CSVMultipleContentTypeField(
|
||||
label=_('Content types'),
|
||||
object_types = CSVMultipleContentTypeField(
|
||||
label=_('Object types'),
|
||||
queryset=ObjectType.objects.with_feature('export_templates'),
|
||||
help_text=_("One or more assigned object types")
|
||||
)
|
||||
@ -135,7 +135,7 @@ class ExportTemplateImportForm(CSVModelForm):
|
||||
class Meta:
|
||||
model = ExportTemplate
|
||||
fields = (
|
||||
'name', 'content_types', 'description', 'mime_type', 'file_extension', 'as_attachment', 'template_code',
|
||||
'name', 'object_types', 'description', 'mime_type', 'file_extension', 'as_attachment', 'template_code',
|
||||
)
|
||||
|
||||
|
||||
|
@ -139,7 +139,7 @@ class ExportTemplateFilterForm(SavedFiltersMixin, FilterForm):
|
||||
fieldsets = (
|
||||
(None, ('q', 'filter_id')),
|
||||
(_('Data'), ('data_source_id', 'data_file_id')),
|
||||
(_('Attributes'), ('content_type_id', 'mime_type', 'file_extension', 'as_attachment')),
|
||||
(_('Attributes'), ('object_types_id', 'mime_type', 'file_extension', 'as_attachment')),
|
||||
)
|
||||
data_source_id = DynamicModelMultipleChoiceField(
|
||||
queryset=DataSource.objects.all(),
|
||||
@ -154,7 +154,7 @@ class ExportTemplateFilterForm(SavedFiltersMixin, FilterForm):
|
||||
'source_id': '$data_source_id'
|
||||
}
|
||||
)
|
||||
content_type_id = ContentTypeMultipleChoiceField(
|
||||
object_types_id = ContentTypeMultipleChoiceField(
|
||||
queryset=ObjectType.objects.with_feature('export_templates'),
|
||||
required=False,
|
||||
label=_('Content types')
|
||||
|
@ -151,8 +151,8 @@ class CustomLinkForm(forms.ModelForm):
|
||||
|
||||
|
||||
class ExportTemplateForm(SyncedDataMixin, forms.ModelForm):
|
||||
content_types = ContentTypeMultipleChoiceField(
|
||||
label=_('Content types'),
|
||||
object_types = ContentTypeMultipleChoiceField(
|
||||
label=_('Object types'),
|
||||
queryset=ObjectType.objects.with_feature('export_templates')
|
||||
)
|
||||
template_code = forms.CharField(
|
||||
@ -162,7 +162,7 @@ class ExportTemplateForm(SyncedDataMixin, forms.ModelForm):
|
||||
)
|
||||
|
||||
fieldsets = (
|
||||
(_('Export Template'), ('name', 'content_types', 'description', 'template_code')),
|
||||
(_('Export Template'), ('name', 'object_types', 'description', 'template_code')),
|
||||
(_('Data Source'), ('data_source', 'data_file', 'auto_sync_enabled')),
|
||||
(_('Rendering'), ('mime_type', 'file_extension', 'as_attachment')),
|
||||
)
|
||||
|
@ -71,7 +71,7 @@ class ExportTemplateType(ObjectType):
|
||||
|
||||
class Meta:
|
||||
model = models.ExportTemplate
|
||||
exclude = ('content_types', )
|
||||
exclude = ('object_types', )
|
||||
filterset_class = filtersets.ExportTemplateFilterSet
|
||||
|
||||
|
||||
|
@ -50,4 +50,16 @@ class Migration(migrations.Migration):
|
||||
name='object_types',
|
||||
field=models.ManyToManyField(related_name='event_rules', to='core.objecttype'),
|
||||
),
|
||||
|
||||
# Export templates
|
||||
migrations.RenameField(
|
||||
model_name='exporttemplate',
|
||||
old_name='content_types',
|
||||
new_name='object_types',
|
||||
),
|
||||
migrations.AlterField(
|
||||
model_name='exporttemplate',
|
||||
name='object_types',
|
||||
field=models.ManyToManyField(related_name='export_templates', to='core.objecttype'),
|
||||
),
|
||||
]
|
||||
|
@ -409,8 +409,8 @@ class CustomLink(CloningMixin, ExportTemplatesMixin, ChangeLoggedModel):
|
||||
|
||||
|
||||
class ExportTemplate(SyncedDataMixin, CloningMixin, ExportTemplatesMixin, ChangeLoggedModel):
|
||||
content_types = models.ManyToManyField(
|
||||
to='contenttypes.ContentType',
|
||||
object_types = models.ManyToManyField(
|
||||
to='core.ObjectType',
|
||||
related_name='export_templates',
|
||||
help_text=_('The object type(s) to which this template applies.')
|
||||
)
|
||||
|
@ -139,8 +139,8 @@ class ExportTemplateTable(NetBoxTable):
|
||||
verbose_name=_('Name'),
|
||||
linkify=True
|
||||
)
|
||||
content_types = columns.ContentTypesColumn(
|
||||
verbose_name=_('Content Types'),
|
||||
object_types = columns.ContentTypesColumn(
|
||||
verbose_name=_('Object Types'),
|
||||
)
|
||||
as_attachment = columns.BooleanColumn(
|
||||
verbose_name=_('As Attachment'),
|
||||
@ -161,11 +161,11 @@ class ExportTemplateTable(NetBoxTable):
|
||||
class Meta(NetBoxTable.Meta):
|
||||
model = ExportTemplate
|
||||
fields = (
|
||||
'pk', 'id', 'name', 'content_types', 'description', 'mime_type', 'file_extension', 'as_attachment',
|
||||
'pk', 'id', 'name', 'object_types', 'description', 'mime_type', 'file_extension', 'as_attachment',
|
||||
'data_source', 'data_file', 'data_synced', 'created', 'last_updated',
|
||||
)
|
||||
default_columns = (
|
||||
'pk', 'name', 'content_types', 'description', 'mime_type', 'file_extension', 'as_attachment', 'is_synced',
|
||||
'pk', 'name', 'object_types', 'description', 'mime_type', 'file_extension', 'as_attachment', 'is_synced',
|
||||
)
|
||||
|
||||
|
||||
|
@ -458,17 +458,17 @@ class ExportTemplateTest(APIViewTestCases.APIViewTestCase):
|
||||
brief_fields = ['description', 'display', 'id', 'name', 'url']
|
||||
create_data = [
|
||||
{
|
||||
'content_types': ['dcim.device'],
|
||||
'object_types': ['dcim.device'],
|
||||
'name': 'Test Export Template 4',
|
||||
'template_code': '{% for obj in queryset %}{{ obj.name }}\n{% endfor %}',
|
||||
},
|
||||
{
|
||||
'content_types': ['dcim.device'],
|
||||
'object_types': ['dcim.device'],
|
||||
'name': 'Test Export Template 5',
|
||||
'template_code': '{% for obj in queryset %}{{ obj.name }}\n{% endfor %}',
|
||||
},
|
||||
{
|
||||
'content_types': ['dcim.device'],
|
||||
'object_types': ['dcim.device'],
|
||||
'name': 'Test Export Template 6',
|
||||
'template_code': '{% for obj in queryset %}{{ obj.name }}\n{% endfor %}',
|
||||
},
|
||||
@ -495,7 +495,7 @@ class ExportTemplateTest(APIViewTestCases.APIViewTestCase):
|
||||
)
|
||||
ExportTemplate.objects.bulk_create(export_templates)
|
||||
for et in export_templates:
|
||||
et.content_types.set([ContentType.objects.get_for_model(Device)])
|
||||
et.object_types.set([ObjectType.objects.get_for_model(Device)])
|
||||
|
||||
|
||||
class TagTest(APIViewTestCases.APIViewTestCase):
|
||||
|
@ -639,7 +639,7 @@ class ExportTemplateTestCase(TestCase, BaseFilterSetTests):
|
||||
|
||||
@classmethod
|
||||
def setUpTestData(cls):
|
||||
content_types = ContentType.objects.filter(model__in=['site', 'rack', 'device'])
|
||||
object_types = ObjectType.objects.filter(model__in=['site', 'rack', 'device'])
|
||||
|
||||
export_templates = (
|
||||
ExportTemplate(name='Export Template 1', template_code='TESTING', description='foobar1'),
|
||||
@ -648,7 +648,7 @@ class ExportTemplateTestCase(TestCase, BaseFilterSetTests):
|
||||
)
|
||||
ExportTemplate.objects.bulk_create(export_templates)
|
||||
for i, et in enumerate(export_templates):
|
||||
et.content_types.set([content_types[i]])
|
||||
et.object_types.set([object_types[i]])
|
||||
|
||||
def test_q(self):
|
||||
params = {'q': 'foobar1'}
|
||||
@ -658,10 +658,10 @@ class ExportTemplateTestCase(TestCase, BaseFilterSetTests):
|
||||
params = {'name': ['Export Template 1', 'Export Template 2']}
|
||||
self.assertEqual(self.filterset(params, self.queryset).qs.count(), 2)
|
||||
|
||||
def test_content_types(self):
|
||||
params = {'content_types': 'dcim.site'}
|
||||
def test_object_types(self):
|
||||
params = {'object_types': 'dcim.site'}
|
||||
self.assertEqual(self.filterset(params, self.queryset).qs.count(), 1)
|
||||
params = {'content_type_id': [ContentType.objects.get_for_model(Site).pk]}
|
||||
params = {'object_types_id': [ContentType.objects.get_for_model(Site).pk]}
|
||||
self.assertEqual(self.filterset(params, self.queryset).qs.count(), 1)
|
||||
|
||||
def test_description(self):
|
||||
|
@ -303,7 +303,7 @@ class ExportTemplateTestCase(ViewTestCases.PrimaryObjectViewTestCase):
|
||||
|
||||
@classmethod
|
||||
def setUpTestData(cls):
|
||||
site_ct = ContentType.objects.get_for_model(Site)
|
||||
site_type = ObjectType.objects.get_for_model(Site)
|
||||
TEMPLATE_CODE = """{% for object in queryset %}{{ object }}{% endfor %}"""
|
||||
|
||||
export_templates = (
|
||||
@ -313,16 +313,16 @@ class ExportTemplateTestCase(ViewTestCases.PrimaryObjectViewTestCase):
|
||||
)
|
||||
ExportTemplate.objects.bulk_create(export_templates)
|
||||
for et in export_templates:
|
||||
et.content_types.set([site_ct])
|
||||
et.object_types.set([site_type])
|
||||
|
||||
cls.form_data = {
|
||||
'name': 'Export Template X',
|
||||
'content_types': [site_ct.pk],
|
||||
'object_types': [site_type.pk],
|
||||
'template_code': TEMPLATE_CODE,
|
||||
}
|
||||
|
||||
cls.csv_data = (
|
||||
"name,content_types,template_code",
|
||||
"name,object_types,template_code",
|
||||
f"Export Template 4,dcim.site,{TEMPLATE_CODE}",
|
||||
f"Export Template 5,dcim.site,{TEMPLATE_CODE}",
|
||||
f"Export Template 6,dcim.site,{TEMPLATE_CODE}",
|
||||
|
@ -70,9 +70,9 @@
|
||||
<div class="card">
|
||||
<h5 class="card-header">{% trans "Assigned Models" %}</h5>
|
||||
<table class="table table-hover attr-table">
|
||||
{% for ct in object.content_types.all %}
|
||||
{% for object_type in object.object_types.all %}
|
||||
<tr>
|
||||
<td>{{ ct }}</td>
|
||||
<td>{{ object_type }}</td>
|
||||
</tr>
|
||||
{% endfor %}
|
||||
</table>
|
||||
|
@ -25,7 +25,7 @@
|
||||
<hr class="dropdown-divider">
|
||||
</li>
|
||||
<li>
|
||||
<a class="dropdown-item" href="{% url 'extras:exporttemplate_add' %}?content_types={{ content_type.pk }}">{% trans "Add export template" %}...</a>
|
||||
<a class="dropdown-item" href="{% url 'extras:exporttemplate_add' %}?object_types={{ object_type.pk }}">{% trans "Add export template" %}...</a>
|
||||
</li>
|
||||
{% endif %}
|
||||
</ul>
|
||||
|
@ -2,6 +2,7 @@ from django import template
|
||||
from django.contrib.contenttypes.models import ContentType
|
||||
from django.urls import NoReverseMatch, reverse
|
||||
|
||||
from core.models import ObjectType
|
||||
from extras.models import Bookmark, ExportTemplate
|
||||
from utilities.utils import get_viewname, prepare_cloned_fields
|
||||
|
||||
@ -132,18 +133,18 @@ def import_button(model, action='import'):
|
||||
|
||||
@register.inclusion_tag('buttons/export.html', takes_context=True)
|
||||
def export_button(context, model):
|
||||
content_type = ContentType.objects.get_for_model(model)
|
||||
object_type = ObjectType.objects.get_for_model(model)
|
||||
user = context['request'].user
|
||||
|
||||
# Determine if the "all data" export returns CSV or YAML
|
||||
data_format = 'YAML' if hasattr(content_type.model_class(), 'to_yaml') else 'CSV'
|
||||
data_format = 'YAML' if hasattr(object_type.model_class(), 'to_yaml') else 'CSV'
|
||||
|
||||
# Retrieve all export templates for this model
|
||||
export_templates = ExportTemplate.objects.restrict(user, 'view').filter(content_types=content_type)
|
||||
export_templates = ExportTemplate.objects.restrict(user, 'view').filter(object_types=object_type)
|
||||
|
||||
return {
|
||||
'perms': context['perms'],
|
||||
'content_type': content_type,
|
||||
'object_type': object_type,
|
||||
'url_params': context['request'].GET.urlencode() if context['request'].GET else '',
|
||||
'export_templates': export_templates,
|
||||
'data_format': data_format,
|
||||
|
Reference in New Issue
Block a user