diff --git a/netbox/dcim/forms.py b/netbox/dcim/forms.py index a216bb75f35..6d37621c3a2 100644 --- a/netbox/dcim/forms.py +++ b/netbox/dcim/forms.py @@ -423,6 +423,18 @@ class Meta: fields = ['name', 'slug'] +class ManufacturerCSVForm(forms.ModelForm): + class Meta: + model = Manufacturer + fields = [ + 'name', 'slug' + ] + help_texts = { + 'name': 'Manufacturer name', + 'slug': 'URL-friendly slug', + } + + # # Device types # diff --git a/netbox/dcim/models.py b/netbox/dcim/models.py index d59c998dc2b..4fc9bf23f55 100644 --- a/netbox/dcim/models.py +++ b/netbox/dcim/models.py @@ -455,6 +455,10 @@ class Manufacturer(models.Model): name = models.CharField(max_length=50, unique=True) slug = models.SlugField(unique=True) + csv_headers = [ + 'name', 'slug', + ] + class Meta: ordering = ['name'] @@ -464,6 +468,12 @@ def __str__(self): def get_absolute_url(self): return "{}?manufacturer={}".format(reverse('dcim:devicetype_list'), self.slug) + def to_csv(self): + return csv_format([ + self.name, + self.slug, + ]) + @python_2_unicode_compatible class DeviceType(models.Model, CustomFieldModel): diff --git a/netbox/dcim/urls.py b/netbox/dcim/urls.py index 12f8ebf86b7..ffd9b9005f8 100644 --- a/netbox/dcim/urls.py +++ b/netbox/dcim/urls.py @@ -64,6 +64,7 @@ # Manufacturers url(r'^manufacturers/$', views.ManufacturerListView.as_view(), name='manufacturer_list'), url(r'^manufacturers/add/$', views.ManufacturerCreateView.as_view(), name='manufacturer_add'), + url(r'^manufacturers/import/$', views.ManufacturerBulkImportView.as_view(), name='manufacturer_import'), url(r'^manufacturers/delete/$', views.ManufacturerBulkDeleteView.as_view(), name='manufacturer_bulk_delete'), url(r'^manufacturers/(?P[\w-]+)/edit/$', views.ManufacturerEditView.as_view(), name='manufacturer_edit'), diff --git a/netbox/dcim/views.py b/netbox/dcim/views.py index c155774db19..6766ab24647 100644 --- a/netbox/dcim/views.py +++ b/netbox/dcim/views.py @@ -561,6 +561,13 @@ class ManufacturerEditView(ManufacturerCreateView): permission_required = 'dcim.change_manufacturer' +class ManufacturerBulkImportView(PermissionRequiredMixin, BulkImportView): + permission_required = 'dcim.add_manufacturer' + model_form = forms.ManufacturerCSVForm + table = tables.ManufacturerTable + default_return_url = 'dcim:manufacturer_list' + + class ManufacturerBulkDeleteView(PermissionRequiredMixin, BulkDeleteView): permission_required = 'dcim.delete_manufacturer' cls = Manufacturer diff --git a/netbox/extras/constants.py b/netbox/extras/constants.py index 2c3918f75ba..815c896c5b5 100644 --- a/netbox/extras/constants.py +++ b/netbox/extras/constants.py @@ -37,7 +37,7 @@ # Models which support export templates EXPORTTEMPLATE_MODELS = [ - 'site', 'region', 'rack', 'rackgroup', 'device', # DCIM + 'site', 'region', 'rack', 'rackgroup', 'manufacturer', 'device', # DCIM 'consoleport', 'powerport', 'interfaceconnection', # DCIM 'aggregate', 'prefix', 'ipaddress', 'vlan', # IPAM 'provider', 'circuit', # Circuits diff --git a/netbox/templates/_base.html b/netbox/templates/_base.html index ebc8bc680b2..d41b2c66f46 100644 --- a/netbox/templates/_base.html +++ b/netbox/templates/_base.html @@ -105,6 +105,7 @@
  • Manufacturers
  • {% if perms.dcim.add_manufacturer %}
  • Add a Manufacturer
  • +
  • Import Manufacturers
  • {% endif %} {% if perms.dcim.add_manufacturer or perms.dcim.add_platform %}
  • diff --git a/netbox/templates/dcim/manufacturer_list.html b/netbox/templates/dcim/manufacturer_list.html index d535e11e814..e0d47dba1db 100644 --- a/netbox/templates/dcim/manufacturer_list.html +++ b/netbox/templates/dcim/manufacturer_list.html @@ -10,7 +10,12 @@ Add a manufacturer + + + Import manufacturers + {% endif %} + {% include 'inc/export_button.html' with obj_type='manufacturers' %}

    Manufacturers