xsoar-cli 2.1.1__tar.gz → 2.2.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.
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/CHANGELOG.md +26 -1
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/CLAUDE.md +1 -3
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/CONTRIBUTING.md +5 -30
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/PKG-INFO +2 -1
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/_version.py +2 -2
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/pyproject.toml +1 -1
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/cli.py +23 -7
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/case/commands.py +14 -7
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/completions/commands.py +2 -1
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/config/README.md +18 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/config/commands.py +26 -6
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/content/commands.py +9 -9
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/graph/commands.py +4 -3
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/integration/commands.py +8 -8
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/manifest/commands.py +6 -5
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/pack/commands.py +4 -4
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/plugins/README.md +13 -2
- xsoar_cli-2.2.0/src/xsoar_cli/commands/plugins/commands.py +257 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/rbac/commands.py +8 -8
- xsoar_cli-2.2.0/src/xsoar_cli/plugins/README.md +45 -0
- xsoar_cli-2.2.0/src/xsoar_cli/plugins/__init__.py +48 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/plugins/manager.py +59 -73
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/utilities/validators.py +19 -26
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/xsoar_client/artifact_providers/azure.py +4 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/xsoar_client/artifact_providers/s3.py +3 -3
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/xsoar_client/content.py +3 -2
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/cli/conftest.py +48 -14
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/cli/test_config.py +39 -0
- xsoar_cli-2.2.0/tests/cli/test_plugins.py +244 -0
- xsoar_cli-2.2.0/tests/unit/test_plugin_manager.py +319 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/test_validators.py +4 -4
- xsoar_cli-2.1.1/src/xsoar_cli/commands/plugins/commands.py +0 -184
- xsoar_cli-2.1.1/src/xsoar_cli/plugins/README.md +0 -53
- xsoar_cli-2.1.1/src/xsoar_cli/plugins/__init__.py +0 -62
- xsoar_cli-2.1.1/tests/cli/test_plugins.py +0 -104
- xsoar_cli-2.1.1/tests/unit/test_plugin_manager.py +0 -213
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/.github/workflows/main.yml +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/.github/workflows/pull-request-open.yml +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/.github/workflows/release.yml +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/.github/workflows/update-changelog.yml +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/.gitignore +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/LICENSE.txt +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/README.md +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/case/README.md +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/case/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/completions/README.md +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/completions/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/config/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/content/README.md +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/content/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/graph/README.md +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/graph/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/integration/README.md +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/integration/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/manifest/README.md +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/manifest/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/pack/README.md +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/pack/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/plugins/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/rbac/README.md +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/commands/rbac/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/configuration.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/error_handling/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/error_handling/connection.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/error_handling/http.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/log.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/utilities/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/utilities/config_file.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/utilities/content.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/utilities/download_content_handlers.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/utilities/manifest.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/utilities/version_check.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/xsoar_client/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/xsoar_client/artifact_providers/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/xsoar_client/artifact_providers/base.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/xsoar_client/cases.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/xsoar_client/client.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/xsoar_client/constants.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/xsoar_client/integrations.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/xsoar_client/packs.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/src/xsoar_cli/xsoar_client/rbac.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/cli/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/cli/test_base.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/cli/test_case.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/cli/test_completions.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/cli/test_content.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/cli/test_graph.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/cli/test_manifest.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/cli/test_pack.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/conftest.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/cases/create.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/cases/get.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/content/automation_search.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/content/playbook_search.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/content/user_commands.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/integrations/instances.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/manifest/manifest_base.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/manifest/manifest_invalid.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/manifest/manifest_with_pack_not_on_server.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/manifest/server_base_response.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/manifest/server_base_response_missing_one_pack.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/manifest/server_base_response_with_updates.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/manifest/server_base_response_with_updates_and_one_extra.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/packs/installed.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/packs/installed_expired.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/rbac/roles.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/rbac/user_groups.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/fixtures/rbac/users.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Download/playbook-empty.yml +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_CommonPlaybooks/.pack-ignore +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_CommonPlaybooks/.secrets-ignore +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_CommonPlaybooks/Author_image.png +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_CommonPlaybooks/Playbooks/GenericPlaybook.yml +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_CommonPlaybooks/README.md +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_CommonPlaybooks/pack_metadata.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_CommonScripts/.pack-ignore +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_CommonScripts/.secrets-ignore +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_CommonScripts/Author_image.png +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_CommonScripts/README.md +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_CommonScripts/Scripts/GenericScript/GenericScript.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_CommonScripts/Scripts/GenericScript/GenericScript.yml +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_CommonScripts/Scripts/GenericScript/README.md +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_CommonScripts/pack_metadata.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_EDR/.pack-ignore +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_EDR/.secrets-ignore +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_EDR/Author_image.png +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_EDR/Playbooks/EDR_InitialTriage.yml +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_EDR/README.md +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_EDR/Scripts/EDR_FetchFile/EDR_FetchFile.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_EDR/Scripts/EDR_FetchFile/EDR_FetchFile.yml +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_EDR/Scripts/EDR_FetchFile/README.md +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_EDR/Scripts/EDR_Triage/EDR_Triage.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_EDR/Scripts/EDR_Triage/EDR_Triage.yml +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_EDR/Scripts/EDR_Triage/README.md +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_EDR/Scripts/LegacyItem/LegacyItem.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_EDR/Scripts/LegacyItem/LegacyItem.yml +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_EDR/Scripts/LegacyItem/README.md +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_EDR/Scripts/LegacyItem/test_data/basescript-dummy.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_EDR/pack_metadata.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_Layouts/.pack-ignore +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_Layouts/.secrets-ignore +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_Layouts/Author_image.png +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_Layouts/Layouts/layoutscontainer-GenericLayout.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_Layouts/README.md +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/MyOrg_Layouts/pack_metadata.json +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/mock_content/Packs/Not_applicable/Playbooks/Empty.yml +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/__init__.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/conftest.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/test_artifact_azure.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/test_artifact_base.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/test_artifact_s3.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/test_cases.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/test_client.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/test_config_file.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/test_content_domain.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/test_content_filters.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/test_content_handlers.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/test_error_handling.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/test_integrations.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/test_main.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/test_manifest_utils.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/test_packs.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/test_rbac.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/tests/unit/test_version_check.py +0 -0
- {xsoar_cli-2.1.1 → xsoar_cli-2.2.0}/uv.lock +0 -0
|
@@ -6,6 +6,31 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/).
|
|
|
6
6
|
|
|
7
7
|
## [Unreleased]
|
|
8
8
|
|
|
9
|
+
### Added
|
|
10
|
+
|
|
11
|
+
- `config set-version-check` command to enable or disable the version update check on CLI startup. Accepts `--enable` or `--disable`.
|
|
12
|
+
- `plugins init` command to create the plugins directory and generate an example plugin.
|
|
13
|
+
|
|
14
|
+
### Changed
|
|
15
|
+
|
|
16
|
+
- **Breaking:** Plugins must explicitly import `XSOARPlugin` (`from xsoar_cli.plugins import XSOARPlugin`). The base class is no longer injected automatically and so old plugins require modification. See the [plugin README](src/xsoar_cli/plugins/README.md) for details.
|
|
17
|
+
- Plugin commands (`list`, `info`, `validate`) now report a clear error when the plugins directory has not been initialized.
|
|
18
|
+
- Plugin registration failures no longer prevent remaining plugins from loading.
|
|
19
|
+
- `content get-detached --type` is now required. The `all` choice has been removed; specify `scripts` or `playbooks` explicitly.
|
|
20
|
+
- `integration dump`, `rbac getroles`, `rbac getusers`, and `rbac getusergroups` no longer emit a trailing blank line after JSON output.
|
|
21
|
+
- `config show` now uses `click.echo()` instead of `print()`, improving behavior when piping output to other tools.
|
|
22
|
+
|
|
23
|
+
### Removed
|
|
24
|
+
|
|
25
|
+
- The plugins directory is no longer automatically created on CLI startup. Run `xsoar-cli plugins init` to create it explicitly.
|
|
26
|
+
|
|
27
|
+
### Fixed
|
|
28
|
+
|
|
29
|
+
- `content get-detached` no longer fails when invoked without `--type` due to a stale default value that referenced the removed `all` choice.
|
|
30
|
+
- Content bundle download (`get_content_bundle`) now raises on HTTP errors instead of silently proceeding and failing with a confusing `tarfile` error.
|
|
31
|
+
|
|
32
|
+
## [2.1.1] - 2026-04-08
|
|
33
|
+
|
|
9
34
|
### Changed
|
|
10
35
|
|
|
11
36
|
- `manifest generate` now uses an `--output-dir` option (default: current directory) instead of a positional path argument. The output file is always named `xsoar_config.json`. Prompts for confirmation if the file already exists.
|
|
@@ -83,4 +108,4 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/).
|
|
|
83
108
|
|
|
84
109
|
### Removed
|
|
85
110
|
|
|
86
|
-
- `config validate --stacktrace` option. Use `--verbose` / `-v` instead.
|
|
111
|
+
- `config validate --stacktrace` option. Use `--verbose` / `-v` instead.
|
|
@@ -64,6 +64,7 @@ src/xsoar_cli/ # Main package (src layout)
|
|
|
64
64
|
azure.py # AzureArtifactProvider (Azure Blob Storage)
|
|
65
65
|
commands/ # CLI command groups
|
|
66
66
|
case/ # Case operations command group
|
|
67
|
+
completions/ # Shell autocompletion command group
|
|
67
68
|
config/ # Config management command group
|
|
68
69
|
content/ # Content download/list command group
|
|
69
70
|
graph/ # Dependency graph command group
|
|
@@ -124,9 +125,6 @@ Always use `--no-pager` when running git commands (e.g. `git --no-pager log`, `g
|
|
|
124
125
|
```sh
|
|
125
126
|
# Install dependencies
|
|
126
127
|
uv sync
|
|
127
|
-
uv pip install -r requirements.txt
|
|
128
|
-
uv pip install -r requirements_dev.txt
|
|
129
|
-
uv pip install -e .
|
|
130
128
|
|
|
131
129
|
# Run all tests
|
|
132
130
|
uv run pytest
|
|
@@ -44,40 +44,16 @@ For other platforms and installation options, see the [uv installation docs](htt
|
|
|
44
44
|
|
|
45
45
|
### 3. Set Up Development Environment
|
|
46
46
|
|
|
47
|
-
**Recommended: uv**
|
|
48
|
-
|
|
49
|
-
You may find that you will need to make modifications in [xsoar-client](https://github.com/tlium/xsoar-client) and/or [xsoar-dependency-graph](https://github.com/tlium/xsoar-dependency-graph) in order
|
|
50
|
-
to fix bugs or add new features to `xsoar-cli`. If you need to work on `xsoar-client` or `xsoar-dependency-graph`, install them in editable mode from your local Git clones:
|
|
51
|
-
|
|
52
|
-
```bash
|
|
53
|
-
uv pip install -e /path/to/your/xsoar-client
|
|
54
|
-
uv pip install -e /path/to/your/xsoar-dependency-graph
|
|
55
|
-
```
|
|
56
|
-
|
|
57
47
|
```bash
|
|
58
48
|
# Install dependencies and xsoar-cli in editable mode
|
|
59
49
|
uv sync
|
|
60
50
|
uv pip install -e .
|
|
61
51
|
```
|
|
62
|
-
**Alternative: pip/venv**
|
|
63
52
|
|
|
64
|
-
|
|
65
|
-
# Create and activate a virtual environment
|
|
66
|
-
python -m venv venv
|
|
67
|
-
source venv/bin/activate
|
|
68
|
-
|
|
69
|
-
# Install development dependencies
|
|
70
|
-
pip install -r requirements_dev.txt
|
|
71
|
-
|
|
72
|
-
# Install xsoar-cli in editable mode
|
|
73
|
-
pip install -e .
|
|
74
|
-
```
|
|
75
|
-
|
|
76
|
-
If you need to work on the supporting libraries, install them in editable mode as well:
|
|
53
|
+
You may need to make modifications in [xsoar-dependency-graph](https://github.com/tlium/xsoar-dependency-graph) to fix bugs or add new features to `xsoar-cli`. If so, install it in editable mode from your local Git clone:
|
|
77
54
|
|
|
78
55
|
```bash
|
|
79
|
-
pip install -e /path/to/your/xsoar-
|
|
80
|
-
pip install -e /path/to/your/xsoar-dependency-graph
|
|
56
|
+
uv pip install -e /path/to/your/xsoar-dependency-graph
|
|
81
57
|
```
|
|
82
58
|
|
|
83
59
|
## Development Workflow
|
|
@@ -115,16 +91,15 @@ pip install -e /path/to/your/xsoar-dependency-graph
|
|
|
115
91
|
|
|
116
92
|
#### Lazy imports
|
|
117
93
|
|
|
118
|
-
Heavy third-party packages like `
|
|
94
|
+
Heavy third-party packages like `xsoar_dependency_graph` and `demisto_client` pull in large dependency trees (boto3, azure-storage-blob, matplotlib, networkx, etc.) that are expensive to load. To keep everyday invocations like `--help` and `--version` fast, these imports are placed inside the functions that need them rather than at the top of the file. Each lazy import is marked with the comment `# Lazy import for performance reasons`.
|
|
119
95
|
|
|
120
|
-
Type hints for the deferred types still appear in function signatures. To
|
|
96
|
+
Type hints for the deferred types still appear in function signatures. To keep them clean, use a `TYPE_CHECKING` block at the top of the module:
|
|
121
97
|
|
|
122
98
|
```python
|
|
123
|
-
from __future__ import annotations
|
|
124
99
|
from typing import TYPE_CHECKING
|
|
125
100
|
|
|
126
101
|
if TYPE_CHECKING:
|
|
127
|
-
from xsoar_client.
|
|
102
|
+
from xsoar_cli.xsoar_client.client import Client
|
|
128
103
|
```
|
|
129
104
|
|
|
130
105
|
See `configuration.py` for a complete example.
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: xsoar-cli
|
|
3
|
-
Version: 2.
|
|
3
|
+
Version: 2.2.0
|
|
4
|
+
Summary: A command-line interface for managing Palo Alto Networks XSOAR (Cortex XSOAR)
|
|
4
5
|
Project-URL: Documentation, https://github.com/tlium/xsoar-cli#readme
|
|
5
6
|
Project-URL: Issues, https://github.com/tlium/xsoar-cli/issues
|
|
6
7
|
Project-URL: Source, https://github.com/tlium/xsoar-cli
|
|
@@ -18,7 +18,7 @@ version_tuple: tuple[int | str, ...]
|
|
|
18
18
|
commit_id: str | None
|
|
19
19
|
__commit_id__: str | None
|
|
20
20
|
|
|
21
|
-
__version__ = version = '2.
|
|
22
|
-
__version_tuple__ = version_tuple = (2,
|
|
21
|
+
__version__ = version = '2.2.0'
|
|
22
|
+
__version_tuple__ = version_tuple = (2, 2, 0)
|
|
23
23
|
|
|
24
24
|
__commit_id__ = commit_id = None
|
|
@@ -5,7 +5,7 @@ build-backend = "hatchling.build"
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "xsoar-cli"
|
|
7
7
|
dynamic = ["version"]
|
|
8
|
-
description = ''
|
|
8
|
+
description = 'A command-line interface for managing Palo Alto Networks XSOAR (Cortex XSOAR)'
|
|
9
9
|
readme = "README.md"
|
|
10
10
|
requires-python = ">=3.10"
|
|
11
11
|
license = "MIT"
|
|
@@ -83,13 +83,29 @@ def _load_plugins() -> tuple[list[str], PluginManager]:
|
|
|
83
83
|
"""Captures core command names, then loads and registers plugins. Returns both."""
|
|
84
84
|
core_commands = list(cli.commands.keys())
|
|
85
85
|
manager = PluginManager()
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
86
|
+
|
|
87
|
+
if not manager.plugins_dir_exists:
|
|
88
|
+
logging.getLogger(__name__).debug("Plugins directory not found, skipping plugin loading")
|
|
89
|
+
return core_commands, manager
|
|
90
|
+
|
|
91
|
+
manager.load_all_plugins(ignore_errors=True)
|
|
92
|
+
|
|
93
|
+
# Report load failures on stderr. These warnings run at module level before
|
|
94
|
+
# logging is configured, so logger.warning would be invisible. Plugin load
|
|
95
|
+
# failures are important enough to surface unconditionally.
|
|
96
|
+
load_failures = set(manager.get_failed_plugins().keys())
|
|
97
|
+
for plugin_name, error in manager.get_failed_plugins().items():
|
|
98
|
+
click.echo(f"Warning: plugin '{plugin_name}' failed to load: {error}", err=True)
|
|
99
|
+
|
|
100
|
+
manager.register_plugin_commands(cli)
|
|
101
|
+
|
|
102
|
+
# Registration failures are recorded in failed_plugins by the manager
|
|
103
|
+
# (skip-and-record pattern). Report only the new ones added during registration.
|
|
104
|
+
for plugin_name, error in manager.get_failed_plugins().items():
|
|
105
|
+
if plugin_name in load_failures:
|
|
106
|
+
continue # Already reported above
|
|
107
|
+
click.echo(f"Warning: plugin '{plugin_name}' failed to register: {error}", err=True)
|
|
108
|
+
|
|
93
109
|
return core_commands, manager
|
|
94
110
|
|
|
95
111
|
|
|
@@ -8,7 +8,10 @@ from requests.exceptions import HTTPError
|
|
|
8
8
|
from xsoar_cli.error_handling.connection import ConnectionErrorHandler
|
|
9
9
|
from xsoar_cli.error_handling.http import HTTPErrorHandler
|
|
10
10
|
from xsoar_cli.utilities.config_file import get_xsoar_config, load_config
|
|
11
|
-
from xsoar_cli.utilities.validators import validate_environments
|
|
11
|
+
from xsoar_cli.utilities.validators import validate_environments, validate_xsoar_connectivity
|
|
12
|
+
|
|
13
|
+
if TYPE_CHECKING:
|
|
14
|
+
from xsoar_cli.xsoar_client.client import Client
|
|
12
15
|
|
|
13
16
|
logger = logging.getLogger(__name__)
|
|
14
17
|
|
|
@@ -22,12 +25,9 @@ def parse_string_to_dict(input_string: str | None, delimiter: str) -> dict:
|
|
|
22
25
|
return {key.strip(): value.strip() for key, value in valid_pairs}
|
|
23
26
|
|
|
24
27
|
|
|
25
|
-
|
|
26
|
-
from xsoar_cli.xsoar_client.client import Client
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
@click.group(help="Create, retrieve, and clone cases")
|
|
28
|
+
@click.group()
|
|
30
29
|
def case() -> None:
|
|
30
|
+
"""Create, retrieve, and clone cases"""
|
|
31
31
|
pass
|
|
32
32
|
|
|
33
33
|
|
|
@@ -36,6 +36,7 @@ def case() -> None:
|
|
|
36
36
|
@click.option("--environment", default=None, help="Default environment set in config file.")
|
|
37
37
|
@click.pass_context
|
|
38
38
|
@load_config
|
|
39
|
+
@validate_xsoar_connectivity
|
|
39
40
|
def get(ctx: click.Context, casenumber: int, environment: str | None) -> None:
|
|
40
41
|
"""Retrieve and display a single case.
|
|
41
42
|
|
|
@@ -82,7 +83,12 @@ def clone(ctx: click.Context, casenumber: int, source: str, dest: str) -> None:
|
|
|
82
83
|
click.echo(f"Error: cannot find environments {source} and/or {dest} in config")
|
|
83
84
|
ctx.exit(1)
|
|
84
85
|
|
|
85
|
-
# Test connectivity to both environments before proceeding
|
|
86
|
+
# Test connectivity to both environments before proceeding. This is the only function that does
|
|
87
|
+
# explicit connectivity testing and error handling due to the fact that it is the only function
|
|
88
|
+
# that operates on multiple environments. If later a new command or sub-command is added to
|
|
89
|
+
# xsoar-cli that operates on multiple environments, then a new decorator should be created to
|
|
90
|
+
# handle connectivity testing for multiple environments (@validate_xsoar_connectivity only tests
|
|
91
|
+
# a single environment)
|
|
86
92
|
config = get_xsoar_config(ctx)
|
|
87
93
|
for env_name in (source, dest):
|
|
88
94
|
logger.debug("Testing XSOAR connectivity for environment '%s'", env_name)
|
|
@@ -159,6 +165,7 @@ def clone(ctx: click.Context, casenumber: int, source: str, dest: str) -> None:
|
|
|
159
165
|
@click.argument("name", type=str, default="Test case created from xsoar-cli")
|
|
160
166
|
@click.pass_context
|
|
161
167
|
@load_config
|
|
168
|
+
@validate_xsoar_connectivity
|
|
162
169
|
def create( # noqa: PLR0913
|
|
163
170
|
ctx: click.Context,
|
|
164
171
|
environment: str | None,
|
|
@@ -73,8 +73,9 @@ def _resolve_shell(shell_name: str | None) -> str:
|
|
|
73
73
|
return detected
|
|
74
74
|
|
|
75
75
|
|
|
76
|
-
@click.group(
|
|
76
|
+
@click.group()
|
|
77
77
|
def completions() -> None:
|
|
78
|
+
"""Install and manage shell completion for xsoar-cli"""
|
|
78
79
|
pass
|
|
79
80
|
|
|
80
81
|
|
|
@@ -101,3 +101,21 @@ Set the Azure Blob Storage SAS token for an environment in the configuration fil
|
|
|
101
101
|
xsoar-cli config set-azure-token my-sas-token
|
|
102
102
|
xsoar-cli config set-azure-token --environment prod my-sas-token
|
|
103
103
|
```
|
|
104
|
+
|
|
105
|
+
## Set Version Check
|
|
106
|
+
|
|
107
|
+
Enable or disable the version update check on CLI startup. When enabled, the CLI checks PyPI for newer versions and prints a notice to stderr.
|
|
108
|
+
|
|
109
|
+
**Syntax:** `xsoar-cli config set-version-check [OPTIONS]`
|
|
110
|
+
|
|
111
|
+
**Options:**
|
|
112
|
+
- `--enable` - Enable the version update check
|
|
113
|
+
- `--disable` - Disable the version update check
|
|
114
|
+
|
|
115
|
+
One of `--enable` or `--disable` must be provided.
|
|
116
|
+
|
|
117
|
+
**Examples:**
|
|
118
|
+
```
|
|
119
|
+
xsoar-cli config set-version-check --enable
|
|
120
|
+
xsoar-cli config set-version-check --disable
|
|
121
|
+
```
|
|
@@ -5,9 +5,6 @@ from typing import TYPE_CHECKING
|
|
|
5
5
|
|
|
6
6
|
import click
|
|
7
7
|
|
|
8
|
-
if TYPE_CHECKING:
|
|
9
|
-
from xsoar_cli.xsoar_client.client import Client
|
|
10
|
-
|
|
11
8
|
from xsoar_cli.utilities.config_file import (
|
|
12
9
|
get_config_file_contents,
|
|
13
10
|
get_config_file_path,
|
|
@@ -15,6 +12,9 @@ from xsoar_cli.utilities.config_file import (
|
|
|
15
12
|
load_config,
|
|
16
13
|
)
|
|
17
14
|
|
|
15
|
+
if TYPE_CHECKING:
|
|
16
|
+
from xsoar_cli.xsoar_client.client import Client
|
|
17
|
+
|
|
18
18
|
logger = logging.getLogger(__name__)
|
|
19
19
|
|
|
20
20
|
|
|
@@ -47,8 +47,9 @@ def get_config_file_template_contents() -> dict:
|
|
|
47
47
|
}
|
|
48
48
|
|
|
49
49
|
|
|
50
|
-
@click.group(
|
|
50
|
+
@click.group()
|
|
51
51
|
def config() -> None:
|
|
52
|
+
"""Create, validate, and manage CLI configuration"""
|
|
52
53
|
pass
|
|
53
54
|
|
|
54
55
|
|
|
@@ -67,8 +68,7 @@ def show(ctx: click.Context, masked: bool) -> None:
|
|
|
67
68
|
if "azure_storage_access_token" in config["server_config"][key]:
|
|
68
69
|
config["server_config"][key]["azure_storage_access_token"] = "*****" # noqa: S105
|
|
69
70
|
|
|
70
|
-
|
|
71
|
-
ctx.exit()
|
|
71
|
+
click.echo(json.dumps(config, indent=4))
|
|
72
72
|
|
|
73
73
|
|
|
74
74
|
@click.command()
|
|
@@ -203,8 +203,28 @@ def set_azure_token(ctx: click.Context, environment: str, sastoken: str) -> None
|
|
|
203
203
|
logger.info("Azure SAS token updated for environment '%s'", environment)
|
|
204
204
|
|
|
205
205
|
|
|
206
|
+
@click.command()
|
|
207
|
+
@click.option("--enable", "action", flag_value="enable", help="Enable the version update check on CLI startup.")
|
|
208
|
+
@click.option("--disable", "action", flag_value="disable", help="Disable the version update check on CLI startup.")
|
|
209
|
+
@click.pass_context
|
|
210
|
+
@load_config
|
|
211
|
+
def set_version_check(ctx: click.Context, action: str | None) -> None: # noqa: ARG001
|
|
212
|
+
"""Enable or disable the version update check on CLI startup."""
|
|
213
|
+
if action is None:
|
|
214
|
+
raise click.UsageError("Specify either --enable or --disable.")
|
|
215
|
+
config_file = get_config_file_path()
|
|
216
|
+
config_data = json.loads(config_file.read_text())
|
|
217
|
+
# skip_version_check is the inverse: enabling the check means skip=False.
|
|
218
|
+
config_data["skip_version_check"] = action == "disable"
|
|
219
|
+
config_file.write_text(json.dumps(config_data, indent=4))
|
|
220
|
+
state = "enabled" if action == "enable" else "disabled"
|
|
221
|
+
logger.info("Version check %s", state)
|
|
222
|
+
click.echo(f"Version check {state}.")
|
|
223
|
+
|
|
224
|
+
|
|
206
225
|
config.add_command(create)
|
|
207
226
|
config.add_command(validate)
|
|
208
227
|
config.add_command(show)
|
|
209
228
|
config.add_command(set_credentials)
|
|
210
229
|
config.add_command(set_azure_token)
|
|
230
|
+
config.add_command(set_version_check)
|
|
@@ -19,7 +19,8 @@ logger = logging.getLogger(__name__)
|
|
|
19
19
|
|
|
20
20
|
@click.group()
|
|
21
21
|
def content() -> None:
|
|
22
|
-
"""Inspect and manage content items
|
|
22
|
+
"""Inspect and manage content items"""
|
|
23
|
+
pass
|
|
23
24
|
|
|
24
25
|
|
|
25
26
|
@click.command()
|
|
@@ -27,21 +28,20 @@ def content() -> None:
|
|
|
27
28
|
@click.option(
|
|
28
29
|
"--type",
|
|
29
30
|
"content_type",
|
|
30
|
-
type=click.Choice(["scripts", "playbooks"
|
|
31
|
-
|
|
32
|
-
show_default=True,
|
|
31
|
+
type=click.Choice(["scripts", "playbooks"], case_sensitive=False),
|
|
32
|
+
required=True,
|
|
33
33
|
help="Type of content items to retrieve.",
|
|
34
34
|
)
|
|
35
35
|
@click.pass_context
|
|
36
36
|
@load_config
|
|
37
|
-
@validate_xsoar_connectivity
|
|
37
|
+
@validate_xsoar_connectivity
|
|
38
38
|
def get_detached(ctx: click.Context, environment: str | None, content_type: str) -> None:
|
|
39
39
|
"""List detached content items."""
|
|
40
40
|
config = get_xsoar_config(ctx)
|
|
41
41
|
xsoar_client: Client = config.get_client(environment)
|
|
42
42
|
response = xsoar_client.content.get_detached(content_type)
|
|
43
|
-
|
|
44
|
-
click.echo(
|
|
43
|
+
data = json.loads(response)
|
|
44
|
+
click.echo(json.dumps(data, indent=4))
|
|
45
45
|
|
|
46
46
|
|
|
47
47
|
# We name the command in the decorator here to avoid shadowing the builtin list.
|
|
@@ -59,7 +59,7 @@ def get_detached(ctx: click.Context, environment: str | None, content_type: str)
|
|
|
59
59
|
@click.option("--verbose", is_flag=True, default=False, help="Output the full unfiltered response.")
|
|
60
60
|
@click.pass_context
|
|
61
61
|
@load_config
|
|
62
|
-
@validate_xsoar_connectivity
|
|
62
|
+
@validate_xsoar_connectivity
|
|
63
63
|
def list_content(ctx: click.Context, environment: str | None, content_type: str, detail: bool, verbose: bool) -> None:
|
|
64
64
|
"""
|
|
65
65
|
List detached content items. The purpose of this function is to list out available commands,
|
|
@@ -98,7 +98,7 @@ def list_content(ctx: click.Context, environment: str | None, content_type: str,
|
|
|
98
98
|
@click.argument("name", type=str)
|
|
99
99
|
@click.pass_context
|
|
100
100
|
@load_config
|
|
101
|
-
@validate_xsoar_connectivity
|
|
101
|
+
@validate_xsoar_connectivity
|
|
102
102
|
def download(ctx: click.Context, environment: str | None, content_type: str, output_path: str | None, name: str) -> None:
|
|
103
103
|
"""Download a content item by name.
|
|
104
104
|
|
|
@@ -67,8 +67,9 @@ def _build_content_graph(
|
|
|
67
67
|
return cg
|
|
68
68
|
|
|
69
69
|
|
|
70
|
-
@click.group(
|
|
70
|
+
@click.group()
|
|
71
71
|
def graph() -> None:
|
|
72
|
+
"""(BETA) Create dependency graphs from one or more content packs"""
|
|
72
73
|
pass
|
|
73
74
|
|
|
74
75
|
|
|
@@ -76,7 +77,7 @@ def graph() -> None:
|
|
|
76
77
|
@click.command()
|
|
77
78
|
@click.pass_context
|
|
78
79
|
@load_config
|
|
79
|
-
@validate_xsoar_connectivity
|
|
80
|
+
@validate_xsoar_connectivity
|
|
80
81
|
def generate(ctx: click.Context, packs: tuple[Path], repo_path: str, upstream_repo_path: str, environment: str | None) -> None:
|
|
81
82
|
"""BETA
|
|
82
83
|
|
|
@@ -99,7 +100,7 @@ def generate(ctx: click.Context, packs: tuple[Path], repo_path: str, upstream_re
|
|
|
99
100
|
@_common_graph_options
|
|
100
101
|
@click.pass_context
|
|
101
102
|
@load_config
|
|
102
|
-
@validate_xsoar_connectivity
|
|
103
|
+
@validate_xsoar_connectivity
|
|
103
104
|
def export(
|
|
104
105
|
ctx: click.Context,
|
|
105
106
|
packs: tuple[Path],
|
|
@@ -14,25 +14,25 @@ logger = logging.getLogger(__name__)
|
|
|
14
14
|
|
|
15
15
|
|
|
16
16
|
@click.group()
|
|
17
|
-
|
|
18
|
-
def integration(ctx: click.Context) -> None:
|
|
17
|
+
def integration() -> None:
|
|
19
18
|
"""(BETA) Save/load integration configuration for an integration instance."""
|
|
19
|
+
pass
|
|
20
20
|
|
|
21
21
|
|
|
22
22
|
@click.command()
|
|
23
23
|
@click.option("--environment", default=None, help="Default environment set in config file.")
|
|
24
|
-
@click.option("--all", is_flag=True, default=False)
|
|
24
|
+
@click.option("--all", "all_integrations", is_flag=True, default=False, help="Dump all integrations")
|
|
25
25
|
@click.argument("name", type=str, required=False, default=None)
|
|
26
26
|
@click.pass_context
|
|
27
27
|
@load_config
|
|
28
|
-
@validate_xsoar_connectivity
|
|
29
|
-
def dump(ctx: click.Context, environment: str | None, name: str | None,
|
|
28
|
+
@validate_xsoar_connectivity
|
|
29
|
+
def dump(ctx: click.Context, environment: str | None, name: str | None, all_integrations: bool) -> None:
|
|
30
30
|
"""Dump integration instance configuration to stdout as JSON."""
|
|
31
31
|
config = get_xsoar_config(ctx)
|
|
32
32
|
xsoar_client: Client = config.get_client(environment)
|
|
33
33
|
logger.debug("Dumping integration config (environment: '%s')", environment or config.default_environment)
|
|
34
34
|
integrations = xsoar_client.integrations.get_instances()
|
|
35
|
-
if
|
|
35
|
+
if all_integrations:
|
|
36
36
|
logger.debug("Fetching config for all integrations (environment: '%s')", environment or config.default_environment)
|
|
37
37
|
integration_data = integrations
|
|
38
38
|
else:
|
|
@@ -41,11 +41,11 @@ def dump(ctx: click.Context, environment: str | None, name: str | None, all: boo
|
|
|
41
41
|
if not integration_data:
|
|
42
42
|
click.echo(f"Cannot find integration instance '{name}'")
|
|
43
43
|
ctx.exit(1)
|
|
44
|
-
click.echo(json.dumps(integration_data, sort_keys=True, indent=4)
|
|
44
|
+
click.echo(json.dumps(integration_data, sort_keys=True, indent=4))
|
|
45
45
|
|
|
46
46
|
|
|
47
47
|
@click.command()
|
|
48
|
-
def load(
|
|
48
|
+
def load() -> None:
|
|
49
49
|
"""Load integration instance configuration into XSOAR from a JSON file. Not yet implemented."""
|
|
50
50
|
logger.debug("integration loadconfig command not implemented")
|
|
51
51
|
click.echo("Command not implemented")
|
|
@@ -116,6 +116,7 @@ def _check_pack_availability(
|
|
|
116
116
|
@click.group()
|
|
117
117
|
def manifest() -> None:
|
|
118
118
|
"""Various commands to interact/update/deploy content packs defined in the xsoar_config.json manifest."""
|
|
119
|
+
pass
|
|
119
120
|
|
|
120
121
|
|
|
121
122
|
MANIFEST_FILENAME = "xsoar_config.json"
|
|
@@ -132,7 +133,7 @@ MANIFEST_FILENAME = "xsoar_config.json"
|
|
|
132
133
|
)
|
|
133
134
|
@click.pass_context
|
|
134
135
|
@load_config
|
|
135
|
-
@validate_xsoar_connectivity
|
|
136
|
+
@validate_xsoar_connectivity
|
|
136
137
|
def generate(ctx: click.Context, environment: str | None, output_dir: str) -> None:
|
|
137
138
|
"""Generate a new xsoar_config.json manifest from installed content packs.
|
|
138
139
|
|
|
@@ -168,7 +169,7 @@ def generate(ctx: click.Context, environment: str | None, output_dir: str) -> No
|
|
|
168
169
|
@click.pass_context
|
|
169
170
|
@load_config
|
|
170
171
|
@validate_artifacts_provider
|
|
171
|
-
@validate_xsoar_connectivity
|
|
172
|
+
@validate_xsoar_connectivity
|
|
172
173
|
def update(ctx: click.Context, environment: str | None, manifest: str) -> None:
|
|
173
174
|
"""Update manifest on disk with latest available content pack versions."""
|
|
174
175
|
# Lazy import for performance reasons
|
|
@@ -256,7 +257,7 @@ def update(ctx: click.Context, environment: str | None, manifest: str) -> None:
|
|
|
256
257
|
@click.pass_context
|
|
257
258
|
@load_config
|
|
258
259
|
@validate_artifacts_provider
|
|
259
|
-
@validate_xsoar_connectivity
|
|
260
|
+
@validate_xsoar_connectivity
|
|
260
261
|
def validate(ctx: click.Context, environment: str | None, mode: str, manifest: str) -> None:
|
|
261
262
|
"""Validate manifest JSON and content pack availability.
|
|
262
263
|
|
|
@@ -320,7 +321,7 @@ def validate(ctx: click.Context, environment: str | None, mode: str, manifest: s
|
|
|
320
321
|
@click.argument("manifest", type=click.Path(exists=True))
|
|
321
322
|
@click.pass_context
|
|
322
323
|
@load_config
|
|
323
|
-
@validate_xsoar_connectivity
|
|
324
|
+
@validate_xsoar_connectivity
|
|
324
325
|
def diff(ctx: click.Context, manifest: str, environment: str | None) -> None:
|
|
325
326
|
"""Prints out the differences (if any) between what is defined in the xsoar_config.json manifest and what is actually
|
|
326
327
|
installed on the XSOAR server."""
|
|
@@ -379,7 +380,7 @@ def diff(ctx: click.Context, manifest: str, environment: str | None) -> None:
|
|
|
379
380
|
@click.pass_context
|
|
380
381
|
@load_config
|
|
381
382
|
@validate_artifacts_provider
|
|
382
|
-
@validate_xsoar_connectivity
|
|
383
|
+
@validate_xsoar_connectivity
|
|
383
384
|
def deploy(ctx: click.Context, environment: str | None, manifest: str, verbose: bool, yes: bool) -> None: # noqa: FBT001
|
|
384
385
|
"""Deploy content packs to the server as defined in the xsoar_config.json manifest.
|
|
385
386
|
|
|
@@ -13,9 +13,9 @@ logger = logging.getLogger(__name__)
|
|
|
13
13
|
|
|
14
14
|
|
|
15
15
|
@click.group()
|
|
16
|
-
|
|
17
|
-
def pack(ctx: click.Context) -> None:
|
|
16
|
+
def pack() -> None:
|
|
18
17
|
"""Various content pack related commands."""
|
|
18
|
+
pass
|
|
19
19
|
|
|
20
20
|
|
|
21
21
|
@click.command()
|
|
@@ -23,7 +23,7 @@ def pack(ctx: click.Context) -> None:
|
|
|
23
23
|
@click.argument("pack_id", type=str)
|
|
24
24
|
@click.pass_context
|
|
25
25
|
@load_config
|
|
26
|
-
@validate_xsoar_connectivity
|
|
26
|
+
@validate_xsoar_connectivity
|
|
27
27
|
def delete(ctx: click.Context, environment: str | None, pack_id: str) -> None:
|
|
28
28
|
"""Delete a content pack from the server."""
|
|
29
29
|
config = get_xsoar_config(ctx)
|
|
@@ -45,7 +45,7 @@ def delete(ctx: click.Context, environment: str | None, pack_id: str) -> None:
|
|
|
45
45
|
@click.pass_context
|
|
46
46
|
@load_config
|
|
47
47
|
@validate_artifacts_provider
|
|
48
|
-
@validate_xsoar_connectivity
|
|
48
|
+
@validate_xsoar_connectivity
|
|
49
49
|
def get_outdated(ctx: click.Context, environment: str | None) -> None:
|
|
50
50
|
"""Print a list of outdated content packs."""
|
|
51
51
|
config = get_xsoar_config(ctx)
|
|
@@ -2,6 +2,19 @@
|
|
|
2
2
|
|
|
3
3
|
Manage plugins loaded into the CLI.
|
|
4
4
|
|
|
5
|
+
## Init
|
|
6
|
+
|
|
7
|
+
Initialize the plugins directory and generate an example plugin.
|
|
8
|
+
|
|
9
|
+
**Syntax:** `xsoar-cli plugins init`
|
|
10
|
+
|
|
11
|
+
Creates `~/.local/xsoar-cli/plugins/` (if it does not exist) and writes an example `hello.py` plugin. If the example file already exists, prompts for confirmation before overwriting.
|
|
12
|
+
|
|
13
|
+
**Examples:**
|
|
14
|
+
```
|
|
15
|
+
xsoar-cli plugins init
|
|
16
|
+
```
|
|
17
|
+
|
|
5
18
|
## List
|
|
6
19
|
|
|
7
20
|
List all available and loaded plugins.
|
|
@@ -41,5 +54,3 @@ Validate all plugins in the plugins directory. Checks that each plugin can load
|
|
|
41
54
|
```
|
|
42
55
|
xsoar-cli plugins validate
|
|
43
56
|
```
|
|
44
|
-
|
|
45
|
-
|