netbox-atlassian 0.2.2__tar.gz → 0.2.4__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (21) hide show
  1. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/PKG-INFO +1 -1
  2. netbox_atlassian-0.2.4/netbox_atlassian/__init__.py +148 -0
  3. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/netbox_atlassian/atlassian_client.py +32 -26
  4. netbox_atlassian-0.2.4/netbox_atlassian/templates/netbox_atlassian/endpoint_tab.html +25 -0
  5. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/netbox_atlassian/urls.py +9 -0
  6. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/netbox_atlassian/views.py +150 -0
  7. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/netbox_atlassian.egg-info/PKG-INFO +1 -1
  8. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/netbox_atlassian.egg-info/SOURCES.txt +1 -0
  9. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/pyproject.toml +1 -1
  10. netbox_atlassian-0.2.2/netbox_atlassian/__init__.py +0 -74
  11. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/README.md +0 -0
  12. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/netbox_atlassian/forms.py +0 -0
  13. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/netbox_atlassian/navigation.py +0 -0
  14. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/netbox_atlassian/templates/netbox_atlassian/device_tab.html +0 -0
  15. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/netbox_atlassian/templates/netbox_atlassian/settings.html +0 -0
  16. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/netbox_atlassian/templates/netbox_atlassian/tab_content.html +0 -0
  17. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/netbox_atlassian/templates/netbox_atlassian/vm_tab.html +0 -0
  18. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/netbox_atlassian.egg-info/dependency_links.txt +0 -0
  19. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/netbox_atlassian.egg-info/requires.txt +0 -0
  20. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/netbox_atlassian.egg-info/top_level.txt +0 -0
  21. {netbox_atlassian-0.2.2 → netbox_atlassian-0.2.4}/setup.cfg +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: netbox-atlassian
3
- Version: 0.2.2
3
+ Version: 0.2.4
4
4
  Summary: NetBox plugin to display Jira issues and Confluence pages related to devices
5
5
  Author-email: sieteunoseis <jeremy.worden@gmail.com>
6
6
  License: Apache-2.0
@@ -0,0 +1,148 @@
1
+ """
2
+ NetBox Atlassian Plugin
3
+
4
+ Display Jira issues and Confluence pages related to devices in NetBox.
5
+ Searches by configurable fields (hostname, serial, role, etc.) with OR logic.
6
+ """
7
+
8
+ import logging
9
+
10
+ from netbox.plugins import PluginConfig
11
+
12
+ __version__ = "0.2.4"
13
+
14
+ logger = logging.getLogger(__name__)
15
+
16
+
17
+ class AtlassianConfig(PluginConfig):
18
+ """Plugin configuration for NetBox Atlassian integration."""
19
+
20
+ name = "netbox_atlassian"
21
+ verbose_name = "Atlassian"
22
+ description = "Display Jira issues and Confluence pages related to devices"
23
+ version = __version__
24
+ author = "sieteunoseis"
25
+ author_email = "sieteunoseis@github.com"
26
+ base_url = "atlassian"
27
+ min_version = "4.0.0"
28
+
29
+ # Required settings - plugin won't load without these
30
+ required_settings = []
31
+
32
+ # Default configuration values
33
+ default_settings = {
34
+ # Jira settings (on-prem)
35
+ "jira_url": "", # e.g., "https://jira.example.com"
36
+ "jira_username": "",
37
+ "jira_password": "", # or API token
38
+ "jira_token": "", # Personal Access Token (PAT) - preferred for on-prem
39
+ "jira_verify_ssl": True,
40
+ # Confluence settings (on-prem)
41
+ "confluence_url": "", # e.g., "https://confluence.example.com"
42
+ "confluence_username": "",
43
+ "confluence_password": "", # or API token
44
+ "confluence_token": "", # Personal Access Token (PAT) - preferred for on-prem
45
+ "confluence_verify_ssl": True,
46
+ # Cloud settings (for future use)
47
+ "use_cloud": False,
48
+ "cloud_api_token": "",
49
+ "cloud_email": "",
50
+ # Search configuration
51
+ # Fields to search - values are device attribute paths
52
+ # Searches use OR logic - matches any field
53
+ "search_fields": [
54
+ {"name": "Hostname", "attribute": "name", "enabled": True},
55
+ {"name": "Serial", "attribute": "serial", "enabled": True},
56
+ {"name": "Asset Tag", "attribute": "asset_tag", "enabled": False},
57
+ {"name": "Role", "attribute": "role.name", "enabled": False},
58
+ {"name": "Primary IP", "attribute": "primary_ip4.address", "enabled": False},
59
+ ],
60
+ # Endpoint search fields (for netbox-endpoints plugin)
61
+ # Searches use OR logic - matches any field
62
+ "endpoint_search_fields": [
63
+ {"name": "Name", "attribute": "name", "enabled": True},
64
+ {"name": "MAC Address", "attribute": "mac_address", "enabled": True},
65
+ {"name": "Serial", "attribute": "serial", "enabled": True},
66
+ {"name": "Asset Tag", "attribute": "asset_tag", "enabled": False},
67
+ ],
68
+ # Jira search settings
69
+ "jira_max_results": 10,
70
+ "jira_projects": [], # Empty = search all projects
71
+ "jira_issue_types": [], # Empty = all types
72
+ # Confluence search settings
73
+ "confluence_max_results": 10,
74
+ "confluence_spaces": [], # Empty = search all spaces
75
+ # General settings
76
+ "timeout": 30,
77
+ "cache_timeout": 300, # Cache results for 5 minutes
78
+ # Enable legacy SSL renegotiation for older servers (required for OHSU wiki)
79
+ "enable_legacy_ssl": False,
80
+ # Device type filtering (like catalyst-center)
81
+ # Empty list = show tab for all devices
82
+ "device_types": [], # e.g., ["cisco", "juniper"]
83
+ }
84
+
85
+ def ready(self):
86
+ """Register endpoint view if netbox_endpoints is available."""
87
+ super().ready()
88
+ self._register_endpoint_views()
89
+
90
+ def _register_endpoint_views(self):
91
+ """Register Atlassian tab for Endpoints if plugin is installed."""
92
+ import sys
93
+
94
+ # Quick check if netbox_endpoints is available
95
+ if "netbox_endpoints" not in sys.modules:
96
+ try:
97
+ import importlib.util
98
+
99
+ if importlib.util.find_spec("netbox_endpoints") is None:
100
+ logger.debug("netbox_endpoints not installed, skipping endpoint view registration")
101
+ return
102
+ except Exception:
103
+ logger.debug("netbox_endpoints not available, skipping endpoint view registration")
104
+ return
105
+
106
+ try:
107
+ from django.shortcuts import render
108
+ from netbox.views import generic
109
+ from netbox_endpoints.models import Endpoint
110
+ from utilities.views import ViewTab, register_model_view
111
+
112
+ from .views import should_show_atlassian_tab_endpoint
113
+
114
+ @register_model_view(Endpoint, name="atlassian", path="atlassian")
115
+ class EndpointAtlassianView(generic.ObjectView):
116
+ """Display Jira issues and Confluence pages for an Endpoint."""
117
+
118
+ queryset = Endpoint.objects.all()
119
+ template_name = "netbox_atlassian/endpoint_tab.html"
120
+
121
+ tab = ViewTab(
122
+ label="Atlassian",
123
+ weight=9100,
124
+ permission="netbox_endpoints.view_endpoint",
125
+ hide_if_empty=False,
126
+ visible=should_show_atlassian_tab_endpoint,
127
+ )
128
+
129
+ def get(self, request, pk):
130
+ endpoint = Endpoint.objects.get(pk=pk)
131
+ return render(
132
+ request,
133
+ self.template_name,
134
+ {
135
+ "object": endpoint,
136
+ "tab": self.tab,
137
+ "loading": True,
138
+ },
139
+ )
140
+
141
+ logger.info("Registered Atlassian tab for Endpoint model")
142
+ except ImportError:
143
+ logger.debug("netbox_endpoints not installed, skipping endpoint view registration")
144
+ except Exception as e:
145
+ logger.warning(f"Could not register endpoint views: {e}")
146
+
147
+
148
+ config = AtlassianConfig
@@ -219,22 +219,26 @@ class AtlassianClient:
219
219
  issues = []
220
220
  for issue in result.get("issues", []):
221
221
  fields = issue.get("fields", {})
222
- issues.append({
223
- "key": issue.get("key"),
224
- "summary": fields.get("summary", ""),
225
- "status": fields.get("status", {}).get("name", ""),
226
- "status_category": fields.get("status", {}).get("statusCategory", {}).get("key", ""),
227
- "type": fields.get("issuetype", {}).get("name", ""),
228
- "type_icon": fields.get("issuetype", {}).get("iconUrl", ""),
229
- "priority": fields.get("priority", {}).get("name", "") if fields.get("priority") else "",
230
- "priority_icon": fields.get("priority", {}).get("iconUrl", "") if fields.get("priority") else "",
231
- "assignee": fields.get("assignee", {}).get("displayName", "") if fields.get("assignee") else "Unassigned",
232
- "created": fields.get("created", ""),
233
- "updated": fields.get("updated", ""),
234
- "project": fields.get("project", {}).get("name", ""),
235
- "project_key": fields.get("project", {}).get("key", ""),
236
- "url": f"{self.jira_url}/browse/{issue.get('key')}",
237
- })
222
+ issues.append(
223
+ {
224
+ "key": issue.get("key"),
225
+ "summary": fields.get("summary", ""),
226
+ "status": fields.get("status", {}).get("name", ""),
227
+ "status_category": fields.get("status", {}).get("statusCategory", {}).get("key", ""),
228
+ "type": fields.get("issuetype", {}).get("name", ""),
229
+ "type_icon": fields.get("issuetype", {}).get("iconUrl", ""),
230
+ "priority": fields.get("priority", {}).get("name", "") if fields.get("priority") else "",
231
+ "priority_icon": fields.get("priority", {}).get("iconUrl", "") if fields.get("priority") else "",
232
+ "assignee": (
233
+ fields.get("assignee", {}).get("displayName", "") if fields.get("assignee") else "Unassigned"
234
+ ),
235
+ "created": fields.get("created", ""),
236
+ "updated": fields.get("updated", ""),
237
+ "project": fields.get("project", {}).get("name", ""),
238
+ "project_key": fields.get("project", {}).get("key", ""),
239
+ "url": f"{self.jira_url}/browse/{issue.get('key')}",
240
+ }
241
+ )
238
242
 
239
243
  response = {
240
244
  "issues": issues,
@@ -308,16 +312,18 @@ class AtlassianClient:
308
312
  ancestors = page.get("ancestors", [])
309
313
  breadcrumb = " > ".join([a.get("title", "") for a in ancestors])
310
314
 
311
- pages.append({
312
- "id": page.get("id"),
313
- "title": page.get("title", ""),
314
- "space_key": space.get("key", ""),
315
- "space_name": space.get("name", ""),
316
- "last_modified": version.get("when", ""),
317
- "last_modified_by": version.get("by", {}).get("displayName", ""),
318
- "breadcrumb": breadcrumb,
319
- "url": f"{self.confluence_url}{page.get('_links', {}).get('webui', '')}",
320
- })
315
+ pages.append(
316
+ {
317
+ "id": page.get("id"),
318
+ "title": page.get("title", ""),
319
+ "space_key": space.get("key", ""),
320
+ "space_name": space.get("name", ""),
321
+ "last_modified": version.get("when", ""),
322
+ "last_modified_by": version.get("by", {}).get("displayName", ""),
323
+ "breadcrumb": breadcrumb,
324
+ "url": f"{self.confluence_url}{page.get('_links', {}).get('webui', '')}",
325
+ }
326
+ )
321
327
 
322
328
  response = {
323
329
  "pages": pages,
@@ -0,0 +1,25 @@
1
+ {% extends 'netbox_endpoints/endpoint.html' %}
2
+ {% load helpers %}
3
+
4
+ {% block content %}
5
+ {% if loading %}
6
+ <div id="atlassian-content"
7
+ hx-get="{% url 'plugins:netbox_atlassian:endpoint_content' pk=object.pk %}"
8
+ hx-trigger="load"
9
+ hx-swap="innerHTML">
10
+ <div class="d-flex justify-content-center align-items-center py-5">
11
+ <div class="text-center">
12
+ <div class="spinner-border text-primary mb-3" role="status" style="width: 3rem; height: 3rem;">
13
+ <span class="visually-hidden">Loading...</span>
14
+ </div>
15
+ <p class="text-muted mb-0">Loading Atlassian data...</p>
16
+ <p class="text-muted small">Searching Jira and Confluence</p>
17
+ </div>
18
+ </div>
19
+ </div>
20
+ {% elif error %}
21
+ <div class="alert alert-warning">
22
+ <i class="mdi mdi-alert"></i> {{ error }}
23
+ </div>
24
+ {% endif %}
25
+ {% endblock %}
@@ -5,6 +5,7 @@ URL patterns for NetBox Atlassian Plugin
5
5
  from django.urls import path
6
6
 
7
7
  from .views import (
8
+ ENDPOINTS_PLUGIN_INSTALLED,
8
9
  AtlassianSettingsView,
9
10
  DeviceAtlassianContentView,
10
11
  TestConfluenceConnectionView,
@@ -19,3 +20,11 @@ urlpatterns = [
19
20
  path("device/<int:pk>/content/", DeviceAtlassianContentView.as_view(), name="device_content"),
20
21
  path("vm/<int:pk>/content/", VMAtlassianContentView.as_view(), name="vm_content"),
21
22
  ]
23
+
24
+ # Add endpoint URLs if netbox_endpoints is installed
25
+ if ENDPOINTS_PLUGIN_INSTALLED:
26
+ from .views import EndpointAtlassianContentView
27
+
28
+ urlpatterns.append(
29
+ path("endpoint/<int:pk>/content/", EndpointAtlassianContentView.as_view(), name="endpoint_content"),
30
+ )
@@ -22,6 +22,14 @@ from virtualization.models import VirtualMachine
22
22
  from .atlassian_client import get_client
23
23
  from .forms import AtlassianSettingsForm
24
24
 
25
+ # Check if netbox_endpoints plugin is installed
26
+ try:
27
+ from netbox_endpoints.models import Endpoint
28
+
29
+ ENDPOINTS_PLUGIN_INSTALLED = True
30
+ except ImportError:
31
+ ENDPOINTS_PLUGIN_INSTALLED = False
32
+
25
33
 
26
34
  def get_device_attribute(device, attribute_path: str):
27
35
  """
@@ -354,3 +362,145 @@ class TestConfluenceConnectionView(View):
354
362
  if success:
355
363
  return JsonResponse({"success": True, "message": message})
356
364
  return JsonResponse({"success": False, "error": message}, status=400)
365
+
366
+
367
+ # Endpoint-specific functions for netbox_endpoints plugin
368
+ def get_endpoint_attribute(endpoint, attribute_path: str):
369
+ """
370
+ Get an endpoint attribute by dot-separated path.
371
+
372
+ Args:
373
+ endpoint: Endpoint instance
374
+ attribute_path: Dot-separated attribute path (e.g., "name", "mac_address")
375
+
376
+ Returns:
377
+ Attribute value or None if not found
378
+ """
379
+ try:
380
+ value = endpoint
381
+ for part in attribute_path.split("."):
382
+ value = getattr(value, part, None)
383
+ if value is None:
384
+ return None
385
+ # Convert to string for IP addresses and MAC
386
+ if hasattr(value, "ip"):
387
+ return str(value.ip)
388
+ return str(value) if value else None
389
+ except Exception:
390
+ return None
391
+
392
+
393
+ def get_endpoint_search_terms(endpoint) -> list[str]:
394
+ """
395
+ Get search terms from endpoint based on configured endpoint_search_fields.
396
+
397
+ Returns list of non-empty values from enabled search fields.
398
+ """
399
+ config = settings.PLUGINS_CONFIG.get("netbox_atlassian", {})
400
+ search_fields = config.get(
401
+ "endpoint_search_fields",
402
+ [
403
+ {"name": "Name", "attribute": "name", "enabled": True},
404
+ {"name": "MAC Address", "attribute": "mac_address", "enabled": True},
405
+ {"name": "Serial", "attribute": "serial", "enabled": True},
406
+ ],
407
+ )
408
+
409
+ terms = []
410
+ for field in search_fields:
411
+ if not field.get("enabled", True):
412
+ continue
413
+
414
+ attribute = field.get("attribute", "")
415
+ if not attribute:
416
+ continue
417
+
418
+ value = get_endpoint_attribute(endpoint, attribute)
419
+ if value and value.strip():
420
+ # Split comma-separated values
421
+ if "," in value:
422
+ for part in value.split(","):
423
+ part = part.strip()
424
+ if part and part not in terms:
425
+ terms.append(part)
426
+ else:
427
+ if value.strip() not in terms:
428
+ terms.append(value.strip())
429
+
430
+ return terms
431
+
432
+
433
+ def should_show_atlassian_tab_endpoint(endpoint) -> bool:
434
+ """
435
+ Determine if the Atlassian tab should be visible for this endpoint.
436
+
437
+ Shows tab if endpoint has at least one searchable field value.
438
+ """
439
+ if not ENDPOINTS_PLUGIN_INSTALLED:
440
+ return False
441
+
442
+ terms = get_endpoint_search_terms(endpoint)
443
+ return len(terms) > 0
444
+
445
+
446
+ # Endpoint views - only available if netbox_endpoints is installed
447
+ if ENDPOINTS_PLUGIN_INSTALLED:
448
+
449
+ class EndpointAtlassianContentView(LoginRequiredMixin, PermissionRequiredMixin, View):
450
+ """HTMX endpoint that returns Atlassian content for Endpoint async loading."""
451
+
452
+ permission_required = "netbox_endpoints.view_endpoint"
453
+
454
+ def get(self, request, pk):
455
+ """Fetch Atlassian data and return HTML content."""
456
+ endpoint = Endpoint.objects.get(pk=pk)
457
+
458
+ config = settings.PLUGINS_CONFIG.get("netbox_atlassian", {})
459
+ client = get_client()
460
+
461
+ # Get search terms from endpoint
462
+ search_terms = get_endpoint_search_terms(endpoint)
463
+
464
+ # Get configured search fields for display
465
+ search_fields = config.get(
466
+ "endpoint_search_fields",
467
+ [
468
+ {"name": "Name", "attribute": "name", "enabled": True},
469
+ {"name": "MAC Address", "attribute": "mac_address", "enabled": True},
470
+ {"name": "Serial", "attribute": "serial", "enabled": True},
471
+ ],
472
+ )
473
+ enabled_fields = [f for f in search_fields if f.get("enabled", True)]
474
+
475
+ # Search Jira and Confluence
476
+ jira_results = {"issues": [], "total": 0, "error": None}
477
+ confluence_results = {"pages": [], "total": 0, "error": None}
478
+
479
+ if search_terms:
480
+ jira_max = config.get("jira_max_results", 10)
481
+ confluence_max = config.get("confluence_max_results", 10)
482
+
483
+ jira_results = client.search_jira(search_terms, max_results=jira_max)
484
+ confluence_results = client.search_confluence(search_terms, max_results=confluence_max)
485
+
486
+ # Get URLs for external links
487
+ jira_url = config.get("jira_url", "").rstrip("/")
488
+ confluence_url = config.get("confluence_url", "").rstrip("/")
489
+
490
+ return HttpResponse(
491
+ render_to_string(
492
+ "netbox_atlassian/tab_content.html",
493
+ {
494
+ "object": endpoint,
495
+ "search_terms": search_terms,
496
+ "enabled_fields": enabled_fields,
497
+ "jira_results": jira_results,
498
+ "confluence_results": confluence_results,
499
+ "jira_url": jira_url,
500
+ "confluence_url": confluence_url,
501
+ "jira_configured": bool(jira_url),
502
+ "confluence_configured": bool(confluence_url),
503
+ },
504
+ request=request,
505
+ )
506
+ )
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: netbox-atlassian
3
- Version: 0.2.2
3
+ Version: 0.2.4
4
4
  Summary: NetBox plugin to display Jira issues and Confluence pages related to devices
5
5
  Author-email: sieteunoseis <jeremy.worden@gmail.com>
6
6
  License: Apache-2.0
@@ -12,6 +12,7 @@ netbox_atlassian.egg-info/dependency_links.txt
12
12
  netbox_atlassian.egg-info/requires.txt
13
13
  netbox_atlassian.egg-info/top_level.txt
14
14
  netbox_atlassian/templates/netbox_atlassian/device_tab.html
15
+ netbox_atlassian/templates/netbox_atlassian/endpoint_tab.html
15
16
  netbox_atlassian/templates/netbox_atlassian/settings.html
16
17
  netbox_atlassian/templates/netbox_atlassian/tab_content.html
17
18
  netbox_atlassian/templates/netbox_atlassian/vm_tab.html
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
4
4
 
5
5
  [project]
6
6
  name = "netbox-atlassian"
7
- version = "0.2.2"
7
+ version = "0.2.4"
8
8
  description = "NetBox plugin to display Jira issues and Confluence pages related to devices"
9
9
  readme = "README.md"
10
10
  license = {text = "Apache-2.0"}
@@ -1,74 +0,0 @@
1
- """
2
- NetBox Atlassian Plugin
3
-
4
- Display Jira issues and Confluence pages related to devices in NetBox.
5
- Searches by configurable fields (hostname, serial, role, etc.) with OR logic.
6
- """
7
-
8
- from netbox.plugins import PluginConfig
9
-
10
- __version__ = "0.2.2"
11
-
12
-
13
- class AtlassianConfig(PluginConfig):
14
- """Plugin configuration for NetBox Atlassian integration."""
15
-
16
- name = "netbox_atlassian"
17
- verbose_name = "Atlassian"
18
- description = "Display Jira issues and Confluence pages related to devices"
19
- version = __version__
20
- author = "sieteunoseis"
21
- author_email = "sieteunoseis@github.com"
22
- base_url = "atlassian"
23
- min_version = "4.0.0"
24
-
25
- # Required settings - plugin won't load without these
26
- required_settings = []
27
-
28
- # Default configuration values
29
- default_settings = {
30
- # Jira settings (on-prem)
31
- "jira_url": "", # e.g., "https://jira.example.com"
32
- "jira_username": "",
33
- "jira_password": "", # or API token
34
- "jira_token": "", # Personal Access Token (PAT) - preferred for on-prem
35
- "jira_verify_ssl": True,
36
- # Confluence settings (on-prem)
37
- "confluence_url": "", # e.g., "https://confluence.example.com"
38
- "confluence_username": "",
39
- "confluence_password": "", # or API token
40
- "confluence_token": "", # Personal Access Token (PAT) - preferred for on-prem
41
- "confluence_verify_ssl": True,
42
- # Cloud settings (for future use)
43
- "use_cloud": False,
44
- "cloud_api_token": "",
45
- "cloud_email": "",
46
- # Search configuration
47
- # Fields to search - values are device attribute paths
48
- # Searches use OR logic - matches any field
49
- "search_fields": [
50
- {"name": "Hostname", "attribute": "name", "enabled": True},
51
- {"name": "Serial", "attribute": "serial", "enabled": True},
52
- {"name": "Asset Tag", "attribute": "asset_tag", "enabled": False},
53
- {"name": "Role", "attribute": "role.name", "enabled": False},
54
- {"name": "Primary IP", "attribute": "primary_ip4.address", "enabled": False},
55
- ],
56
- # Jira search settings
57
- "jira_max_results": 10,
58
- "jira_projects": [], # Empty = search all projects
59
- "jira_issue_types": [], # Empty = all types
60
- # Confluence search settings
61
- "confluence_max_results": 10,
62
- "confluence_spaces": [], # Empty = search all spaces
63
- # General settings
64
- "timeout": 30,
65
- "cache_timeout": 300, # Cache results for 5 minutes
66
- # Enable legacy SSL renegotiation for older servers (required for OHSU wiki)
67
- "enable_legacy_ssl": False,
68
- # Device type filtering (like catalyst-center)
69
- # Empty list = show tab for all devices
70
- "device_types": [], # e.g., ["cisco", "juniper"]
71
- }
72
-
73
-
74
- config = AtlassianConfig