Skip to content

Commit

Permalink
Code cleanup + fixes and docs
Browse files Browse the repository at this point in the history
  • Loading branch information
dupondje committed May 5, 2022
1 parent 1095c31 commit e12cd4e
Show file tree
Hide file tree
Showing 4 changed files with 147 additions and 46 deletions.
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@ This ensures stale objects are removed from NetBox keeping an accurate current s
* requests==2.24.0
* pyvmomi==6.7.3
* aiodns==2.0.0
* openstack

### Environment
* NetBox >= 2.9
Expand Down
57 changes: 11 additions & 46 deletions module/sources/openstack/connection.py
Original file line number Diff line number Diff line change
Expand Up @@ -85,16 +85,13 @@ class OpenStackHandler(SourceBase):
"user_domain": None,
"project_domain": None,
"group_name": "Openstack",
"validate_tls_certs": False,
"permitted_subnets": None,
"cluster_exclude_filter": None,
"cluster_include_filter": None,
"host_exclude_filter": None,
"host_include_filter": None,
"vm_exclude_filter": None,
"vm_include_filter": None,
"permitted_subnets": None,
"collect_hardware_asset_tag": True,
"match_host_by_serial": True,
"cluster_site_relation": None,
"cluster_tag_relation": None,
"cluster_tenant_relation": None,
Expand All @@ -108,14 +105,12 @@ class OpenStackHandler(SourceBase):
"vm_tenant_relation": None,
"dns_name_lookup": False,
"custom_dns_servers": None,
"validate_tls_certs": False,
"set_primary_ip": "when-undefined",
"skip_vm_platform": False,
"skip_vm_comments": False,
"skip_vm_templates": True,
"strip_host_domain_name": False,
"strip_vm_domain_name": False,
"sync_tags": False,
"sync_parent_tags": False,
"sync_custom_attributes": False
"strip_vm_domain_name": False
}

deprecated_settings = {}
Expand Down Expand Up @@ -652,8 +647,7 @@ def add_device_vm_to_inventory(self, object_type, object_data, pnic_data=None, v
Try to find object first based on the object data, interface MAC addresses and primary IPs.
1. try to find by name and cluster/site
2. try to find by mac addresses interfaces
3. try to find by serial number (1st) or asset tag (2nd) (ESXi host)
4. try to find by primary IP
3. try to find by primary IP
IP addresses for each interface are added here as well. First they will be checked and added
if all checks pass. For each IP address a matching IP prefix will be searched for. First we
Expand Down Expand Up @@ -742,21 +736,6 @@ def add_device_vm_to_inventory(self, object_type, object_data, pnic_data=None, v

device_vm_object = self.get_object_based_on_macs(object_type, nic_macs)

# look for devices with same serial or asset tag
if object_type == NBDevice:

if device_vm_object is None and object_data.get("serial") is not None and \
bool(self.match_host_by_serial) is True:
log.debug2(f"No match found. Trying to find {object_type.name} based on serial number")

device_vm_object = self.inventory.get_by_data(object_type, data={"serial": object_data.get("serial")})

if device_vm_object is None and object_data.get("asset_tag") is not None:
log.debug2(f"No match found. Trying to find {object_type.name} based on asset tag")

device_vm_object = self.inventory.get_by_data(object_type,
data={"asset_tag": object_data.get("asset_tag")})

if device_vm_object is not None:
log.debug2("Found a matching %s object: %s" %
(object_type.name, device_vm_object.get_display_name(including_second_key=True)))
Expand Down Expand Up @@ -919,13 +898,8 @@ def add_host(self, obj):
does the host pass the host_include_filter and host_exclude_filter
Then all necessary host data will be collected.
host model, manufacturer, serial, physical interfaces, virtual interfaces,
virtual switches, proxy switches, host port groups, interface VLANs, IP addresses
Primary IPv4/6 will be determined by
1. if the interface port group name contains
"management" or "mngt"
2. interface is the default route of this host
Primary IPv4/6 will be determined by 'host_ip' value
Parameters
----------
Expand Down Expand Up @@ -1005,9 +979,6 @@ def add_host(self, obj):
if get_string_or_none(obj.status) == "enabled":
status = "active"

# add asset tag if desired and present
asset_tag = None

# get host_tenant_relation
tenant_name = self.get_object_relation(name, "host_tenant_relation")

Expand All @@ -1029,8 +1000,6 @@ def add_host(self, obj):
}

# add data if present
if asset_tag is not None:
host_data["asset_tag"] = asset_tag
if platform is not None:
host_data["platform"] = {"name": platform}
if tenant_name is not None:
Expand Down Expand Up @@ -1078,7 +1047,6 @@ def add_virtual_machine(self, obj):
# get VM power state
status = "active" if get_string_or_none(obj.status) == "ACTIVE" else "offline"

# hypervisor_name = get_string_or_none(obj.hypervisor_hostname)
cluster_name = get_string_or_none(obj.availability_zone)

# honor strip_host_domain_name
Expand Down Expand Up @@ -1113,16 +1081,13 @@ def add_virtual_machine(self, obj):
# Collect data
#

# check if cluster is a Standalone ESXi
site_name = self.permitted_clusters.get(cluster_name)
if site_name is None:
site_name = self.get_site_name(NBCluster, cluster_name)

# first check against vm_platform_relation
platform = get_string_or_none(obj.flavor["original_name"])
platform = None
if bool(self.skip_vm_platform) is False:
platform = get_string_or_none(obj.flavor["original_name"])

if platform is not None:
platform = self.get_object_relation(platform, "vm_platform_relation", fallback=platform)
if platform is not None:
platform = self.get_object_relation(platform, "vm_platform_relation", fallback=platform)

disk = 0
for volume in obj.attached_volumes:
Expand Down
1 change: 1 addition & 0 deletions requirements.txt
Original file line number Diff line number Diff line change
Expand Up @@ -4,4 +4,5 @@ wheel
requests==2.24.0
pyvmomi==6.7.3
aiodns==2.0.0
setuptools==60.10.0
openstack
134 changes: 134 additions & 0 deletions settings-example.ini
Original file line number Diff line number Diff line change
Expand Up @@ -277,4 +277,138 @@ permitted_subnets = 172.16.0.0/12, 10.0.0.0/8, 192.168.0.0/16, fd00::/8
# if False only data which is not preset in NetBox will be added
#overwrite_interface_attributes = True


[source/my-openstack-example]

# Defines if this source is enabled or not
#enabled = true

# type of source. This defines which source handler to use.
type = openstack

# URL to the Openstack API
auth_url = https://api.openstack-instance.local:5000/v3

# Openstack project to connect to
project = MyProject

# Openstack region
region = RegionOne

# Openstack user_domain
user_domain = Default

# Openstack project_domain
project_domain = Default

# Enforces TLS certificate validation. If Openstack API uses a valid TLS certificate then
# this option should be set to 'true' to ensure a secure connection.
#validate_tls_certs = false

# username and password to use to log into vCenter
username = vcenteruser
password = supersecret

# IP networks eligible to be synced to NetBox.
# If an IP address is not part of this networks then it WON'T be synced to NetBox
permitted_subnets = 172.16.0.0/12, 10.0.0.0/8, 192.168.0.0/16, fd00::/8

# filters can be used to include/exclude certain objects from importing into NetBox
# Include filters are checked first and exclude filters after. An object name has to
# pass both filters to be synced to NetBox. If a filter is unset it will be ignored.
# Filters are all treated as regex expressions!

# If a cluster is excluded from sync then ALL VMs and HOSTS inside the cluster will
# be ignored!
#cluster_exclude_filter =
#cluster_include_filter =

# This will only include/exclude the host, not the VM if Host is part of a multi host
# cluster.
#host_exclude_filter =
#host_include_filter =

# simply include/exclude VMs
#vm_exclude_filter =
#vm_include_filter =

# This option defines which Openstack Availability Zones is part of a NetBox site. This is done
# with a comma separated key = value list.
# key: defines the cluster name as regex
# value: defines the NetBox site name (use quotes if name contains commas)
# This is a quite important config setting as IP addresses, prefixes, VLANs and
# VRFs are site dependent. In order to assign the correct prefix to an IP
# address it is important to pick the correct site.
# A VM always depends on the cluster site relation
#cluster_site_relation = Cluster_NYC = New York , Cluster_FFM.* = Frankfurt

# Same as cluster site but on host level. If unset it will fall back
# to cluster_site_relation.
#host_site_relation = nyc02.* = New York, ffm01.* = Frankfurt

# This option defines which cluster/host/VM belongs to which tenant. This is done
# with a comma separated key = value list.
# key: defines a hosts/VM name as regex
# value: defines the NetBox tenant name (use quotes if name contains commas)
#cluster_tenant_relation = Cluster_NYC.* = Customer A
#host_tenant_relation = esxi300.* = Infrastructure
#vm_tenant_relation = grafana.* = Infrastructure

# This option defines custom platforms if the used Flavors are not suitable.
# Pretty much a mapping of Openstack flavor name to your own platform name.
# This is done with a comma separated key = value list.
# key: defines a Openstack returned flavor name
# value: defines the desired NetBox platform name
#vm_platform_relation = centos-7.* = centos7, microsoft-windows-server-2016.* = Windows2016

# Define the NetBox device role used for hosts and VMs. The default is set to "Server". This is done
# with a comma separated key = value list.
# key: defines a hosts/VM name as regex
# value: defines the NetBox role name (use quotes if name contains commas)
#host_role_relation = .* = Server
#vm_role_relation = .* = Server

# Define NetBox tags which are assigned to a cluster, host or VM. This is done
# with a comma separated key = value list.
# key: defines a hosts/VM name as regex
# value: defines the NetBox tag (use quotes if name contains commas)
#cluster_tag_relation = Cluster_NYC.* = Infrastructure
#host_tag_relation = esxi300.* = Infrastructure
#vm_tag_relation = grafana.* = Infrastructure

# Perform a reverse lookup for all collected IP addresses. If a dns name
# was found it will be added to the IP address object in NetBox
#dns_name_lookup = True

# use custom DNS server to do the reverse lookups
#custom_dns_servers = 192.168.1.11, 192.168.1.12

# define how the primary IPs should be set
# possible values
#
# always: will remove primary IP from the object where this address is
# currently set as primary and moves it to new object
#
# when-undefined: (default)
# only sets primary IP if undefined, will cause ERRORs if same IP is
# assigned more then once to different hosts and IP is set as the
# objects primary IP
#
# never: don't set any primary IPs, will cause the same ERRORs
# as "when-undefined"

#set_primary_ip = when-undefined

# Do not sync flavors from a VM in Openstack to the comments field on a VM in netbox
#skip_vm_platform = False

# Do not sync ID from a VM in Openstack to the comments field on a VM in netbox
#skip_vm_comments = False

# strip domain part from host name before syncing device to NetBox
#strip_host_domain_name = False

# strip domain part from VM name before syncing VM to NetBox
#strip_vm_domain_name = False

# EOF

0 comments on commit e12cd4e

Please sign in to comment.