def test_vlan_create_from_pynautobot_with_tags(nautobot_api_base): api = pynautobot.api(url="http://mock_nautobot", token="1234567890") data = yaml.safe_load(open(f"{ROOT}/../fixtures/vlan_101_tags_01.json")) pnb = pynautobot.core.response.Record(values=data, api=api, endpoint=1) nautobot_api_base.add( NautobotDevice(name="devA", site_name="nyc", remote_id="eb697742-364d-4714-b585-a267c64d7720") ) item = NautobotVlan.create_from_pynautobot(diffsync=nautobot_api_base, obj=pnb, site_name="nyc") assert isinstance(item, NautobotVlan) is True assert item.remote_id == "eb697742-364d-4714-b585-a267c64d7720" assert item.vid == 101 assert item.associated_devices == ["devA"] # Try again with one additional device in the inventory nautobot_api_base.add( NautobotDevice(name="devB", site_name="nyc", remote_id="eb697742-364d-4714-b585-a267c64d7731") ) item = NautobotVlan.create_from_pynautobot(diffsync=nautobot_api_base, obj=pnb, site_name="nyc") assert isinstance(item, NautobotVlan) is True assert item.remote_id == "eb697742-364d-4714-b585-a267c64d7720" assert item.vid == 101 assert item.associated_devices == ["devA", "devB"]
def load(self): """Initialize pynautobot and load all data from nautobot in the local cache.""" inventory_settings = InventorySettings( **config.SETTINGS.inventory.settings) self.nautobot = pynautobot.api(url=inventory_settings.address, token=inventory_settings.token) if not inventory_settings.verify_ssl: self.nautobot.http_session.verify = False else: self.nautobot.http_session.verify = True self._check_nautobot_version() sites = {} device_names = [] results = self.nornir.run(task=query_device_info_from_nautobot) for device_name, items in results.items(): if items[0].failed: continue result = items[0].result nb_device = result["device"] site_name = nb_device["site"].get("slug") if site_name not in sites.keys(): site = self.site(name=site_name, remote_id=nb_device["site"].get("id")) sites[site_name] = site self.add(site) else: site = sites[site_name] device = self.device(name=device_name, site_name=site_name, remote_id=nb_device["id"]) if nb_device["primary_ip"]: device.primary_ip = nb_device["primary_ip"].get("address") device = self.apply_model_flag(device, nb_device) self.add(device) # Load Prefix and Vlan per site for site in self.get_all(self.site): self.load_nautobot_prefix(site) self.load_nautobot_vlan(site) # Load interfaces and IP addresses for each devices devices = self.get_all(self.device) for device in devices: site = sites[device.site_name] device_names.append(device.name) self.load_nautobot_device(site=site, device=device) # Load Cabling for site in self.get_all(self.site): self.load_nautobot_cable(site=site, device_names=device_names)
def __init__(self, **kwargs): self.url = kwargs.get("url") or os.getenv("NAUTOBOT_URL") self.token = kwargs.get("token") or os.getenv("NAUTOBOT_TOKEN") self.ssl_verify = kwargs.get("ssl_verify", True) # Setup the API client calls self.api = pynautobot.api(url=self.url, token=self.token) self.api.http_session.verify = self.ssl_verify
def test_config(self, *_): api = pynautobot.api(host, **def_kwargs) config = api.users.config() self.assertEqual(sorted(config.keys()), ["tables"]) self.assertEqual( sorted(config["tables"]["DeviceTable"]["columns"]), ["name", "status", "tags", "tenant"], )
def test_create_from_pynautobot(nautobot_api_base): api = pynautobot.api(url="http://mock", token="1234567890") data = yaml.safe_load(open(f"{ROOT}/../fixtures/ip_address.json")) pnb = pynautobot.core.response.Record(values=data, api=api, endpoint=1) ipaddr = NautobotIPAddress.create_from_pynautobot(diffsync=nautobot_api_base, obj=pnb, device_name="HQ-CORE-SW02") assert ipaddr.interface_name == "TenGigabitEthernet1/0/1" assert ipaddr.device_name == "HQ-CORE-SW02"
def nb_client(docker_ip, devicetype_library_repo_dirpath): """Setup the nb_client and import necessary data. """ url = "http://{}:{}".format(docker_ip, 8000) nb_api = pynautobot.api(url, token="0123456789abcdef0123456789abcdef01234567") populate_nautobot_object_types(nb_api=nb_api, devicetype_library_repo_dirpath=devicetype_library_repo_dirpath) return nb_api
def test_vlan_create_from_pynautobot(nautobot_api_base): api = pynautobot.api(url="http://mock_nautobot", token="1234567890") data = yaml.safe_load(open(f"{ROOT}/../fixtures/vlan_101_no_tag.json")) pnb = pynautobot.core.response.Record(values=data, api=api, endpoint="eb697742-364d-4714-b585-a267c64d7720") item = NautobotVlan.create_from_pynautobot(diffsync=nautobot_api_base, obj=pnb, site_name="nyc") assert isinstance(item, NautobotVlan) is True assert item.remote_id == "eb697742-364d-4714-b585-a267c64d7720" assert item.vid == 101 assert item.associated_devices == []
def query_device_info_from_nautobot(task: Task) -> Result: """Nornir Task to query the device information from Nautobot. Currently this task will pull both the device information but th goal is to pull additional information and return everything in a single dict TODO add logic to pull interfaces as well TODO add logic to pull ip addresses as well Args: task (Task): Nornir Task with a valid network device Returns: Result: Nornir Result object with the result in a dict format """ inventory_settings = InventorySettings( **config.SETTINGS.inventory.settings) nautobot = pynautobot.api(url=inventory_settings.address, token=inventory_settings.token) # Check for SSL Verification, set it to false if not. Else set to true if not inventory_settings.verify_ssl: # No manual session is required for this, pynautobot will automatically create one nautobot.http_session.verify = False else: nautobot.http_session.verify = True # Set a Results dictionary results = { "device": None, "interfaces": None, } # Get the device based on the filter device = nautobot.dcim.devices.filter(name=task.host.name) # Return a failed that there were too many devices returned in the filterset if len(device) > 1: LOGGER.warning("More than 1 device returned from Nautobot for %s", task.host.name) return Result(host=task.host, failed=True) # Return a failed when no devices were returned if not device: LOGGER.warning("No device returned from Nautobot for %s", task.host.name) return Result(host=task.host, failed=True) results["device"] = dict(device[0]) # TODO move the logic to pull the interface and potentially IP here # interfaces = netbox.dcim.interfaces.filter(device=task.host.name) # results["interfaces"] = [ dict(intf) for intf in interfaces ] return Result(host=task.host, result=results)
def _connect_api(self, url, token, ssl_verify): try: nb = pynautobot.api(url, token=token) nb.http_session.verify = ssl_verify try: self.version = nb.version except Exception: self.module.fail_json( msg="Failed to establish connection to Nautobot API") return nb except Exception: self.module.fail_json( msg="Failed to establish connection to Nautobot API")
def test_update_clean_tags_no_incoming_tags(nautobot_api_base): vlan = NautobotVlan(vid=100, site_name="HQ", remote_id="464a2de3-fd5e-4b65-a58d-e0a2a617c12e") nautobot_api_base.add(vlan) api = pynautobot.api(url="http://mock_nautobot", token="1234567890") data = yaml.safe_load(open(f"{ROOT}/../fixtures/vlan_101_tags_01.json")) pnb = pynautobot.core.response.Record(values=data, api=api, endpoint="eb697742-364d-4714-b585-a267c64d7720") params = vlan.translate_attrs_for_nautobot({"name": "VOICE"}) clean_params = vlan.update_clean_tags(nb_params=params, obj=pnb) assert "tags" not in clean_params
def __init__( self, *args, **kwargs: Any, ) -> None: """Nornir Inventory Plugin for Nautobot API.""" super().__init__( *args, **kwargs, ) try: self.settings = InventorySettings(**self.settings) except ValidationError as exc: print( f"Inventory Settings are not valid, found {len(exc.errors())} error(s)" ) for error in exc.errors(): print( f" inventory/{'/'.join(error['loc'])} | {error['msg']} ({error['type']})" ) sys.exit(1) # Build Filter based on inventory_settings filter and on limit self.filter_parameters = {} if self.settings.filter is not None: build_filter_params(self.settings.filter.split((",")), self.filter_parameters) if self.limit: if "=" not in self.limit: self.filter_parameters["name"] = self.limit else: build_filter_params(self.limit.split((",")), self.filter_parameters) if "exclude" not in self.filter_parameters.keys(): self.filter_parameters["exclude"] = "config_context" # Instantiate nautobot session using pynautobot self.session = pynautobot.api(url=self.settings.address, token=self.settings.token) if not self.settings.verify_ssl: self.session.http_session.verify = False
def test_update_clean_tags_with_incoming_tags(nautobot_api_base): vlan = NautobotVlan(vid=100, site_name="HQ", remote_id="464a2de3-fd5e-4b65-a58d-e0a2a617c12e") nautobot_api_base.add(vlan) nautobot_api_base.add( NautobotDevice( name="dev1", site_name="HQ", remote_id="e0633a07-c3e2-41b0-a1df-4627392acf0a", device_tag_id="0bc28fc5-4e3d-4e84-b407-318c2151d64e", ) ) nautobot_api_base.add( NautobotDevice( name="dev2", site_name="HQ", remote_id="e0633a07-c3e2-41b0-a1df-4627392acf0b", device_tag_id="0bc28fc5-4e3d-4e84-b407-318c2151d65a", ) ) api = pynautobot.api(url="http://mock_nautobot", token="1234567890") data = yaml.safe_load(open(f"{ROOT}/../fixtures/vlan_101_tags_01.json")) pnb = pynautobot.core.response.Record(values=data, api=api, endpoint="eb697742-364d-4714-b585-a267c64d7720") params = vlan.translate_attrs_for_nautobot({"name": "VOICE", "associated_devices": ["dev1", "dev2"]}) clean_params = vlan.update_clean_tags(nb_params=params, obj=pnb) assert "tags" in clean_params print(clean_params) assert sorted(clean_params["tags"]) == [ "0bc28fc5-4e3d-4e84-b407-318c2151d64e", "0bc28fc5-4e3d-4e84-b407-318c2151d65a", "999121c7-37d6-44a8-83f9-61706e915bde", "d0c52a6c-b3e9-4234-98ef-ee9b76ca31db", "fd6809fa-26cf-47b2-8742-974cd4d22ca9", ]
def nautobot_api_base(): """Provide an instance of NautobotAPIAdapter with pynautoboot initiliazed.""" diffsync = NautobotAPIAdapter(nornir=None, settings={}) diffsync.nautobot = pynautobot.api(url="http://mock_nautobot", token="1234567890") diffsync.add( NautobotSite(name="HQ", remote_id="a325e477-62fe-47f0-8b67-acf411b1868f")) diffsync.add( NautobotDevice(name="HQ-CORE-SW02", site_name="HQ", remote_id="e0633a07-c3e2-41b0-a1df-4627392acf0a")) diffsync.add( NautobotInterface(name="TenGigabitEthernet1/0/1", device_name="HQ-CORE-SW02", remote_id="fecc1d8f-99b1-491d-9bdf-1dcb394e27a1")) diffsync.add( NautobotVlan(vid=111, site_name="HQ", remote_id="464a2de3-fd5e-4b65-a58d-e0a2a617c12e")) return diffsync
import unittest import six import pynautobot from .util import Response if six.PY3: from unittest.mock import patch else: from mock import patch api = pynautobot.api("http://localhost:8000", token="abc123",) nb = api.dcim HEADERS = { "accept": "application/json;", "authorization": "Token abc123", } class Generic(object): class Tests(unittest.TestCase): name = "" ret = pynautobot.core.response.Record app = "dcim" def test_get_all(self): with patch( "requests.sessions.Session.get",
import pynautobot from modules.render_template import render_template import json from data_output import region_list import pandas as pd import sys error_log = open("errors_ingest_data.log", "w") nautobot = pynautobot.api(url="http://10.66.69.149:8481/", token="b7d568b9a5a400a249a057fca8a2b0d6dcc05828") # nautobot = pynautobot.api( # url="http://10.66.69.142:8481/", # token="5af16d6a2ffa79f62103139d2414d0f214edc7ad") def devices(): my_devices = nautobot.dcim.devices render_devices = render_template() to_add_devices = render_devices.devices() for devices in to_add_devices: try: print(devices) devices_conv = json.loads(devices) add_devices = my_devices.create(devices_conv) except pynautobot.RequestError as e: print(e.error) pass print("Done")
def main(): """Main code execution block.""" urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning) nautobot = pynautobot.api(url=os.getenv("NAUTOBOT_ADDRESS"), token=os.getenv("NAUTOBOT_TOKEN")) nautobot.http_session.verify = False # Create region for region in ["ni_multi_site_02"]: print(f"Checking on region: {region}") _, created = get_or_create( object_endpoint=nautobot.dcim.regions, search_key="name", search_term=region, slug=region.lower() ) if created: print(f"Created region: {region}") else: print(f"Region already exists: {region}") mfg_map = dict() device_type_map = dict() for item in PLATFORMS: print(f"Checking on platform: {item}") mfg, created = get_or_create( object_endpoint=nautobot.dcim.manufacturers, search_key="slug", search_term=item["manufacturer"], name=item["manufacturer"].capitalize(), slug=item["manufacturer"].lower(), ) mfg_map[item["manufacturer"]]: mfg if created: print(f"Created manufacturer: {item['manufacturer']}") else: print(f"Manufacturer already created: {item['manufacturer']}") # Create device type if not already created device_type, created = get_or_create( object_endpoint=nautobot.dcim.device_types, search_key="model", search_term=item["name"], slug=item["name"], manufacturer=mfg.id, ) device_type_map[item["name"]] = device_type if created: print(f"Create Device Type: {item['name']}") else: print(f"Device Type Already Created: {item['name']}") device_role_map = dict() # Create device role for dev_role in DEVICE_ROLES: print(f"Checking on device role: {dev_role}") device_role_obj, created = get_or_create( object_endpoint=nautobot.dcim.device_roles, search_key="name", search_term=dev_role, slug=dev_role, ) if created: print(f"Created device role: {dev_role}") else: print(f"Device role already created: {dev_role}") device_role_map[dev_role] = device_role_obj # Get all of the sites site_map = dict() # Iterate over the sites for site in SITE_LIST: print(f"Checking on site: {site}") # Check if the device is created site_obj, created = get_or_create( object_endpoint=nautobot.dcim.sites, search_key="name", search_term=site, slug=site.lower(), status="Active" ) if created: print(f"Created site: {site}") else: print(f"Site already created: {site}") site_map[site] = site_obj # Create Devices for dev in DEVICE_LIST: print(f"Creating device: {dev}") _, created = get_or_create( object_endpoint=nautobot.dcim.devices, search_key="name", search_term=dev["name"], slug=dev["name"].lower(), status="Active", site=site_map["ni_spine_leaf_01"].id, device_type=device_type_map[dev["type"]].id, device_role=device_role_map[dev["role"]].id, just_create_device=True, ) if created: print(f"Created device: {dev['name']}") else: print(f"Device already created: {dev['name']}")
def test_custom_choices(self, *_): api = pynautobot.api(host, **def_kwargs) choices = api.plugins.test_plugin.custom_choices() self.assertEqual(len(choices), 2) self.assertEqual(sorted(choices.keys()), ["Testfield1", "Testfield2"])
def test_api_version(self, *_): api = pynautobot.api(host, ) self.assertEqual(api.version, "1.999")
def test_api_status(self, *_): api = pynautobot.api(host, ) self.assertEqual(api.status()["netbox-version"], "0.9.9")
def test_get(self, *_): api = pynautobot.api(host, **def_kwargs) self.assertTrue(api)
def nautobot_api_empty(): """Provide an instance of NautobotAPIAdapter with pynautobot initiliazed.""" diffsync = NautobotAPIAdapter(nornir=None, settings={}) diffsync.nautobot = pynautobot.api(url="http://mock", token="1234567890") return diffsync
__metaclass__ = type import os import sys import pynautobot from packaging import version # NOTE: If anything depends on specific versions of Nautobot, can check INTEGRATION_TESTS in env # os.environ["INTEGRATION_TESTS"] # Set nb variable to connect to Nautobot and use the veriable in future calls nb_host = os.getenv("NAUTOBOT_URL", "http://nautobot:8000") nb_token = os.getenv("NAUTOBOT_TOKEN", "0123456789abcdef0123456789abcdef01234567") nb = pynautobot.api(nb_host, nb_token) nb_version = version.parse(nb.version) ERRORS = False def make_nautobot_calls(endpoint, payload): """Make the necessary calls to create endpoints, and pass any errors. Args: endpoint (obj): pynautobot endpoint object. payload (list): List of endpoint objects. """ try: created = endpoint.create(payload) except pynautobot.RequestError as e:
import unittest import six import pynautobot from .util import Response if six.PY3: from unittest.mock import patch else: from mock import patch api = pynautobot.api("http://localhost:8000",) nb = api.users HEADERS = {"accept": "application/json;"} class Generic(object): class Tests(unittest.TestCase): name = "" ret = pynautobot.core.response.Record app = "users" def test_get_all(self): with patch( "requests.sessions.Session.get", return_value=Response(fixture="{}/{}.json".format(self.app, self.name)), ) as mock: ret = getattr(nb, self.name).all()
def test_api_version_not_found(self, *_): api = pynautobot.api(host, ) self.assertEqual(api.version, "")
def test_api_status(self, *_): api = pynautobot.api(host, ) self.assertEqual(api.status()["nautobot-version"], "1.3.2")
def test_installed_plugins(self, *_): api = pynautobot.api(host, **def_kwargs) plugins = api.plugins.installed_plugins() self.assertEqual(len(plugins), 1) self.assertEqual(plugins[0]["name"], "test_plugin")
from pprint import pprint import pynautobot, json import urllib3 urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning) file = open('nautobox.json', 'r') account = json.load(file) NB_URL = account['NB_URL'] TOKEN = account['TOKEN'] file.close() nb = pynautobot.api( url=NB_URL, token=TOKEN, ) nb.http_session.verify = False try: nb.dcim.regions.create({ "name": "GMM", 'slug': "gmm", 'description': "Greater Metro Manila" }) nb.dcim.regions.create({ "name": "NL", 'slug': "nl", 'description': "North Luzon" }) nb.dcim.regions.create({ "name": "SL",
def test_sanitize_url(self, *_): api = pynautobot.api("http://localhost:8000/", **def_kwargs) self.assertTrue(api) self.assertEqual(api.base_url, "http://localhost:8000/api")
def run(self, terms, variables=None, **kwargs): if PYNAUTOBOT_IMPORT_ERROR: raise_from( AnsibleError("pynautobot must be installed to use this plugin"), PYNAUTOBOT_IMPORT_ERROR, ) if REQUESTS_IMPORT_ERROR: raise_from( AnsibleError("requests must be installed to use this plugin"), REQUESTS_IMPORT_ERROR, ) api_token = kwargs.get("token") or os.getenv("NAUTOBOT_TOKEN") api_endpoint = kwargs.get("api_endpoint") or os.getenv("NAUTOBOT_URL") ssl_verify = kwargs.get("validate_certs", True) api_filter = kwargs.get("api_filter") raw_return = kwargs.get("raw_data") plugin = kwargs.get("plugin") if not isinstance(terms, list): terms = [terms] session = requests.Session() session.verify = ssl_verify nautobot = pynautobot.api( api_endpoint, token=api_token if api_token else None, ) nautobot.http_session = session results = [] for term in terms: if plugin: endpoint = get_plugin_endpoint(nautobot, plugin, term) else: try: endpoint = get_endpoint(nautobot, term) except KeyError: raise AnsibleError("Unrecognised term %s. Check documentation" % term) Display().vvvv("Nautobot lookup for %s to %s using token %s filter %s" % (term, api_endpoint, api_token, api_filter)) if api_filter: filter = build_filters(api_filter) if "id" in filter: Display().vvvv("Filter is: %s and includes id, will use .get instead of .filter" % (filter)) try: id = int(filter["id"][0]) data = endpoint.get(id) data = dict(data) Display().vvvvv(pformat(data)) return [data] except pynautobot.RequestError as e: raise AnsibleError(e.error) Display().vvvv("filter is %s" % filter) # Make call to Nautobot API and capture any failures data = make_call(endpoint, filters=filter if api_filter else None) for data in data: data = dict(data) Display().vvvvv(pformat(data)) if raw_return: results.append(data) else: key = data["id"] result = {key: data} results.extend(self._flatten_hash_to_list(result)) return results