Skip to content

Commit

Permalink
Allow plugin models to be reported.
Browse files Browse the repository at this point in the history
  • Loading branch information
Kircheneer committed Oct 17, 2023
1 parent 7ae5984 commit b6a40cc
Show file tree
Hide file tree
Showing 10 changed files with 93 additions and 77 deletions.
73 changes: 1 addition & 72 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -190,50 +190,11 @@ $RECYCLE.BIN/

### PyCharm ###
# Covers JetBrains IDEs: IntelliJ, RubyMine, PhpStorm, AppCode, PyCharm, CLion, Android Studio, WebStorm and Rider
# Reference: https://intellij-support.jetbrains.com/hc/en-us/articles/206544839

# User-specific stuff
.idea/**/workspace.xml
.idea/**/tasks.xml
.idea/**/usage.statistics.xml
.idea/**/dictionaries
.idea/**/shelf

# Generated files
.idea/**/contentModel.xml

# Sensitive or high-churn files
.idea/**/dataSources/
.idea/**/dataSources.ids
.idea/**/dataSources.local.xml
.idea/**/sqlDataSources.xml
.idea/**/dynamic.xml
.idea/**/uiDesigner.xml
.idea/**/dbnavigator.xml

# Gradle
.idea/**/gradle.xml
.idea/**/libraries

# Gradle and Maven with auto-import
# When using Gradle or Maven with auto-import, you should exclude module files,
# since they will be recreated, and may cause churn. Uncomment if using
# auto-import.
# .idea/artifacts
# .idea/compiler.xml
# .idea/jarRepositories.xml
# .idea/modules.xml
# .idea/*.iml
# .idea/modules
# *.iml
# *.ipr
.idea

# CMake
cmake-build-*/

# Mongo Explorer plugin
.idea/**/mongoSettings.xml

# File-based project format
*.iws

Expand All @@ -246,50 +207,18 @@ out/
# JIRA plugin
atlassian-ide-plugin.xml

# Cursive Clojure plugin
.idea/replstate.xml

# Crashlytics plugin (for Android Studio and IntelliJ)
com_crashlytics_export_strings.xml
crashlytics.properties
crashlytics-build.properties
fabric.properties

# Editor-based Rest Client
.idea/httpRequests

# Android studio 3.1+ serialized cache file
.idea/caches/build_file_checksums.ser

### PyCharm Patch ###
# Comment Reason: https://github.com/joeblau/gitignore.io/issues/186#issuecomment-215987721

# *.iml
# modules.xml
# .idea/misc.xml
# *.ipr

# Sonarlint plugin
# https://plugins.jetbrains.com/plugin/7973-sonarlint
.idea/**/sonarlint/

# SonarQube Plugin
# https://plugins.jetbrains.com/plugin/7238-sonarqube-community-plugin
.idea/**/sonarIssues.xml

# Markdown Navigator plugin
# https://plugins.jetbrains.com/plugin/7896-markdown-navigator-enhanced
.idea/**/markdown-navigator.xml
.idea/**/markdown-navigator-enh.xml
.idea/**/markdown-navigator/

# Cache file creation bug
# See https://youtrack.jetbrains.com/issue/JBR-2257
.idea/$CACHE_FILE$

# CodeStream plugin
# https://plugins.jetbrains.com/plugin/12206-codestream
.idea/codestream.xml

### vscode ###
.vscode/*
Expand Down
8 changes: 8 additions & 0 deletions development/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,14 @@ RUN curl -sSL https://install.python-poetry.org | python3 - && \

# Copy in the source code
WORKDIR /source

# Copy in only pyproject.toml/poetry.lock to help with caching this layer if no updates to dependencies
COPY poetry.lock pyproject.toml /source/
# --no-root declares not to install the project package since we're wanting to take advantage of caching dependency installation
# and the project is copied in and installed after this step
RUN poetry install --no-interaction --no-ansi --no-root

# Copy in the rest of the source code and install local Nautobot plugin
COPY . /source

# Get container's installed Nautobot version as a forced constraint
Expand Down
3 changes: 2 additions & 1 deletion development/nautobot_config.py
Original file line number Diff line number Diff line change
Expand Up @@ -249,7 +249,7 @@
NAPALM_ARGS = {}

# Enable installed plugins. Add the name of each plugin to the list.
PLUGINS = ["nautobot_capacity_metrics"]
PLUGINS = ["nautobot_capacity_metrics", "nautobot_capacity_metrics.test_models"]

# Plugins configuration settings. These settings are used by various plugins that the user may have installed.
# Each key in the dictionary is the name of an installed plugin and its value is a dictionary of settings.
Expand All @@ -268,6 +268,7 @@
},
"ipam": {"IPAddress": True, "Prefix": True},
"extras": {"GitRepository": True},
"test_models": {"_module": "nautobot_capacity_metrics", "TestModel": True},
},
"queues": True,
"versions": {
Expand Down
2 changes: 1 addition & 1 deletion docs/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -112,7 +112,7 @@ The behavior of the app_metrics feature can be controlled with the following lis
- `gitrepositories` boolean (default **False**), publish stats about the gitrepositories (success, warning, info, failure)
- `jobs` boolean (default **False**), publish stats about the jobs (success, warning, info, failure)
- `queues` boolean (default **False**), publish stats about RQ Worker (nbr of worker, nbr and type of job in the different queues)
- `models` nested dict, publish the count for a given object (Nbr Device, Nbr IP etc.. ). The first level must be the name of the module in lowercase (dcim, ipam etc..), the second level must be the name of the object (usually starting with a uppercase)
- `models` nested dict, publish the count for a given object (Nbr Device, Nbr IP etc.. ). The first level must be the name of the module in lowercase (dcim, ipam etc..), the second level must be the name of the object (usually starting with a uppercase). Note that you can include models from plugins by specifying the module name under the "_module" key
- `versions` nested dict, publish the versions of installed software

```python
Expand Down
9 changes: 6 additions & 3 deletions nautobot_capacity_metrics/metrics.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
import importlib
import platform
from collections.abc import Iterable
from copy import deepcopy

import django
from packaging import version
Expand Down Expand Up @@ -111,10 +112,12 @@ def metric_models(params):
nautobot_model_count: with model name and application name as labels
"""
gauge = GaugeMetricFamily("nautobot_model_count", "Per Nautobot Model count", labels=["app", "name"])
for app, _ in params.items():
for model, _ in params[app].items():
for app in params:
app_config = deepcopy(params[app]) # Avoid changing the dictionary we are iterating over
module = app_config.pop("_module", "nautobot")
for model in app_config:
try:
models = importlib.import_module(f"nautobot.{app}.models")
models = importlib.import_module(f"{module}.{app}.models")
model_class = getattr(models, model)
gauge.add_metric([app, model], model_class.objects.count())
except ModuleNotFoundError:
Expand Down
30 changes: 30 additions & 0 deletions nautobot_capacity_metrics/test_models/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
"""Plugin declaration for nautobot_capacity_metrics.test_models.
Why is this here? In order to test the plugin model count metric mechanics, a plugin metric had to be introduced.
This was put into a separate app so that it is not installed whenever this plugin is installed, rather just when tests
are ran within this plugins development environment.
"""

__version__ = "1.0.0"

from nautobot.extras.plugins import PluginConfig


class TestConfig(PluginConfig):
"""Plugin configuration for the nautobot_capacity_metrics plugin."""

name = "nautobot_capacity_metrics.test_models"
verbose_name = "Metrics & Monitoring Extension Test Model Plugin"
version = __version__
author = "Network to Code, LLC"
author_email = "[email protected]"
description = "Plugin that exists solely to test nautobot_capacity_metrics, don't install.."
base_url = "capacity-metrics-test"
required_settings = []
min_version = "1.2.0"
max_version = "1.9999"
default_settings = {}
caching_config = {}


config = TestConfig # pylint:disable=invalid-name
29 changes: 29 additions & 0 deletions nautobot_capacity_metrics/test_models/migrations/0001_initial.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
# Generated by Django 3.2.16 on 2022-12-20 13:24

from django.db import migrations, models
import uuid


class Migration(migrations.Migration):

initial = True

dependencies = []

operations = [
migrations.CreateModel(
name="TestModel",
fields=[
(
"id",
models.UUIDField(
default=uuid.uuid4, editable=False, primary_key=True, serialize=False, unique=True
),
),
("name", models.CharField(max_length=20)),
],
options={
"abstract": False,
},
),
]
Empty file.
10 changes: 10 additions & 0 deletions nautobot_capacity_metrics/test_models/models.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
"""Models for the testing plugin."""

from django.db.models import CharField
from nautobot.core.models import BaseModel


class TestModel(BaseModel):
"""This is a model solely used for the testing of the capacity metrics plugin."""

name = CharField(max_length=20)
6 changes: 6 additions & 0 deletions nautobot_capacity_metrics/tests/test_endpoints.py
Original file line number Diff line number Diff line change
Expand Up @@ -21,3 +21,9 @@ def test_endpoint(self):
self.assertEqual(resp.status_code, status.HTTP_200_OK)
resp = self.client.get(self.rq_metric_url)
self.assertEqual(resp.status_code, status.HTTP_200_OK)

def test_model_count_metrics(self):
"""Ensure that the model count metrics work correctly."""
resp = self.client.get(self.app_metric_url)
if "TestModel" not in resp.content.decode("utf-8"):
self.fail("nautobot_capacity_metrics.test_models.models.TestModel does not report its count.")

0 comments on commit b6a40cc

Please sign in to comment.