Skip to content

Commit f6b4394

Browse files
authored
Merge pull request #36 from wobcom/feature/performance2
Splitted, multi-threaded and rewamped some queries to speed up perfor…
2 parents 839b5d6 + dc969c4 commit f6b4394

25 files changed

+597
-347
lines changed

.gitignore

+1-2
Original file line numberDiff line numberDiff line change
@@ -6,8 +6,7 @@ cosmo.yml
66
.direnv
77
leaf*.json
88

9-
cosmo_data.yaml
10-
machines/test0001/*
9+
machines/**
1110

1211
.coverage
1312
*~

cosmo/__main__.py

+3-5
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,3 @@
1-
import ipaddress
21
import json
32
import os
43
import sys
@@ -8,12 +7,11 @@
87
import yaml
98
import argparse
109

11-
from cosmo.netboxclient import NetboxClient
10+
from cosmo.clients.netbox import NetboxClient
11+
from cosmo.log import info
1212
from cosmo.serializer import RouterSerializer, SwitchSerializer, AbstractRecoverableError, RouterSerializerConfig
1313

1414

15-
def info(string: str) -> None:
16-
print("[INFO] " + string)
1715

1816

1917
def main() -> int:
@@ -81,7 +79,7 @@ def noop(*args, **kwargs):
8179
if device['name'] in cosmo_configuration['devices']['router']:
8280

8381
router_serializer_cfg = RouterSerializerConfig(cosmo_configuration.get("router_serializer_configuration", {}))
84-
serializer = RouterSerializer(router_serializer_cfg, device, cosmo_data['l2vpn_list'], cosmo_data["vrf_list"])
82+
serializer = RouterSerializer(router_serializer_cfg, device, cosmo_data['l2vpn_list'], cosmo_data["vrf_list"], cosmo_data["loopbacks"])
8583
content = serializer.serialize()
8684
elif device['name'] in cosmo_configuration['devices']['switch']:
8785
serializer = SwitchSerializer(device)

cosmo/clients/__init__.py

Whitespace-only changes.

cosmo/clients/netbox.py

+47
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
import time
2+
from urllib.parse import urljoin
3+
4+
import requests
5+
6+
from cosmo import log
7+
from cosmo.clients.netbox_v4 import NetboxV4Strategy
8+
9+
10+
class NetboxClient:
11+
def __init__(self, url, token):
12+
self.url = url
13+
self.token = token
14+
15+
self.version = self.query_version()
16+
17+
if self.version.startswith("4."):
18+
log.info("Using version 4.x strategy...")
19+
self.child_client = NetboxV4Strategy(url, token)
20+
else:
21+
raise Exception("Unknown Version")
22+
23+
def query_version(self):
24+
r = requests.get(
25+
urljoin(self.url, "/api/status/"),
26+
headers={
27+
"Authorization": f"Token {self.token}",
28+
"Content-Type": "application/json",
29+
"Accept": "application/json",
30+
},
31+
)
32+
if r.status_code != 200:
33+
raise Exception("Error querying api: " + r.text)
34+
35+
json = r.json()
36+
return json['netbox-version']
37+
38+
def get_data(self, device_config):
39+
start_time = time.perf_counter()
40+
data = self.child_client.get_data(device_config)
41+
end_time = time.perf_counter()
42+
diff_time = end_time - start_time
43+
log.info(f"Data fetching took {round(diff_time, 2)} s...")
44+
45+
return data
46+
47+

cosmo/clients/netbox_client.py

+56
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,56 @@
1+
from urllib.parse import urlencode, urljoin
2+
3+
import requests
4+
5+
6+
class NetboxAPIClient:
7+
def __init__(self, url, token):
8+
self.url = url
9+
self.token = token
10+
11+
def query(self, query):
12+
r = requests.post(
13+
urljoin(self.url, "/graphql/"),
14+
json={"query": query},
15+
headers={
16+
"Authorization": f"Token {self.token}",
17+
"Content-Type": "application/json",
18+
"Accept": "application/json",
19+
},
20+
)
21+
if r.status_code != 200:
22+
raise Exception("Error querying api: " + r.text)
23+
24+
json = r.json()
25+
26+
if 'errors' in json:
27+
for e in json['errors']:
28+
print(e)
29+
30+
return json
31+
32+
def query_rest(self, path, queries):
33+
q = urlencode(queries, doseq=True)
34+
url = urljoin(self.url, path) + f"?{q}"
35+
36+
return_array = list()
37+
38+
while url is not None:
39+
r = requests.get(
40+
url,
41+
headers={
42+
"Authorization": f"Token {self.token}",
43+
"Content-Type": "application/json",
44+
"Accept": "application/json",
45+
},
46+
)
47+
48+
if r.status_code != 200:
49+
raise Exception("Error querying api: " + r.text)
50+
51+
data = r.json()
52+
53+
url = data['next']
54+
return_array.extend(data['results'])
55+
56+
return return_array

0 commit comments

Comments
 (0)