Skip to content

Conversation

@nikhilsinhaparseable
Copy link
Contributor

@nikhilsinhaparseable nikhilsinhaparseable commented Oct 27, 2025

add structs for daily mttr history
add helper functions in object store to save mttr history

Summary by CodeRabbit

  • New Features
    • Introduced Mean Time To Resolution (MTTR) tracking for alerts with persistent history storage.
    • Added date-range filtering for querying historical MTTR data.

add structs for daily mttr history
add helper functions in object store to save mttr history
@coderabbitai
Copy link
Contributor

coderabbitai bot commented Oct 27, 2025

Walkthrough

This PR introduces MTTR (Mean Time To Resolution) data structures and persistent storage capabilities. It adds three new data structures for MTTR tracking, extends the Metastore trait with MTTR history accessor methods, implements those methods in ObjectStoreMetastore, and adds a new storage path utility for MTTR JSON files.

Changes

Cohort / File(s) Summary
MTTR data structures
src/alerts/alert_structs.rs
Introduces DailyMTTRStats, MTTRHistory, and MTTRQueryParams structs with serde serialization. Implements MetastoreObject trait for MTTRHistory to enable persistent storage with object_id "mttr" and path resolution via mttr_json_path().
Metastore trait extension
src/metastore/metastore_traits.rs
Adds async methods get_mttr_history() and put_mttr_history() to the Metastore trait. Updates imports to include MTTRHistory from alerts::alert_structs.
ObjectStoreMetastore implementation
src/metastore/metastores/object_store_metastore.rs
Implements get_mttr_history() to deserialize from mttr.json in ALERTS_ROOT_DIRECTORY and put_mttr_history() to persist MTTR history using existing object storage utilities.
Storage path utilities
src/storage/object_storage.rs
Updates alert state JSON path format by removing "parseable" prefix. Adds mttr_json_path() function to return the MTTR JSON file path under alerts root directory.

Sequence Diagram(s)

sequenceDiagram
    participant Client
    participant Metastore
    participant ObjectStore
    participant Storage as Object Storage

    Client->>Metastore: get_mttr_history()
    activate Metastore
    Metastore->>ObjectStore: Read mttr.json from ALERTS_ROOT_DIRECTORY
    ObjectStore->>Storage: Fetch file at mttr_json_path()
    Storage-->>ObjectStore: Return JSON content (or not found)
    ObjectStore-->>Metastore: Deserialize to MTTRHistory or None
    Metastore-->>Client: Result<Option<MTTRHistory>>
    deactivate Metastore

    Client->>Metastore: put_mttr_history(history)
    activate Metastore
    Metastore->>ObjectStore: Write MTTRHistory object
    ObjectStore->>Storage: Write to history.get_object_path()
    Storage-->>ObjectStore: Success
    ObjectStore-->>Metastore: Result<()>
    Metastore-->>Client: Result<()>
    deactivate Metastore
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

  • Alert state path format change: Verify the removal of "parseable" prefix from alert state JSON paths doesn't break existing alert state lookups or create migration issues
  • MetastoreObject trait implementation: Confirm get_object_path() correctly uses mttr_json_path() and that the "mttr" object_id is consistent across the codebase
  • Error handling in get_mttr_history: Review how deserialization failures are handled (returns Ok(None) vs. propagating errors)
  • Storage path consistency: Ensure mttr_json_path() is used consistently across ALERTS_ROOT_DIRECTORY and that relative path construction is correct

Possibly related PRs

  • PR #1443: Extends alerts types and adds MTTR history storage that directly uses AggregatedMTTRStats and MTTR-related types introduced in this PR.
  • PR #1424: Modifies Metastore abstraction and ObjectStoreMetastore implementations that this PR extends with MTTR-specific storage methods.

Poem

🐰 The rabbit hops through storage vaults so bright,
MTTR metrics gleaming in the light!
With daily stats and history stored with care,
Now mean resolution times float through the air!

Pre-merge checks and finishing touches

❌ Failed checks (1 warning)
Check name Status Explanation Resolution
Description Check ⚠️ Warning The provided description is largely incomplete and does not follow the required template structure. The author has provided only two brief bullet points ("add structs for daily mttr history" and "add helper functions in object store to save mttr history") without the detailed Description section that should include the goal, possible solutions with rationale, and key changes. Additionally, the required checklist items regarding testing, code comments, and documentation are entirely absent. While the bullet points are not vague, the description fails to meet the template requirements and lacks the depth and structure expected for a complete PR description.
✅ Passed checks (2 passed)
Check name Status Explanation
Title Check ✅ Passed The PR title "store mttr history for given date" is directly related to the core objective of this changeset, which is to add data structures for daily MTTR history and implement helper functions in the object store to persist this data. The title specifically captures the primary intent—storing MTTR history—and is sufficiently specific to distinguish this change from others. While the phrase "for given date" could be slightly clearer (it refers to the date-based organization of MTTR statistics), it accurately reflects the DailyMTTRStats structure being introduced and is not vague enough to warrant an inconclusive rating.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.
✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 2f2b324 and 06690ed.

📒 Files selected for processing (4)
  • src/alerts/alert_structs.rs (4 hunks)
  • src/metastore/metastore_traits.rs (2 hunks)
  • src/metastore/metastores/object_store_metastore.rs (3 hunks)
  • src/storage/object_storage.rs (2 hunks)
🧰 Additional context used
🧬 Code graph analysis (3)
src/metastore/metastore_traits.rs (1)
src/metastore/metastores/object_store_metastore.rs (2)
  • get_mttr_history (310-323)
  • put_mttr_history (326-329)
src/alerts/alert_structs.rs (2)
src/storage/object_storage.rs (3)
  • alert_json_path (1140-1142)
  • alert_state_json_path (1157-1162)
  • mttr_json_path (1167-1169)
src/metastore/metastore_traits.rs (2)
  • get_object_id (204-204)
  • get_object_path (203-203)
src/metastore/metastores/object_store_metastore.rs (2)
src/metastore/metastore_traits.rs (2)
  • get_mttr_history (84-84)
  • put_mttr_history (85-85)
src/storage/object_storage.rs (1)
  • to_bytes (1082-1086)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (10)
  • GitHub Check: Quest Smoke and Load Tests for Distributed deployments
  • GitHub Check: Quest Smoke and Load Tests for Standalone deployments
  • GitHub Check: Build Default x86_64-pc-windows-msvc
  • GitHub Check: Build Default x86_64-apple-darwin
  • GitHub Check: Build Default x86_64-unknown-linux-gnu
  • GitHub Check: Build Default aarch64-apple-darwin
  • GitHub Check: Build Default aarch64-unknown-linux-gnu
  • GitHub Check: Build Kafka x86_64-unknown-linux-gnu
  • GitHub Check: Build Kafka aarch64-apple-darwin
  • GitHub Check: coverage
🔇 Additional comments (11)
src/storage/object_storage.rs (2)

1155-1155: Documentation correction looks good.

The comment now accurately reflects the actual path format used in the implementation below.


1164-1169: LGTM!

The new mttr_json_path() function follows the established pattern for path helpers and is correctly integrated with the MTTR history storage implementation.

src/metastore/metastore_traits.rs (2)

30-33: LGTM!

The import correctly adds MTTRHistory alongside existing alert-related types, maintaining consistent structure.


83-85: LGTM!

The new MTTR history methods follow the established patterns in the Metastore trait, with get_mttr_history returning Option<MTTRHistory> for safe handling of missing data and put_mttr_history using the trait object pattern consistent with other put methods.

src/metastore/metastores/object_store_metastore.rs (3)

35-38: LGTM!

The import correctly adds MTTRHistory for use in the new metastore method implementations.


116-116: Minor style improvement.

Consolidating to a single line is consistent with similar methods throughout the file.


325-329: LGTM!

The put_mttr_history implementation correctly follows the established pattern by using obj.get_object_path() to retrieve the storage path.

src/alerts/alert_structs.rs (4)

21-21: LGTM!

NaiveDate import is correctly added for use in the DailyMTTRStats struct.


38-38: LGTM!

The mttr_json_path import is correctly added for use in the MTTRHistory implementation of MetastoreObject.


613-638: LGTM!

The new MTTR data structures are well-designed:

  • DailyMTTRStats appropriately uses NaiveDate for date-only storage
  • MTTRHistory provides a clean container for time-series MTTR data
  • MTTRQueryParams uses Option<String> for flexible date filtering from query parameters
  • All structs follow the established serialization patterns with camelCase

805-813: LGTM!

The MetastoreObject implementation for MTTRHistory correctly uses a constant object ID and leverages the mttr_json_path() helper, following the established pattern.

Comment on lines +309 to +323
/// Get MTTR history from storage
async fn get_mttr_history(&self) -> Result<Option<MTTRHistory>, MetastoreError> {
let path = RelativePathBuf::from_iter([ALERTS_ROOT_DIRECTORY, "mttr.json"]);
match self.storage.get_object(&path).await {
Ok(bytes) => {
if let Ok(history) = serde_json::from_slice::<MTTRHistory>(&bytes) {
Ok(Some(history))
} else {
Ok(None)
}
}
Err(ObjectStorageError::NoSuchKey(_)) => Ok(None),
Err(e) => Err(MetastoreError::ObjectStorageError(e)),
}
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🛠️ Refactor suggestion | 🟠 Major

Use the mttr_json_path() helper for consistency.

Line 311 hardcodes the path construction, while put_mttr_history (Line 327) uses obj.get_object_path() which calls the mttr_json_path() helper. This creates an inconsistency and violates DRY. Consider using the helper directly for better maintainability.

Apply this diff:

-    async fn get_mttr_history(&self) -> Result<Option<MTTRHistory>, MetastoreError> {
-        let path = RelativePathBuf::from_iter([ALERTS_ROOT_DIRECTORY, "mttr.json"]);
+    async fn get_mttr_history(&self) -> Result<Option<MTTRHistory>, MetastoreError> {
+        let path = mttr_json_path();
         match self.storage.get_object(&path).await {

Note: You'll need to import mttr_json_path from crate::storage::object_storage at the top of the file.

Committable suggestion skipped: line range outside the PR's diff.

🤖 Prompt for AI Agents
In src/metastore/metastores/object_store_metastore.rs around lines 309 to 323,
the get_mttr_history function hardcodes the path with
RelativePathBuf::from_iter([ALERTS_ROOT_DIRECTORY, "mttr.json"]) instead of
using the existing mttr_json_path helper; replace the hardcoded path with a call
to mttr_json_path() (or obj.get_object_path()/equivalent helper used elsewhere)
and add an import for mttr_json_path from crate::storage::object_storage at the
top of the file so the same path construction is reused consistently.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant