netbox-super-cli 1.4.0__tar.gz → 1.5.0__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.
- netbox_super_cli-1.5.0/.github/ISSUE_TEMPLATE/bug_report.yml +127 -0
- netbox_super_cli-1.5.0/.github/ISSUE_TEMPLATE/config.yml +11 -0
- netbox_super_cli-1.5.0/.github/ISSUE_TEMPLATE/docs.yml +35 -0
- netbox_super_cli-1.5.0/.github/ISSUE_TEMPLATE/feature_request.yml +68 -0
- netbox_super_cli-1.5.0/.github/pull_request_template.md +17 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/.github/workflows/test.yml +2 -3
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/CHANGELOG.md +18 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/PKG-INFO +19 -9
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/README.md +10 -6
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/guides/interactive-tui.md +16 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/_version.py +1 -1
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/registration.py +22 -10
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/tui_commands.py +7 -47
- netbox_super_cli-1.5.0/nsc/config/saved_searches.py +112 -0
- netbox_super_cli-1.5.0/nsc/savedfilters/__init__.py +4 -0
- netbox_super_cli-1.5.0/nsc/savedfilters/objecttypes.py +103 -0
- netbox_super_cli-1.5.0/nsc/savedfilters/params.py +55 -0
- netbox_super_cli-1.5.0/nsc/savedfilters/store.py +140 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/__init__.py +2 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/app.py +34 -1
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/screens/filter.py +27 -9
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/pyproject.toml +9 -3
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_registration.py +20 -6
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_tui_command.py +13 -31
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/writes/test_bulk.py +19 -14
- netbox_super_cli-1.5.0/tests/config/test_saved_search_fallback.py +55 -0
- netbox_super_cli-1.5.0/tests/savedfilters/test_objecttypes.py +123 -0
- netbox_super_cli-1.5.0/tests/savedfilters/test_params.py +64 -0
- netbox_super_cli-1.5.0/tests/savedfilters/test_store.py +190 -0
- netbox_super_cli-1.5.0/tests/tui/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_filter_screen.py +6 -0
- netbox_super_cli-1.5.0/tests/tui/test_saved_filter_integration.py +98 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/uv.lock +1 -1
- netbox_super_cli-1.4.0/nsc/config/saved_searches.py +0 -54
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/.github/dependabot.yml +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/.github/workflows/bench.yml +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/.github/workflows/claude.yml +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/.github/workflows/docs.yml +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/.github/workflows/e2e.yml +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/.github/workflows/lint.yml +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/.github/workflows/release.yml +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/.github/workflows/skill-convention-review.yml +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/.gitignore +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/.pre-commit-config.yaml +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/.python-version +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/AGENTS.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/CLAUDE.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/LICENSE +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/architecture/caching.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/architecture/command-generation.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/architecture/http-client.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/architecture/overview.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/architecture/schema-loading.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/assets/tui/detail.svg +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/assets/tui/filter.svg +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/assets/tui/list.svg +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/assets/tui/picker.svg +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/assets/tui/search.svg +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/contributing/adding-bundled-schemas.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/contributing/branching.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/contributing/development.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/contributing/release-process.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/getting-started/concepts.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/getting-started/first-run.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/getting-started/install.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/guides/audit-log.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/guides/ci-and-automation.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/guides/managing-profiles.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/guides/output-formats.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/guides/using-with-ai-agents.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/guides/working-with-plugins.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/guides/writes-and-safety.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/index.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/reference/cli.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/reference/config.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/reference/exit-codes.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/docs/reference/schemas.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/justfile +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/mkdocs.yml +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/__main__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/aliases/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/aliases/resolver.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/auth/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/auth/verify.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/builder/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/builder/build.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cache/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cache/store.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/aliases_commands.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/app.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/cache_commands.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/commands_dump.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/config_commands.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/globals.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/handlers.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/init_commands.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/login_commands.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/profiles_commands.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/runtime.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/skill_commands.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/writes/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/writes/apply.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/writes/bulk.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/writes/coercion.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/writes/confirmation.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/writes/input.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/cli/writes/preflight.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/completion/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/completion/cache_probe.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/completion/callbacks.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/completion/providers.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/config/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/config/loader.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/config/models.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/config/settings.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/config/writer.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/http/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/http/audit.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/http/client.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/http/errors.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/http/retry.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/model/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/model/command_model.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/output/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/output/_console.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/output/colors.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/output/csv_.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/output/errors.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/output/explain.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/output/flatten.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/output/headers.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/output/json_.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/output/jsonl.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/output/render.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/output/table.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/output/yaml_.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/schema/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/schema/hashing.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/schema/loader.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/schema/models.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/schema/source.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/schemas/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/schemas/bundled/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/schemas/bundled/manifest.yaml +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/schemas/bundled/netbox-4.5.10.json.gz +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/schemas/bundled/netbox-4.6.0.json.gz +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/skill/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/_bindings.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/bulk.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/catalog.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/columns.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/errors.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/filters.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/fk.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/forms.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/keymap.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/nav.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/relations.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/screens/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/screens/bulk_edit_form.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/screens/columns.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/screens/detail.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/screens/edit_form.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/screens/global_search.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/screens/list.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/screens/picker.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/screens/record_picker.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/screens/saved_search_picker.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/search.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/selection.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/styles.tcss +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/view.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/widgets/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/widgets/_modal.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/widgets/bulk_diff.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/widgets/bulk_summary.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/widgets/confirm.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/widgets/diff.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/widgets/help.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/nsc/tui/widgets/nav_tree.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/scripts/gen_docs.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/scripts/sync_agents_md.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/skills/netbox-super-cli/SKILL.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/aliases/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/aliases/test_resolver.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/audit/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/audit/test_redaction_full.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/auth/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/auth/test_verify.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/benchmarks/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/benchmarks/test_startup.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/builder/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/builder/test_build.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/builder/test_default_columns.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/builder/test_redaction_marking.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/builder/test_request_body_shape.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cache/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cache/test_prune.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cache/test_store.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_aliases_commands.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_app_smoke.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_cache_commands.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_commands_dump.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_completion_protocol_smoke.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_completion_smoke.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_config_commands.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_dynamic_completion.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_explain.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_globals_color.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_handlers.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_init_commands.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_lazy_textual_import.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_login_commands.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_meta_subcommands_under_broken_config.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_ndjson_input.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_profiles_commands.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_respx_integration.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_runtime.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_runtime_color.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_skill_commands.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_stdin_sniffer.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/test_writes_respx.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/writes/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/writes/test_apply.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/writes/test_confirmation.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/writes/test_handler_helpers.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/writes/test_handlers_audit.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/writes/test_input.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/cli/writes/test_preflight.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/config/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/config/test_loader.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/config/test_models.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/config/test_saved_searches.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/config/test_settings_private_dir.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/config/test_writer_atomicity.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/config/test_writer_dotted_paths.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/config/test_writer_roundtrip.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/conftest.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/e2e/README.md +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/e2e/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/e2e/conftest.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/e2e/docker-compose.yml +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/e2e/test_audit_redaction.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/e2e/test_auth_error_envelope.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/e2e/test_bulk_create_with_loop_fallback.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/e2e/test_full_cycle.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/e2e/test_login.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/e2e/test_ndjson.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/e2e/test_preflight_blocks_apply.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/e2e/test_validation_error_envelope_from_netbox.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/e2e/wait_for_netbox.sh +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/fixtures/profiles/single_profile.yaml +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/fixtures/responses/auth_401.json +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/fixtures/responses/circuits_providers_list.json +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/fixtures/responses/dcim_devices_get.json +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/fixtures/responses/dcim_devices_list_p1.json +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/fixtures/responses/dcim_devices_list_p2.json +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/http/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/http/test_audit.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/http/test_audit_permissions.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/http/test_audit_redaction.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/http/test_client.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/http/test_client_redaction_threading.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/http/test_errors.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/http/test_retry.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/model/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/model/test_command_model.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/model/test_request_body_shape.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/output/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/output/test_colors.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/output/test_console.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/output/test_csv.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/output/test_errors.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/output/test_errors_aliases.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/output/test_errors_color.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/output/test_explain.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/output/test_explain_color.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/output/test_flatten.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/output/test_input_error_envelope.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/output/test_json.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/output/test_jsonl.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/output/test_render_dispatch.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/output/test_table.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/output/test_table_color.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/output/test_yaml.py +0 -0
- {netbox_super_cli-1.4.0/tests/schema → netbox_super_cli-1.5.0/tests/savedfilters}/__init__.py +0 -0
- {netbox_super_cli-1.4.0/tests/scripts → netbox_super_cli-1.5.0/tests/schema}/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/schema/test_hashing.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/schema/test_loader.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/schema/test_models.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/schema/test_source.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/schema/test_source_ttl.py +0 -0
- {netbox_super_cli-1.4.0/tests/skill → netbox_super_cli-1.5.0/tests/scripts}/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/scripts/test_gen_docs.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/scripts/test_sync_agents_md.py +0 -0
- {netbox_super_cli-1.4.0/tests/tui → netbox_super_cli-1.5.0/tests/skill}/__init__.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/skill/test_bundle.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/test_packaging.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_app.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_bindings.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_bulk_apply.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_bulk_diff.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_bulk_diff_modal.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_bulk_edit_form.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_bulk_import_isolation.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_bulk_summary.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_catalog.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_column_chooser.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_columns.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_detail_screen.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_diff.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_diff_modal.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_edit_form.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_errors.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_filters.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_fk_resolve.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_forms.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_global_search.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_help_overlay.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_keymap.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_list_screen.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_picker.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_record_picker.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_relations.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_search.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_selection.py +0 -0
- {netbox_super_cli-1.4.0 → netbox_super_cli-1.5.0}/tests/tui/test_view.py +0 -0
|
@@ -0,0 +1,127 @@
|
|
|
1
|
+
name: 🐞 Bug report
|
|
2
|
+
description: Something in nsc (the CLI or TUI) behaves incorrectly or crashes.
|
|
3
|
+
title: "[Bug]: "
|
|
4
|
+
labels: ["bug"]
|
|
5
|
+
body:
|
|
6
|
+
- type: markdown
|
|
7
|
+
attributes:
|
|
8
|
+
value: |
|
|
9
|
+
Thanks for filing a bug! The version numbers and the **exact command** make
|
|
10
|
+
most issues reproducible — please fill in as much as you can.
|
|
11
|
+
|
|
12
|
+
> [!WARNING]
|
|
13
|
+
> **Redact secrets.** Never paste your `NSC_TOKEN`, API tokens, or any
|
|
14
|
+
> credential. Replace them with `***`.
|
|
15
|
+
|
|
16
|
+
- type: input
|
|
17
|
+
id: nsc-version
|
|
18
|
+
attributes:
|
|
19
|
+
label: nsc version
|
|
20
|
+
description: Output of `nsc --version`.
|
|
21
|
+
placeholder: "nsc 1.4.0"
|
|
22
|
+
validations:
|
|
23
|
+
required: true
|
|
24
|
+
|
|
25
|
+
- type: dropdown
|
|
26
|
+
id: install-method
|
|
27
|
+
attributes:
|
|
28
|
+
label: How did you install nsc?
|
|
29
|
+
options:
|
|
30
|
+
- uv tool install
|
|
31
|
+
- pipx
|
|
32
|
+
- pip
|
|
33
|
+
- uvx (ephemeral)
|
|
34
|
+
- from source / git checkout
|
|
35
|
+
- other
|
|
36
|
+
validations:
|
|
37
|
+
required: true
|
|
38
|
+
|
|
39
|
+
- type: input
|
|
40
|
+
id: python-version
|
|
41
|
+
attributes:
|
|
42
|
+
label: Python version
|
|
43
|
+
description: Output of `python --version` for the interpreter nsc runs under.
|
|
44
|
+
placeholder: "3.12.x"
|
|
45
|
+
validations:
|
|
46
|
+
required: true
|
|
47
|
+
|
|
48
|
+
- type: dropdown
|
|
49
|
+
id: os
|
|
50
|
+
attributes:
|
|
51
|
+
label: Operating system
|
|
52
|
+
options:
|
|
53
|
+
- Linux
|
|
54
|
+
- macOS
|
|
55
|
+
- Windows
|
|
56
|
+
- Other
|
|
57
|
+
validations:
|
|
58
|
+
required: true
|
|
59
|
+
|
|
60
|
+
- type: input
|
|
61
|
+
id: netbox-version
|
|
62
|
+
attributes:
|
|
63
|
+
label: NetBox version
|
|
64
|
+
description: The NetBox server version nsc talks to (NetBox UI footer, or `/api/status/`).
|
|
65
|
+
placeholder: "v4.6.3"
|
|
66
|
+
validations:
|
|
67
|
+
required: false
|
|
68
|
+
|
|
69
|
+
- type: dropdown
|
|
70
|
+
id: schema-source
|
|
71
|
+
attributes:
|
|
72
|
+
label: Which schema was nsc using?
|
|
73
|
+
description: nsc generates commands from the OpenAPI schema — a live fetch, the on-disk cache, or the bundled offline snapshot.
|
|
74
|
+
options:
|
|
75
|
+
- Live NetBox API
|
|
76
|
+
- Cached schema
|
|
77
|
+
- Bundled offline snapshot
|
|
78
|
+
- Not sure
|
|
79
|
+
validations:
|
|
80
|
+
required: false
|
|
81
|
+
|
|
82
|
+
- type: textarea
|
|
83
|
+
id: command
|
|
84
|
+
attributes:
|
|
85
|
+
label: Command you ran
|
|
86
|
+
description: The exact `nsc ...` invocation. Redact tokens.
|
|
87
|
+
render: shell
|
|
88
|
+
placeholder: nsc dcim devices list --site-id 42 --output json
|
|
89
|
+
validations:
|
|
90
|
+
required: true
|
|
91
|
+
|
|
92
|
+
- type: textarea
|
|
93
|
+
id: what-happened
|
|
94
|
+
attributes:
|
|
95
|
+
label: What happened?
|
|
96
|
+
description: The actual behavior, including any error message or traceback.
|
|
97
|
+
render: shell
|
|
98
|
+
validations:
|
|
99
|
+
required: true
|
|
100
|
+
|
|
101
|
+
- type: textarea
|
|
102
|
+
id: expected
|
|
103
|
+
attributes:
|
|
104
|
+
label: What did you expect to happen?
|
|
105
|
+
validations:
|
|
106
|
+
required: true
|
|
107
|
+
|
|
108
|
+
- type: textarea
|
|
109
|
+
id: logs
|
|
110
|
+
attributes:
|
|
111
|
+
label: Relevant logs / audit output
|
|
112
|
+
description: Optional. Anything else that helps — re-run with extra output if useful. Redact secrets first.
|
|
113
|
+
render: shell
|
|
114
|
+
validations:
|
|
115
|
+
required: false
|
|
116
|
+
|
|
117
|
+
- type: checkboxes
|
|
118
|
+
id: checks
|
|
119
|
+
attributes:
|
|
120
|
+
label: Before submitting
|
|
121
|
+
options:
|
|
122
|
+
- label: I searched existing issues and this isn't a duplicate.
|
|
123
|
+
required: true
|
|
124
|
+
- label: I'm on the latest release of nsc, or I noted my version above.
|
|
125
|
+
required: true
|
|
126
|
+
- label: I removed any tokens / credentials from the command and logs above.
|
|
127
|
+
required: true
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
blank_issues_enabled: false
|
|
2
|
+
contact_links:
|
|
3
|
+
- name: 📖 Documentation
|
|
4
|
+
url: https://thomaschristory.github.io/netbox-super-cli/
|
|
5
|
+
about: Guides, the CLI/TUI reference, and configuration docs — please check here first.
|
|
6
|
+
- name: 💬 Questions & usage help
|
|
7
|
+
url: https://github.com/thomaschristory/netbox-super-cli/discussions
|
|
8
|
+
about: Ask how-to questions, share setups, or propose ideas before filing a feature request.
|
|
9
|
+
- name: 🔐 Security vulnerability
|
|
10
|
+
url: https://github.com/thomaschristory/netbox-super-cli/security/advisories/new
|
|
11
|
+
about: Report a security issue privately. Please do NOT open a public issue for vulnerabilities.
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
name: 📖 Documentation issue
|
|
2
|
+
description: A gap, error, or confusing part of the docs, README, or bundled SKILL.
|
|
3
|
+
title: "[Docs]: "
|
|
4
|
+
labels: ["documentation"]
|
|
5
|
+
body:
|
|
6
|
+
- type: textarea
|
|
7
|
+
id: where
|
|
8
|
+
attributes:
|
|
9
|
+
label: Where is the problem?
|
|
10
|
+
description: A page URL, a file path (e.g. `README.md`, `docs/...`), or a command's `--help` output.
|
|
11
|
+
validations:
|
|
12
|
+
required: true
|
|
13
|
+
|
|
14
|
+
- type: textarea
|
|
15
|
+
id: problem
|
|
16
|
+
attributes:
|
|
17
|
+
label: What's wrong or missing?
|
|
18
|
+
validations:
|
|
19
|
+
required: true
|
|
20
|
+
|
|
21
|
+
- type: textarea
|
|
22
|
+
id: suggestion
|
|
23
|
+
attributes:
|
|
24
|
+
label: Suggested fix
|
|
25
|
+
description: Optional — a sentence, a corrected snippet, or a link to the right info.
|
|
26
|
+
validations:
|
|
27
|
+
required: false
|
|
28
|
+
|
|
29
|
+
- type: checkboxes
|
|
30
|
+
id: checks
|
|
31
|
+
attributes:
|
|
32
|
+
label: Before submitting
|
|
33
|
+
options:
|
|
34
|
+
- label: I searched existing issues and this isn't a duplicate.
|
|
35
|
+
required: true
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
name: ✨ Feature request
|
|
2
|
+
description: Suggest a new capability or improvement for the CLI, TUI, or output.
|
|
3
|
+
title: "[Feature]: "
|
|
4
|
+
labels: ["enhancement"]
|
|
5
|
+
body:
|
|
6
|
+
- type: markdown
|
|
7
|
+
attributes:
|
|
8
|
+
value: |
|
|
9
|
+
Thanks for the idea! Describing the **problem** first (not just the
|
|
10
|
+
solution) helps us find the best fit. nsc is generated from NetBox's
|
|
11
|
+
OpenAPI schema, so features usually apply across every resource.
|
|
12
|
+
|
|
13
|
+
- type: dropdown
|
|
14
|
+
id: area
|
|
15
|
+
attributes:
|
|
16
|
+
label: Which area?
|
|
17
|
+
options:
|
|
18
|
+
- CLI (commands, flags, output)
|
|
19
|
+
- TUI (interactive browser)
|
|
20
|
+
- Output / formatting (table, json, jsonl, yaml, csv)
|
|
21
|
+
- Config / auth / profiles
|
|
22
|
+
- Shell completion
|
|
23
|
+
- Schema / code generation
|
|
24
|
+
- Documentation
|
|
25
|
+
- Other / not sure
|
|
26
|
+
validations:
|
|
27
|
+
required: true
|
|
28
|
+
|
|
29
|
+
- type: textarea
|
|
30
|
+
id: problem
|
|
31
|
+
attributes:
|
|
32
|
+
label: What problem are you trying to solve?
|
|
33
|
+
description: What are you trying to do, and where does nsc get in the way today?
|
|
34
|
+
validations:
|
|
35
|
+
required: true
|
|
36
|
+
|
|
37
|
+
- type: textarea
|
|
38
|
+
id: proposal
|
|
39
|
+
attributes:
|
|
40
|
+
label: Proposed solution
|
|
41
|
+
description: What would you like nsc to do? A sketch of the command, flag, or UX is great.
|
|
42
|
+
validations:
|
|
43
|
+
required: false
|
|
44
|
+
|
|
45
|
+
- type: textarea
|
|
46
|
+
id: example
|
|
47
|
+
attributes:
|
|
48
|
+
label: Example usage
|
|
49
|
+
description: How would it look on the command line (or in the TUI)?
|
|
50
|
+
render: shell
|
|
51
|
+
placeholder: nsc dcim devices list --some-new-flag
|
|
52
|
+
validations:
|
|
53
|
+
required: false
|
|
54
|
+
|
|
55
|
+
- type: textarea
|
|
56
|
+
id: alternatives
|
|
57
|
+
attributes:
|
|
58
|
+
label: Alternatives considered
|
|
59
|
+
validations:
|
|
60
|
+
required: false
|
|
61
|
+
|
|
62
|
+
- type: checkboxes
|
|
63
|
+
id: checks
|
|
64
|
+
attributes:
|
|
65
|
+
label: Before submitting
|
|
66
|
+
options:
|
|
67
|
+
- label: I searched existing issues and this isn't a duplicate.
|
|
68
|
+
required: true
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
<!--
|
|
2
|
+
Thanks for contributing to netbox-super-cli! Keep this short — a couple of
|
|
3
|
+
sentences plus the checklist is plenty. See CLAUDE.md / docs/contributing for
|
|
4
|
+
conventions.
|
|
5
|
+
-->
|
|
6
|
+
|
|
7
|
+
## What & why
|
|
8
|
+
|
|
9
|
+
<!-- What does this change, and why? Link the issue: Closes #123 -->
|
|
10
|
+
|
|
11
|
+
## Checklist
|
|
12
|
+
|
|
13
|
+
- [ ] PR title follows [Conventional Commits](https://www.conventionalcommits.org/) (`feat:`, `fix:`, `docs:`, `chore:`, `refactor:`, …)
|
|
14
|
+
- [ ] Tests added or updated, and `just test` passes
|
|
15
|
+
- [ ] `just lint` passes (ruff + `mypy --strict`)
|
|
16
|
+
- [ ] Docs / `CHANGELOG.md` updated if this is user-facing
|
|
17
|
+
- [ ] Linked the related issue (e.g. `Closes #…`)
|
|
@@ -10,12 +10,11 @@ permissions:
|
|
|
10
10
|
|
|
11
11
|
jobs:
|
|
12
12
|
test:
|
|
13
|
-
runs-on:
|
|
13
|
+
runs-on: ubuntu-latest
|
|
14
14
|
strategy:
|
|
15
15
|
fail-fast: false
|
|
16
16
|
matrix:
|
|
17
|
-
|
|
18
|
-
python: ["3.12", "3.13"]
|
|
17
|
+
python: ["3.12", "3.13", "3.14"]
|
|
19
18
|
steps:
|
|
20
19
|
- uses: actions/checkout@v7
|
|
21
20
|
- name: Install uv
|
|
@@ -2,6 +2,24 @@
|
|
|
2
2
|
|
|
3
3
|
All notable changes to netbox-super-cli are tracked here. Format follows [Keep a Changelog](https://keepachangelog.com/en/1.1.0/) loosely. From v1.0.0 onward, releases follow [Semantic Versioning](https://semver.org/) and the version in `pyproject.toml` matches the git tag. Pre-1.0 milestones (Phase 1-5) were pinned by tag while `pyproject.toml` stayed at `0.0.1`.
|
|
4
4
|
|
|
5
|
+
## v1.5.0 — 2026-06-29
|
|
6
|
+
|
|
7
|
+
Minor release. Saved searches become interchangeable with the NetBox web UI.
|
|
8
|
+
|
|
9
|
+
### Changed
|
|
10
|
+
|
|
11
|
+
- **Saved searches are now NetBox-native** ([#129]). Filter sets saved from the
|
|
12
|
+
TUI (`Ctrl+W`) and applied via `--saved` are stored as NetBox saved filters
|
|
13
|
+
(`extras.saved-filters`), scoped to the resource's object type, so they are
|
|
14
|
+
fully interchangeable with the web UI's filter dropdown — a search saved in
|
|
15
|
+
`nsc` appears in the web UI and vice versa. The object type is resolved from
|
|
16
|
+
NetBox's own object-type registry (`/api/core/object-types/`), so the mapping
|
|
17
|
+
is exact rather than guessed. When NetBox is unreachable or the user lacks
|
|
18
|
+
permission on `extras.savedfilter`, saves/loads transparently fall back to the
|
|
19
|
+
previous local `config.yaml` store and surface a notice instead of failing.
|
|
20
|
+
|
|
21
|
+
[#129]: https://github.com/thomaschristory/netbox-super-cli/issues/129
|
|
22
|
+
|
|
5
23
|
## v1.4.0 — 2026-06-26
|
|
6
24
|
|
|
7
25
|
Minor release. Three user-facing features for the interactive TUI and table
|
|
@@ -1,19 +1,25 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: netbox-super-cli
|
|
3
|
-
Version: 1.
|
|
3
|
+
Version: 1.5.0
|
|
4
4
|
Summary: Dynamic NetBox CLI generated from the live OpenAPI schema.
|
|
5
5
|
Project-URL: Homepage, https://github.com/thomaschristory/netbox-super-cli
|
|
6
|
+
Project-URL: Documentation, https://thomaschristory.github.io/netbox-super-cli/
|
|
7
|
+
Project-URL: Source, https://github.com/thomaschristory/netbox-super-cli
|
|
6
8
|
Project-URL: Issues, https://github.com/thomaschristory/netbox-super-cli/issues
|
|
7
|
-
|
|
9
|
+
Project-URL: Changelog, https://github.com/thomaschristory/netbox-super-cli/blob/main/CHANGELOG.md
|
|
10
|
+
Author: Thomas Christory
|
|
8
11
|
License-Expression: Apache-2.0
|
|
9
12
|
License-File: LICENSE
|
|
10
13
|
Keywords: automation,cli,netbox,openapi
|
|
11
|
-
Classifier: Development Status ::
|
|
14
|
+
Classifier: Development Status :: 5 - Production/Stable
|
|
12
15
|
Classifier: Environment :: Console
|
|
16
|
+
Classifier: Intended Audience :: Information Technology
|
|
13
17
|
Classifier: Intended Audience :: System Administrators
|
|
18
|
+
Classifier: Intended Audience :: Telecommunications Industry
|
|
14
19
|
Classifier: License :: OSI Approved :: Apache Software License
|
|
15
20
|
Classifier: Programming Language :: Python :: 3.12
|
|
16
21
|
Classifier: Programming Language :: Python :: 3.13
|
|
22
|
+
Classifier: Programming Language :: Python :: 3.14
|
|
17
23
|
Classifier: Topic :: System :: Networking
|
|
18
24
|
Requires-Python: >=3.12
|
|
19
25
|
Requires-Dist: click>=8.1
|
|
@@ -114,9 +120,12 @@ uv run nsc ipam prefixes list --filter created__gte=2026-01-01 --output yaml
|
|
|
114
120
|
|
|
115
121
|
### Saved searches
|
|
116
122
|
|
|
117
|
-
Filter sets you save from the TUI (Ctrl+W in the filter builder) are stored
|
|
118
|
-
|
|
119
|
-
|
|
123
|
+
Filter sets you save from the TUI (Ctrl+W in the filter builder) are stored as
|
|
124
|
+
**NetBox native saved filters** (`extras.saved-filters`), scoped to the resource's
|
|
125
|
+
object type. A search you save in `nsc` shows up in the NetBox web UI's filter
|
|
126
|
+
dropdown for that object — and a filter saved in the web UI loads in the TUI
|
|
127
|
+
(Ctrl+O) — so the two are fully interchangeable. Re-apply one on the CLI with
|
|
128
|
+
`--saved`:
|
|
120
129
|
|
|
121
130
|
```sh
|
|
122
131
|
uv run nsc dcim devices list --saved active-switches
|
|
@@ -124,9 +133,10 @@ uv run nsc dcim devices list --saved active-switches
|
|
|
124
133
|
uv run nsc dcim devices list --saved active-switches --status offline
|
|
125
134
|
```
|
|
126
135
|
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
136
|
+
When NetBox is unreachable (offline, or missing permission on
|
|
137
|
+
`extras.savedfilter`), `nsc` transparently falls back to a local store under
|
|
138
|
+
`saved_searches` in `~/.nsc/config.yaml`, keyed by tag/resource, and tells you it
|
|
139
|
+
did so.
|
|
130
140
|
|
|
131
141
|
### Object colors
|
|
132
142
|
|
|
@@ -85,9 +85,12 @@ uv run nsc ipam prefixes list --filter created__gte=2026-01-01 --output yaml
|
|
|
85
85
|
|
|
86
86
|
### Saved searches
|
|
87
87
|
|
|
88
|
-
Filter sets you save from the TUI (Ctrl+W in the filter builder) are stored
|
|
89
|
-
|
|
90
|
-
|
|
88
|
+
Filter sets you save from the TUI (Ctrl+W in the filter builder) are stored as
|
|
89
|
+
**NetBox native saved filters** (`extras.saved-filters`), scoped to the resource's
|
|
90
|
+
object type. A search you save in `nsc` shows up in the NetBox web UI's filter
|
|
91
|
+
dropdown for that object — and a filter saved in the web UI loads in the TUI
|
|
92
|
+
(Ctrl+O) — so the two are fully interchangeable. Re-apply one on the CLI with
|
|
93
|
+
`--saved`:
|
|
91
94
|
|
|
92
95
|
```sh
|
|
93
96
|
uv run nsc dcim devices list --saved active-switches
|
|
@@ -95,9 +98,10 @@ uv run nsc dcim devices list --saved active-switches
|
|
|
95
98
|
uv run nsc dcim devices list --saved active-switches --status offline
|
|
96
99
|
```
|
|
97
100
|
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
+
When NetBox is unreachable (offline, or missing permission on
|
|
102
|
+
`extras.savedfilter`), `nsc` transparently falls back to a local store under
|
|
103
|
+
`saved_searches` in `~/.nsc/config.yaml`, keyed by tag/resource, and tells you it
|
|
104
|
+
did so.
|
|
101
105
|
|
|
102
106
|
### Object colors
|
|
103
107
|
|
|
@@ -81,11 +81,27 @@ NetBox list endpoint exposes hundreds of query parameters.
|
|
|
81
81
|
| <kbd>↓</kbd> | Move to the next field (from a text field) |
|
|
82
82
|
| <kbd>Tab</kbd> / <kbd>Shift</kbd>+<kbd>Tab</kbd> | Move between fields |
|
|
83
83
|
| <kbd>Ctrl</kbd>+<kbd>S</kbd> | Apply |
|
|
84
|
+
| <kbd>Ctrl</kbd>+<kbd>W</kbd> | Save the current filters as a named search |
|
|
85
|
+
| <kbd>Ctrl</kbd>+<kbd>O</kbd> | Load (or delete) a saved search |
|
|
84
86
|
| <kbd>Esc</kbd> | Cancel |
|
|
85
87
|
|
|
86
88
|
Applying re-queries the list. Reopening the builder shows your current filters
|
|
87
89
|
so you can refine them.
|
|
88
90
|
|
|
91
|
+
### Saved searches
|
|
92
|
+
|
|
93
|
+
<kbd>Ctrl</kbd>+<kbd>W</kbd> stores the current filter set as a NetBox **native
|
|
94
|
+
saved filter** (`extras.saved-filters`), scoped to the current resource's object
|
|
95
|
+
type. It then appears in the NetBox web UI's filter dropdown for that object, and
|
|
96
|
+
filters created in the web UI load here with <kbd>Ctrl</kbd>+<kbd>O</kbd> — the two
|
|
97
|
+
surfaces are interchangeable. In the load picker, <kbd>Enter</kbd> applies the
|
|
98
|
+
highlighted search and <kbd>d</kbd> deletes it. Re-apply one non-interactively
|
|
99
|
+
with `nsc <app> <resource> list --saved <name>`.
|
|
100
|
+
|
|
101
|
+
If NetBox is unreachable (offline, or you lack permission on
|
|
102
|
+
`extras.savedfilter`), saves and loads transparently fall back to a local store in
|
|
103
|
+
`~/.nsc/config.yaml` and a toast tells you the fallback was used.
|
|
104
|
+
|
|
89
105
|
## Viewing and editing a record
|
|
90
106
|
|
|
91
107
|
The detail view **is** the edit surface — there is no separate "edit window".
|
|
@@ -128,22 +128,33 @@ def _resolve_saved_filters(
|
|
|
128
128
|
ctx: RuntimeContext,
|
|
129
129
|
tag_name: str,
|
|
130
130
|
resource_name: str,
|
|
131
|
+
list_path: str,
|
|
131
132
|
saved_name: str | None,
|
|
132
133
|
explicit_filters: list[tuple[str, str]],
|
|
133
134
|
typed_kwargs: dict[str, Any],
|
|
134
135
|
) -> list[tuple[str, str]]:
|
|
135
136
|
"""Layer a `--saved` filter set under explicit `--filter` and typed options.
|
|
136
137
|
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
138
|
+
The set is resolved against NetBox's native saved filters (interchangeable
|
|
139
|
+
with the web UI), falling back to the local `config.yaml` map when the API is
|
|
140
|
+
unavailable. Saved params are the base; explicit `--filter` pairs and any
|
|
141
|
+
non-None typed query option (already in ``typed_kwargs``) win. Order matters:
|
|
142
|
+
``handle_list`` overlays ``ctx.filters`` onto the typed-option params, so
|
|
143
|
+
saved keys that the user also set via a typed flag must be dropped here to let
|
|
144
|
+
the flag win.
|
|
141
145
|
"""
|
|
142
146
|
if saved_name is None:
|
|
143
147
|
return explicit_filters
|
|
144
|
-
from nsc.config.saved_searches import
|
|
148
|
+
from nsc.config.saved_searches import ConfigFileSavedSearchStore # noqa: PLC0415
|
|
149
|
+
from nsc.savedfilters.store import NativeSavedFilterStore # noqa: PLC0415
|
|
145
150
|
|
|
146
|
-
|
|
151
|
+
store = NativeSavedFilterStore(
|
|
152
|
+
ctx.client,
|
|
153
|
+
ConfigFileSavedSearchStore(ctx.config),
|
|
154
|
+
on_error=lambda message: typer.echo(f"Warning: {message}", err=True),
|
|
155
|
+
)
|
|
156
|
+
available = store.list(list_path, tag_name, resource_name)
|
|
157
|
+
saved = available.get(saved_name)
|
|
147
158
|
if saved is None:
|
|
148
159
|
raise typer.BadParameter(
|
|
149
160
|
f"no saved search named {saved_name!r} for {tag_name}/{resource_name}"
|
|
@@ -191,7 +202,7 @@ def _build_read_closure(
|
|
|
191
202
|
"limit": limit,
|
|
192
203
|
"fetch_all": fetch_all,
|
|
193
204
|
"filters": _resolve_saved_filters(
|
|
194
|
-
ctx, tag_name, resource_name, saved_name, explicit_filters, kwargs
|
|
205
|
+
ctx, tag_name, resource_name, operation.path, saved_name, explicit_filters, kwargs
|
|
195
206
|
),
|
|
196
207
|
}
|
|
197
208
|
if output:
|
|
@@ -350,9 +361,10 @@ def _build_global_flag_params() -> tuple[inspect.Parameter, ...]:
|
|
|
350
361
|
None,
|
|
351
362
|
"--saved",
|
|
352
363
|
help=(
|
|
353
|
-
"Apply a
|
|
354
|
-
"
|
|
355
|
-
"
|
|
364
|
+
"Apply a named saved filter for this resource. Resolves against "
|
|
365
|
+
"NetBox's native saved filters (interchangeable with the web UI), "
|
|
366
|
+
"falling back to the local config `saved_searches` when the API is "
|
|
367
|
+
"unavailable. Explicit --filter/typed options override it."
|
|
356
368
|
),
|
|
357
369
|
),
|
|
358
370
|
),
|
|
@@ -41,44 +41,13 @@ def _save_columns(tag: str, resource: str, columns: list[str]) -> None:
|
|
|
41
41
|
atomic_write(path, dump_round_trip(doc))
|
|
42
42
|
|
|
43
43
|
|
|
44
|
-
def
|
|
45
|
-
"""
|
|
46
|
-
from nsc.config.saved_searches import
|
|
47
|
-
from nsc.
|
|
48
|
-
from nsc.config.writer import ( # noqa: PLC0415
|
|
49
|
-
acquire_lock,
|
|
50
|
-
atomic_write,
|
|
51
|
-
dump_round_trip,
|
|
52
|
-
load_round_trip,
|
|
53
|
-
set_path,
|
|
54
|
-
)
|
|
55
|
-
|
|
56
|
-
# Defensive: a dotted name would split into a nested map under set_path and
|
|
57
|
-
# corrupt the file. Validate before touching disk so the file is untouched.
|
|
58
|
-
validate_saved_search_name(name)
|
|
59
|
-
path = default_paths().config_file
|
|
60
|
-
with acquire_lock(path):
|
|
61
|
-
doc = load_round_trip(path)
|
|
62
|
-
set_path(doc, f"saved_searches.{tag}.{resource}.{name}", dict(params))
|
|
63
|
-
atomic_write(path, dump_round_trip(doc))
|
|
44
|
+
def _build_saved_filter_store(runtime: RuntimeContext) -> object:
|
|
45
|
+
"""Native NetBox SavedFilter store with a config.yaml offline fallback."""
|
|
46
|
+
from nsc.config.saved_searches import ConfigFileSavedSearchStore # noqa: PLC0415
|
|
47
|
+
from nsc.savedfilters.store import NativeSavedFilterStore # noqa: PLC0415
|
|
64
48
|
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
"""Remove ``saved_searches.<tag>.<resource>.<name>`` and prune empty parents."""
|
|
68
|
-
from nsc.config.settings import default_paths # noqa: PLC0415
|
|
69
|
-
from nsc.config.writer import ( # noqa: PLC0415
|
|
70
|
-
acquire_lock,
|
|
71
|
-
atomic_write,
|
|
72
|
-
dump_round_trip,
|
|
73
|
-
load_round_trip,
|
|
74
|
-
unset_path,
|
|
75
|
-
)
|
|
76
|
-
|
|
77
|
-
path = default_paths().config_file
|
|
78
|
-
with acquire_lock(path):
|
|
79
|
-
doc = load_round_trip(path)
|
|
80
|
-
unset_path(doc, f"saved_searches.{tag}.{resource}.{name}")
|
|
81
|
-
atomic_write(path, dump_round_trip(doc))
|
|
49
|
+
fallback = ConfigFileSavedSearchStore(runtime.config)
|
|
50
|
+
return NativeSavedFilterStore(runtime.client, fallback)
|
|
82
51
|
|
|
83
52
|
|
|
84
53
|
def register(app: typer.Typer) -> None:
|
|
@@ -94,13 +63,6 @@ def register(app: typer.Typer) -> None:
|
|
|
94
63
|
from nsc.tui import run_tui # noqa: PLC0415 # deferred: keeps Textual lazy.
|
|
95
64
|
|
|
96
65
|
column_prefs = {tag: dict(resources) for tag, resources in runtime.config.columns.items()}
|
|
97
|
-
saved_searches = {
|
|
98
|
-
tag: {
|
|
99
|
-
res: {name: dict(params) for name, params in sets.items()}
|
|
100
|
-
for res, sets in resources.items()
|
|
101
|
-
}
|
|
102
|
-
for tag, resources in runtime.config.saved_searches.items()
|
|
103
|
-
}
|
|
104
66
|
run_tui(
|
|
105
67
|
runtime.command_model,
|
|
106
68
|
runtime.client,
|
|
@@ -108,9 +70,7 @@ def register(app: typer.Typer) -> None:
|
|
|
108
70
|
save_columns=_save_columns,
|
|
109
71
|
column_prefs=column_prefs,
|
|
110
72
|
object_colors=runtime.object_colors,
|
|
111
|
-
|
|
112
|
-
save_search=_save_search,
|
|
113
|
-
delete_search=_delete_search,
|
|
73
|
+
saved_filter_store=_build_saved_filter_store(runtime),
|
|
114
74
|
)
|
|
115
75
|
|
|
116
76
|
# `tui` is canonical; `interactive` and `i` are hidden aliases for the same
|