Skip to content

feat(subgraph/web): time travel query refactor #1939

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 5 commits into from
Apr 11, 2025

Conversation

kemuru
Copy link
Contributor

@kemuru kemuru commented Apr 3, 2025

needs subgraph redeployment (or deploy preview will fail)
luckily I had time to compare the data before they deprecate the time travel query (which they will in a couple of hours). everything matches. tested on my personal subgraph.

Screen.Recording.2025-04-03.at.20.32.03.mov

PR-Codex overview

This PR focuses on updating the subgraph to handle new metrics for CourtCounter, enhancing the data model and queries related to court statistics in the Kleros system.

Detailed summary

  • Updated version in subgraph/package.json to 0.15.0.
  • Added CourtCounter entity in subgraph/core/schema.graphql.
  • Introduced updateCourtCumulativeMetric and updateCourtStateVariable functions in subgraph/core/src/datapoint.ts.
  • Enhanced updateJurorStake and handleDisputeCreation functions to utilize new metrics.
  • Modified useHomePageExtraStats to use timestamps instead of block numbers.
  • Updated GraphQL queries in web/src/hooks/queries/useHomePageBlockQuery.ts to fetch data based on timestamps.
  • Adjusted data processing logic to incorporate cumulative metrics for courts.

✨ Ask PR-Codex anything about this PR by commenting with /codex {your question}

Summary by CodeRabbit

  • New Features

    • Introduced a new entity CourtCounter for enhanced tracking of court metrics, including disputes, votes, and effective stake.
    • Upgraded homepage data retrieval to utilize timestamp-based queries, improving efficiency and accuracy of historical statistics.
    • Enhanced cumulative metric tracking for courts related to disputes and votes.
  • Chores

    • Updated the platform version from 0.14.2 to 0.15.0.

@kemuru kemuru requested a review from a team as a code owner April 3, 2025 18:36
Copy link
Contributor

coderabbitai bot commented Apr 3, 2025

Walkthrough

This pull request introduces a new CourtCounter entity in the GraphQL schema to track cumulative metrics such as disputes, votes, effective stake, and timestamps. It adds functions in the datapoint module for updating these metrics and state variables, with calls integrated in dispute creation, appeal decision, and juror stake update flows. Additionally, the web hooks have been modified to query data based on a timestamp rather than a block number, simplifying past data retrieval.

Changes

File(s) Change Summary
subgraph/core/schema.graphql Added the CourtCounter entity with fields: id, court, numberDisputes, numberVotes, effectiveStake, timestamp.
subgraph/core/src/KlerosCore.ts Inserted calls to updateCourtCumulativeMetric in handleDisputeCreation and handleAppealDecision after updating dispute and vote counts.
subgraph/core/src/datapoint.ts Introduced two new functions: updateCourtCumulativeMetric and updateCourtStateVariable for managing court metrics and daily snapshots.
subgraph/core/src/entities/JurorTokensPerCourt.ts Imported and invoked updateCourtStateVariable in updateJurorStake to update the court’s effective stake.
web/src/hooks/queries/useHomePageBlockQuery.ts Modified the query to accept a pastTimestamp (bigint) instead of a block number, reworking data mapping and lookup with a Map.
web/src/hooks/queries/useHomePageExtraStats.ts Updated calculation logic by replacing block number computations with timestamp-based calculations.
subgraph/package.json Updated version from 0.14.2 to 0.15.0.

Sequence Diagram(s)

sequenceDiagram
    participant D as Dispute Creation Handler
    participant C as CourtCounter Entity
    participant U as updateCourtCumulativeMetric
    participant A as Appeal Decision Handler
    participant J as Juror Stake Updater
    participant S as updateCourtStateVariable

    D->>C: Increment numberDisputes
    D->>U: Update "numberDisputes" metric with delta & timestamp
    A->>C: Update numberVotes
    A->>U: Update "numberVotes" metric with delta & timestamp
    J->>S: Update effectiveStake state with new value & timestamp
Loading
sequenceDiagram
    participant UI as Web UI
    participant Hook as useHomePageBlockQuery
    participant Server as GraphQL Server

    UI->>Hook: Request past court data with pastTimestamp
    Hook->>Server: Execute query using pastTimestamp (via courtCounters)
    Server-->>Hook: Return updated data
Loading

Possibly related PRs

  • feat(web): extra statistic on homepage #1671: The changes in the main PR, which introduce a new CourtCounter entity in the GraphQL schema, are related to the retrieved PR as both involve modifications to the handling of court metrics, specifically the effectiveStake and numberVotes, which are directly referenced in the new functions and components introduced in the retrieved PR.

Suggested labels

Type: Feature🗿, Package: Web

Suggested reviewers

  • alcercu
  • Harman-singh-waraich

Poem

I hop in code with joyful cheer,
New counters bloom, both far and near.
Disputes and votes now dance in line,
With every update, metrics shine.
A hoppy song of code I share,
Upgraded paths, a bunny’s flair! 🥕🐰


🪧 Tips

Chat

There are 3 ways to chat with CodeRabbit:

  • Review comments: Directly reply to a review comment made by CodeRabbit. Example:
    • I pushed a fix in commit <commit_id>, please review it.
    • Generate unit testing code for this file.
    • Open a follow-up GitHub issue for this discussion.
  • Files and specific lines of code (under the "Files changed" tab): Tag @coderabbitai in a new review comment at the desired location with your query. Examples:
    • @coderabbitai generate unit testing code for this file.
    • @coderabbitai modularize this function.
  • PR comments: Tag @coderabbitai in a new PR comment to ask questions about the PR branch. For the best results, please provide a very specific query, as very limited context is provided in this mode. Examples:
    • @coderabbitai gather interesting stats about this repository and render them as a table. Additionally, render a pie chart showing the language distribution in the codebase.
    • @coderabbitai read src/utils.ts and generate unit testing code.
    • @coderabbitai read the files in the src/scheduler package and generate a class diagram using mermaid and a README in the markdown format.
    • @coderabbitai help me debug CodeRabbit configuration file.

Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments.

CodeRabbit Commands (Invoked using PR comments)

  • @coderabbitai pause to pause the reviews on a PR.
  • @coderabbitai resume to resume the paused reviews.
  • @coderabbitai review to trigger an incremental review. This is useful when automatic reviews are disabled for the repository.
  • @coderabbitai full review to do a full review from scratch and review all the files again.
  • @coderabbitai summary to regenerate the summary of the PR.
  • @coderabbitai resolve resolve all the CodeRabbit review comments.
  • @coderabbitai plan to trigger planning for file edits and PR creation.
  • @coderabbitai configuration to show the current CodeRabbit configuration for the repository.
  • @coderabbitai help to get help.

Other keywords and placeholders

  • Add @coderabbitai ignore anywhere in the PR description to prevent this PR from being reviewed.
  • Add @coderabbitai summary to generate the high-level summary at a specific location in the PR description.
  • Add @coderabbitai or @coderabbitai title anywhere in the PR title to generate the title automatically.

CodeRabbit Configuration File (.coderabbit.yaml)

  • You can programmatically configure CodeRabbit by adding a .coderabbit.yaml file to the root of your repository.
  • Please see the configuration documentation for more information.
  • If your editor has YAML language server enabled, you can add the path at the top of this file to enable auto-completion and validation: # yaml-language-server: $schema=https://coderabbit.ai/integrations/schema.v2.json

Documentation and Community

  • Visit our Documentation for detailed information on how to use CodeRabbit.
  • Join our Discord Community to get help, request features, and share feedback.
  • Follow us on X/Twitter for updates and announcements.

Copy link

netlify bot commented Apr 3, 2025

Deploy Preview for kleros-v2-testnet ready!

Name Link
🔨 Latest commit 0e47701
🔍 Latest deploy log https://app.netlify.com/sites/kleros-v2-testnet/deploys/67f94a9c969b280008d4089d
😎 Deploy Preview https://deploy-preview-1939--kleros-v2-testnet.netlify.app
📱 Preview on mobile
Toggle QR Code...

QR Code

Use your smartphone camera to open QR code link.

To edit notification comments on pull requests, go to your Netlify site configuration.

Copy link

netlify bot commented Apr 3, 2025

Deploy Preview for kleros-v2-neo failed. Why did it fail? →

Name Link
🔨 Latest commit 0e47701
🔍 Latest deploy log https://app.netlify.com/sites/kleros-v2-neo/deploys/67f94a9cfaef1c000838e408

Copy link

netlify bot commented Apr 3, 2025

Deploy Preview for kleros-v2-university failed. Why did it fail? →

Name Link
🔨 Latest commit 0e47701
🔍 Latest deploy log https://app.netlify.com/sites/kleros-v2-university/deploys/67f94a9c2bd81f00081e29c9

Copy link

netlify bot commented Apr 3, 2025

Deploy Preview for kleros-v2-testnet-devtools ready!

Name Link
🔨 Latest commit 0e47701
🔍 Latest deploy log https://app.netlify.com/sites/kleros-v2-testnet-devtools/deploys/67f94a9ce2b1f20008a53ccd
😎 Deploy Preview https://deploy-preview-1939--kleros-v2-testnet-devtools.netlify.app
📱 Preview on mobile
Toggle QR Code...

QR Code

Use your smartphone camera to open QR code link.

To edit notification comments on pull requests, go to your Netlify site configuration.

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

🧹 Nitpick comments (4)
subgraph/core/src/datapoint.ts (1)

95-132: Consider validation for unrecognized metrics.
This new function correctly updates the “numberDisputes” and “numberVotes” fields of the CourtCounter entity, along with creating a daily snapshot. However, if an unexpected metric value is passed, the function silently does nothing. Consider handling unknown metrics explicitly (e.g., logging, throwing, or ignoring with justification) to avoid silent errors.

web/src/hooks/queries/useHomePageBlockQuery.ts (3)

55-60: Guard against empty arrays when calling [0].
Although these utility functions look clean, calling [0] on an empty array will yield undefined. Consider returning early or defaulting to a sentinel object if courts can be empty.


77-77: Rename Set to maintain clarity.
Using a Set<number> to track processed indices is fine. However, naming it processedIndices or similar could improve clarity in this block.


94-100: Reduce repeated function calls to improve performance.
Repeatedly calling processCourt(parentIndex) can be costly since it’s invoked multiple times in the same object literal. Store the return value in a local variable first to avoid repeated recursion.

    const parentCourt = processCourt(parentIndex);
    processedCourts[id] = {
      ...courtWithTree,
      treeNumberDisputes: courtWithTree.treeNumberDisputes + parentCourt.treeNumberDisputes,
      treeNumberVotes: courtWithTree.treeNumberVotes + parentCourt.treeNumberVotes,
      // ...
    };
📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between c76e4af and 0552fff.

📒 Files selected for processing (6)
  • subgraph/core/schema.graphql (1 hunks)
  • subgraph/core/src/KlerosCore.ts (3 hunks)
  • subgraph/core/src/datapoint.ts (2 hunks)
  • subgraph/core/src/entities/JurorTokensPerCourt.ts (2 hunks)
  • web/src/hooks/queries/useHomePageBlockQuery.ts (5 hunks)
  • web/src/hooks/queries/useHomePageExtraStats.ts (1 hunks)
🧰 Additional context used
🧠 Learnings (1)
web/src/hooks/queries/useHomePageBlockQuery.ts (1)
Learnt from: Harman-singh-waraich
PR: kleros/kleros-v2#1744
File: web/src/hooks/queries/useHomePageBlockQuery.ts:71-71
Timestamp: 2025-04-03T18:37:26.185Z
Learning: In `web/src/hooks/queries/useHomePageBlockQuery.ts`, the non-null assertions on `blockNumber!` and `genesisBlock!` within `queryFn` are safe because `isEnabled` ensures that `queryFn` only runs when either `blockNumber` or `genesisBlock` is defined.
🧬 Code Definitions (3)
subgraph/core/src/entities/JurorTokensPerCourt.ts (1)
subgraph/core/src/datapoint.ts (1)
  • updateCourtStateVariable (134-168)
subgraph/core/src/KlerosCore.ts (1)
subgraph/core/src/datapoint.ts (1)
  • updateCourtCumulativeMetric (96-132)
web/src/hooks/queries/useHomePageExtraStats.ts (1)
web/src/hooks/queries/useHomePageBlockQuery.ts (1)
  • useHomePageBlockQuery (170-187)
⏰ Context from checks skipped due to timeout of 90000ms (15)
  • GitHub Check: Redirect rules - kleros-v2-neo
  • GitHub Check: Redirect rules - kleros-v2-university
  • GitHub Check: Header rules - kleros-v2-neo
  • GitHub Check: Redirect rules - kleros-v2-testnet
  • GitHub Check: Redirect rules - kleros-v2-testnet
  • GitHub Check: Header rules - kleros-v2-university
  • GitHub Check: Header rules - kleros-v2-testnet
  • GitHub Check: Pages changed - kleros-v2-neo
  • GitHub Check: Header rules - kleros-v2-testnet
  • GitHub Check: Pages changed - kleros-v2-university
  • GitHub Check: Pages changed - kleros-v2-testnet
  • GitHub Check: Pages changed - kleros-v2-testnet
  • GitHub Check: Analyze (javascript)
  • GitHub Check: SonarCloud
  • GitHub Check: contracts-testing
🔇 Additional comments (18)
subgraph/core/schema.graphql (1)

245-252: LGTM! A well-designed entity for court metrics tracking.

The addition of the CourtCounter entity is well-structured with appropriate fields for storing cumulative metrics and timestamps. It will provide valuable time-series data points for court metrics.

subgraph/core/src/entities/JurorTokensPerCourt.ts (2)

3-3: Appropriate import for the new updateCourtStateVariable function.

The import is correctly added to bring in the required function for updating court state variables.


97-97: Good integration of court state tracking.

The addition of updateCourtStateVariable call ensures that whenever a juror's stake is updated, the court's effective stake is properly tracked in the new time-series data structure. This will allow for historical queries of court metrics.

subgraph/core/src/KlerosCore.ts (4)

26-26: Appropriate import for the new update function.

The import is correctly added to bring in the required function for updating court cumulative metrics.


85-85: Good addition for dispute creation tracking.

The call to updateCourtCumulativeMetric ensures that new disputes are properly recorded in the time-series data structure, allowing for historical querying of dispute counts.


89-89: Proper tracking of votes during dispute creation.

This tracking of votes at dispute creation time enhances the system's ability to provide historical court metrics related to voting activities.


231-231: Consistent tracking of votes during appeal decisions.

The addition of vote tracking during appeal decisions ensures that all vote metrics are consistently captured in the time-series data, regardless of when they occur in the dispute lifecycle.

web/src/hooks/queries/useHomePageExtraStats.ts (3)

8-8: Good shift from block-based to timestamp-based tracking.

Changing from pastBlockNumber to pastTimestamp simplifies the data model and improves the accuracy of time-based queries.


11-16: Improved time calculation logic.

The new implementation directly calculates the past timestamp based on the current time, which is more intuitive and eliminates dependencies on block-related calculations.


19-19: Updated query to use timestamp-based filtering.

The modified call to useHomePageBlockQuery properly passes the calculated timestamp instead of a block number, completing the transition to timestamp-based historical queries.

subgraph/core/src/datapoint.ts (1)

2-2: Ensure consistent usage of imported entities.
The addition of CourtCounter alongside Counter is consistent with the changes below, where these entities are referenced. No concerns here.

web/src/hooks/queries/useHomePageBlockQuery.ts (7)

8-8: Timestamp-based query parameter looks good.
Changing the query to accept $pastTimestamp aligns with the new time travel approach. Verify that all references to the old blockNumber parameter in downstream code have been removed or updated.


20-20: Querying courtCounters by timestamp is consistent with the new logic.
The pastCourts field now relies on timestamp_lte: $pastTimestamp. This is appropriate for the new time-travel functionality. Ensure that descending order by timestamp is indeed the intended behavior, especially if multiple snapshots exist on the same day.


32-32: Type alias for CourtCounter is a helpful addition.
Creating a dedicated CourtCounter type reference from GraphQL results is good for clarity, ensuring type safety across the codebase.


66-74: Map builder for past courts works as intended.
Storing only the first encountered court snapshot (descending timestamp) ensures we capture the most recent state when !allTime. This logic seems correct, but be mindful of concurrency if multiple snapshots share the same exact timestamp to avoid overwriting.


83-90: Conditional usage of diff logic is appropriate.
Using addTreeValuesWithDiff only when a matching pastCourt snapshot is found ensures that you account for partial historical data. This aligns well with the newly introduced CourtCounter logic.


141-168: Be mindful of integer truncation with BigInt averaging.
Using (presentCourtWithTree.effectiveStake + pastEffectiveStake) / 2n truncates decimals if the sum is odd. This is likely acceptable, but confirm this is intentional. If you want a more precise average, you might need floating arithmetic.


170-187: New time-based hook logic looks solid.
The updated useHomePageBlockQuery hook thoroughly replaces block-number logic with timestamp logic. It is conditionally enabled only if a valid pastTimestamp is provided or allTime is true. Confirm that providing pastTimestamp = 0 does not cause unexpected queries for negative or null time ranges.

coderabbitai[bot]
coderabbitai bot previously approved these changes Apr 3, 2025
coderabbitai[bot]
coderabbitai bot previously approved these changes Apr 4, 2025
alcercu
alcercu previously approved these changes Apr 4, 2025
Copy link
Contributor

@alcercu alcercu left a comment

Choose a reason for hiding this comment

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

lgtm

@kemuru kemuru dismissed stale reviews from alcercu and coderabbitai[bot] via 64c208d April 11, 2025 10:42
coderabbitai[bot]
coderabbitai bot previously approved these changes Apr 11, 2025
coderabbitai[bot]
coderabbitai bot previously approved these changes Apr 11, 2025
@kemuru kemuru requested a review from alcercu April 11, 2025 11:07
Copy link

codeclimate bot commented Apr 11, 2025

Code Climate has analyzed commit 0e47701 and detected 14 issues on this pull request.

Here's the issue category breakdown:

Category Count
Complexity 6
Duplication 4
Style 4

View more on Code Climate.

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

♻️ Duplicate comments (1)
subgraph/core/src/datapoint.ts (1)

134-168: 🛠️ Refactor suggestion

Expand handling for additional variables and fix inconsistent initialization.

This function only explicitly handles effectiveStake but is structured to potentially handle more variables. There's also an inconsistency in how it initializes new counters.

export function updateCourtStateVariable(courtId: string, newValue: BigInt, timestamp: BigInt, variable: string): void {
+  const validVariables = ["effectiveStake"]; // Add more variables as they are introduced
+  if (!validVariables.includes(variable)) {
+    return; // Early return for invalid variables
+  }
  
  // Load or create the current CourtCounter (ID: courtId-0)
  let currentCounter = CourtCounter.load(courtId + "-0");
  if (!currentCounter) {
    currentCounter = new CourtCounter(courtId + "-0");
    currentCounter.court = courtId;
    currentCounter.numberDisputes = ZERO;
    currentCounter.numberVotes = ZERO;
-    currentCounter.effectiveStake = newValue;
+    currentCounter.effectiveStake = variable === "effectiveStake" ? newValue : ZERO;
    currentCounter.timestamp = ZERO;
+    currentCounter.save(); // Save was missing here
  } else {
    if (variable === "effectiveStake") {
      currentCounter.effectiveStake = newValue;
    }
    currentCounter.save();
  }

  // Update daily snapshot
  let dayID = timestamp.toI32() / 86400;
  let dayStartTimestamp = dayID * 86400;
  let dailyCounter = CourtCounter.load(courtId + "-" + dayStartTimestamp.toString());
  if (!dailyCounter) {
    dailyCounter = new CourtCounter(courtId + "-" + dayStartTimestamp.toString());
    dailyCounter.court = courtId;
    dailyCounter.numberDisputes = currentCounter.numberDisputes;
    dailyCounter.numberVotes = currentCounter.numberVotes;
-    dailyCounter.effectiveStake = newValue;
+    dailyCounter.effectiveStake = variable === "effectiveStake" ? newValue : currentCounter.effectiveStake;
    dailyCounter.timestamp = BigInt.fromI32(dayStartTimestamp);
+    dailyCounter.save(); // Save was missing here
  } else {
    if (variable === "effectiveStake") {
      dailyCounter.effectiveStake = newValue;
    }
    dailyCounter.save();
  }
}

The current code unconditionally sets effectiveStake to newValue when creating a new counter, but for existing counters, it only updates if variable === "effectiveStake". This could lead to unexpected behavior in the future.

🧹 Nitpick comments (1)
subgraph/core/src/datapoint.ts (1)

96-132: Consider refactoring for reusability and flexibility.

This function currently handles only two metrics (numberDisputes and numberVotes). If additional metrics are added in the future, the function will need to be modified. Consider refactoring to make it more flexible:

- export function updateCourtCumulativeMetric(courtId: string, delta: BigInt, timestamp: BigInt, metric: string): void {
+ export function updateCourtCumulativeMetric(courtId: string, delta: BigInt, timestamp: BigInt, metric: string): void {
+   const validMetrics = ["numberDisputes", "numberVotes"];
+   if (!validMetrics.includes(metric)) {
+     return; // Early return for invalid metrics
+   }
  
  // Load or create the current CourtCounter (ID: courtId-0)
  let currentCounter = CourtCounter.load(courtId + "-0");
  if (!currentCounter) {
    currentCounter = new CourtCounter(courtId + "-0");
    currentCounter.court = courtId;
    currentCounter.numberDisputes = ZERO;
    currentCounter.numberVotes = ZERO;
    currentCounter.effectiveStake = ZERO;
    currentCounter.timestamp = ZERO;
  }
-  if (metric === "numberDisputes") {
-    currentCounter.numberDisputes = currentCounter.numberDisputes.plus(delta);
-  } else if (metric === "numberVotes") {
-    currentCounter.numberVotes = currentCounter.numberVotes.plus(delta);
-  }
+  // Use dynamic property access
+  const currentValue = currentCounter.get(metric) as BigInt;
+  currentCounter.set(metric, currentValue.plus(delta));
  currentCounter.save();

  // Update daily snapshot
  let dayID = timestamp.toI32() / 86400; // Seconds to days
  let dayStartTimestamp = dayID * 86400;
  let dailyCounter = CourtCounter.load(courtId + "-" + dayStartTimestamp.toString());
  if (!dailyCounter) {
    dailyCounter = new CourtCounter(courtId + "-" + dayStartTimestamp.toString());
    dailyCounter.court = courtId;
    dailyCounter.numberDisputes = currentCounter.numberDisputes.minus(delta); // State before this update
    dailyCounter.numberVotes = currentCounter.numberVotes.minus(delta);
    dailyCounter.effectiveStake = currentCounter.effectiveStake;
    dailyCounter.timestamp = BigInt.fromI32(dayStartTimestamp);
  }
-  if (metric === "numberDisputes") {
-    dailyCounter.numberDisputes = dailyCounter.numberDisputes.plus(delta);
-  } else if (metric === "numberVotes") {
-    dailyCounter.numberVotes = dailyCounter.numberVotes.plus(delta);
-  }
+  // Use dynamic property access
+  const dailyValue = dailyCounter.get(metric) as BigInt;
+  dailyCounter.set(metric, dailyValue.plus(delta));
  dailyCounter.save();
}

Also, extracting the day timestamp calculation to a helper function would reduce duplication.

📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro (Legacy)

📥 Commits

Reviewing files that changed from the base of the PR and between 8bdf724 and 0e47701.

📒 Files selected for processing (2)
  • subgraph/core/src/datapoint.ts (2 hunks)
  • web/src/hooks/queries/useHomePageBlockQuery.ts (5 hunks)
⏰ Context from checks skipped due to timeout of 90000ms (15)
  • GitHub Check: Redirect rules - kleros-v2-testnet-devtools
  • GitHub Check: Header rules - kleros-v2-testnet-devtools
  • GitHub Check: Pages changed - kleros-v2-testnet-devtools
  • GitHub Check: Redirect rules - kleros-v2-testnet
  • GitHub Check: Redirect rules - kleros-v2-testnet
  • GitHub Check: Header rules - kleros-v2-testnet
  • GitHub Check: Header rules - kleros-v2-testnet
  • GitHub Check: Pages changed - kleros-v2-testnet
  • GitHub Check: Pages changed - kleros-v2-testnet
  • GitHub Check: Redirect rules - kleros-v2-neo
  • GitHub Check: Header rules - kleros-v2-neo
  • GitHub Check: Pages changed - kleros-v2-neo
  • GitHub Check: contracts-testing
  • GitHub Check: SonarCloud
  • GitHub Check: Analyze (javascript)
🔇 Additional comments (10)
web/src/hooks/queries/useHomePageBlockQuery.ts (8)

8-9: GraphQL query updated to use timestamp-based filtering

The query structure has been refactored to use timestamps instead of block numbers for historical data retrieval, with clear separation between present and past data. This approach aligns with The Graph's recommended practice as time-travel queries using block numbers are being deprecated.

Also applies to: 20-33


38-38: New type definition added for court counter data

Good addition of the CourtCounter type to represent the new data structure returned from the courtCounters query, improving type safety.


61-66: Updated sorting helper functions using modern JavaScript

The sorting helper functions now use the newer toSorted() array method which is more concise and avoids mutating the original array.


69-81: Enhanced data processing with Map-based lookups

The implementation now uses Map objects for both present and past courts, which provides more efficient lookups compared to array iterations. The conditional processing for past courts is a good optimization for the non-allTime case.


83-110: Refactored court processing with improved recursive approach

The court processing logic has been enhanced with:

  1. Memoization via the processedCourtsMap
  2. Proper handling of the new data structure
  3. Conditional logic to use either diff or direct values based on availability of past data

This should result in more efficient and accurate court data processing.


150-168: Added fallback mechanisms and error handling for missing data

Good addition of fallback logic and warning messages when snapshot data is missing or shows no activity. This improves reliability and debugging capabilities.


170-174: Improved metric calculation using average effective stake

The implementation now uses the average of past and present effective stake for calculating per-PNK metrics, which provides a more accurate representation over the time period.


192-209: Updated hook signature to use bigint for timestamp

The hook signature has been updated to use bigint for the timestamp parameter, which is appropriate for handling large timestamp values. The implementation also correctly handles the allTime case by using "0" as the pastTimestamp.

subgraph/core/src/datapoint.ts (2)

2-2: Looks good - Import statement updated correctly.

The import statement has been properly updated to include the new CourtCounter entity, which is used in the newly added functions.


121-122: Verify the initial state calculation for daily counters.

When creating a new daily counter, you're setting the initial values by subtracting the current delta from the current counter's values. This assumes the delta has already been applied to the current counter, which seems correct based on the code flow, but worth verifying:

Are you certain that the formula currentCounter.numberDisputes.minus(delta) correctly represents the state before the update? This approach assumes that the delta has already been added to the current counter.

Copy link
Contributor

@alcercu alcercu left a comment

Choose a reason for hiding this comment

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

lgtm

@alcercu alcercu merged commit 74142c1 into dev Apr 11, 2025
13 of 26 checks passed
@kemuru kemuru deleted the fix/time-travel-query-refactor branch April 11, 2025 17:47
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.

2 participants