fix: resolve monitor tools scope issue and handle missing history endpoint gracefully#6
Open
akeyx wants to merge 15 commits into
Open
fix: resolve monitor tools scope issue and handle missing history endpoint gracefully#6akeyx wants to merge 15 commits into
akeyx wants to merge 15 commits into
Conversation
When search_logs is called without a time_zone, the SearchRequest model sets time_zone=None. This None value gets passed into search_params as timeZone=None. The validator then tries to type-check None as a string, which raises an APIParameterError. The fix skips None values during validation so they are treated as "not provided", allowing the default value (UTC) to be applied in the subsequent defaults loop. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The Sumo Logic search jobs API (/api/v1/search/jobs) requires time values as epoch milliseconds, not ISO 8601 strings. Sending ISO format results in: "The 'from' field contains an invalid time." This changes to_sumo_api_format and to_sumo_time_format to output epoch milliseconds, and adds epoch time pattern validation to the API validator so it accepts the format it now produces. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The search results endpoint always fetched /messages, which fails for aggregate queries (count by, sum by, etc.) with "requireRawMessages is false". Aggregate query results are served from /records instead. This changes get_search_results to try /records first, then fall back to /messages. Both endpoints are handled gracefully when empty, so queries that match nothing return an empty result set instead of raising an error. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The tool layer passes filter_type to the API client, but the client method didn't accept it. Add the parameter and filter client-side since the Sumo Logic API doesn't support it as a query param. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The Sumo Logic Collector API does not support filter_type as a query parameter. Remove it from the tool schema, tool method, and API client rather than faking it with client-side filtering. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Two changes to the sumologic-api circuit breaker: 1. resilience.py: reset failure_count to 0 on a success in CLOSED state. Previously failure_count was monotonic in CLOSED state, so any process accumulating ~5 transient errors over its lifetime was guaranteed to trip the breaker eventually — "5 ever" rather than "5 consecutive." That's the wrong semantics for an MCP server doing dozens of small queries per session. 2. api_client.py: narrow expected_exception from bare Exception to the same transient set the retry layer already uses (APIError, RateLimitError, TimeoutError, ConnectionError, OSError, httpx.RequestError). User errors like 4xx-from-bad-query no longer count toward opening the breaker. Updated CircuitBreakerConfig.expected_exception's type annotation to reflect that a tuple is supported (Python's except clause accepts either form at runtime). Validated with three async test cases: - failure_count resets on success in CLOSED state - non-transient exceptions are propagated but don't count - 3 consecutive transient errors still open the breaker (intended behavior preserved) Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
… API
Previously get_monitor_status called non-existent status endpoints. Derive
status from the Monitors Management API instead:
- Single monitor: read /api/v1/monitors/{id} and normalize its status array.
- All monitors: delegate to list_monitors (folder recursion) and build a
status record per monitor, skipping folder entries.
Add helpers _unwrap_monitor_item, _normalize_monitor_status (maps the raw
status array + isDisabled to Normal/Triggered/Disabled/Unknown with a
severity ranking), and _build_monitor_status_record. Timing fields
(lastTriggered/triggerCount24h/last|nextEvaluation) are reported as
unavailable since the API does not expose live evaluation data.
Also:
- Fix LogRecord 'name' attribute collision in get_monitor logging.
- Remove unreachable dead code in the tool-layer get_monitor_status.
- Add 15 unit tests for the status normalization helpers.
- Track tests/test_*.py despite the broad test_*.py ignore rule.
Replace deprecated @validator with @field_validator (and @model_validator(mode="after") for cross-field consistency checks), swap class-based Config for model_config = ConfigDict(...), drop non-functional env= kwargs from Field definitions, and use min_length in place of min_items. Resolves all PydanticDeprecatedSince20 warnings; full test suite passes with -W error::DeprecationWarning.
feat(monitors): implement get_monitor_status from the Monitors Management API
fix: migrate Pydantic v1 syntax to v2 to silence deprecation warnings
- Implement execute_raw_request on SumoLogicAPIClient to support raw requests using configured authentication, resilience, and rate-limiting - Add api_call MCP tool to APITools and register it in server.py - Add api subcommand to main.py supporting optional -X/--method switch (defaulting to GET), params, headers, and request body - Write unit tests in test_api_tools.py - Document tool and CLI subcommand in README.md
feat: add generic api command and api_call MCP tool
…point gracefully - Add nonlocal search_fields declaration inside _search_monitors_impl to prevent UnboundLocalError - Handle 404 in get_monitor_history gracefully by returning empty data and warning metadata since public Sumo Logic REST APIs do not support it - Make endpoint validation in config.py lenient by stripping trailing /api, /api/v1, /api/v2 paths and trailing slashes - Accept list response formats for search alerts fallback without triggering warning - Add unit tests in test_config.py
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
This PR addresses critical bugs in the monitor tools when running against a live Sumo Logic environment.
Changes
search_monitors: Fixed a scoping bug by addingnonlocal search_fieldsinside the nested_search_monitors_implfunction.get_monitor_history: Since Sumo Logic public REST APIs do not support a/historyendpoint for monitors, calling it returned a 404. We now intercept the 404 inget_monitor_historyand return an empty list with a warning metadata message rather than crashing with an API error.config.pyto automatically strip trailing/api,/api/v1,/api/v2paths and slashes from the endpoint URL. This prevents validation crashes if credentials setSUMO_ENDPOINT=https://api.sumologic.com/api(which is common across Sumo Logic CLI and Terraform configs).tests/test_config.py.