Skip to content

[Refactor] Replace ScaleHelper and createLabeledScales with RechartsScale and CartesianScaleHelper#6811

Merged
ckifer merged 2 commits into
mainfrom
ts-strict
Dec 22, 2025
Merged

[Refactor] Replace ScaleHelper and createLabeledScales with RechartsScale and CartesianScaleHelper#6811
ckifer merged 2 commits into
mainfrom
ts-strict

Conversation

@PavelVanecek

@PavelVanecek PavelVanecek commented Dec 22, 2025

Copy link
Copy Markdown
Collaborator

Description

Now that we have internal and external scale representations, we can make changes to the internal one.

First I renamed the "apply/implicit call signature" (typescript treats them equally even though they have different arguments - very confusing) to "map" so that we can search for usage and we do not need to worry about passing "this"

That exposed many many @ts-expect-error so I removed and fixed those - this was hiding a tick index/offset problem so I fixed that.

Then I added the "position" argument from ScaleHelper.apply into RechartsScale.map, this is useful

Then I replaced "createLabeledScales" with new "CartesianScaleHelper" and used it in Reference elements

And then removed ScaleHelper and createLabeledScales and replaced all "any" with RechartsScale/CartesianScaleHelper.

Related Issue

#6645

Motivation and Context

Removing any

Summary by CodeRabbit

  • New Features

    • Added position support ('start', 'middle', 'end') for banded scale coordinate mapping
    • Introduced unified scale helper for coordinated x/y axis mapping with fallback support
  • Enhancements

    • Tick items now include index and offset fields for improved positioning accuracy
    • Added range boundary query methods (rangeMin, rangeMax, isInRange) to scale interface

✏️ Tip: You can customize this high-level summary in your review settings.

@coderabbitai

coderabbitai Bot commented Dec 22, 2025

Copy link
Copy Markdown
Contributor

Walkthrough

This PR refactors Recharts' scale abstraction layer, introducing a new CartesianScaleHelper interface with implementation, expanding the RechartsScale API with map(), rangeMin(), rangeMax(), and isInRange() methods, and updating numerous chart components to use the new scale access patterns. It also adds offset field to TickItem type and removes legacy ScaleHelper and createLabeledScales utilities.

Changes

Cohort / File(s) Summary
Scale abstractions and factories
src/util/scale/RechartsScale.ts, src/util/scale/CartesianScaleHelper.ts
Expanded RechartsScale with map(input, options?), rangeMin(), rangeMax(), isInRange(value) methods; added BandPosition type. Introduced d3ScaleToRechartsScale() adapter and renamed makeRechartsScale to rechartsScaleFactory. Created new CartesianScaleHelper interface and CartesianScaleHelperImpl class for coordinating x/y scale mappings with fallback support.
Scale removal
src/util/CartesianUtils.ts
Deleted legacy ScaleHelper class, createLabeledScales function, and dependent type aliases (ScaleResult, Scales, ScalesApply, ScalesIsInRange, LabeledScales). Retained geometry utilities (rectWithPoints, rectWithCoords, normalizeAngle, getAngledRectangleWidth).
Axis state selectors
src/state/selectors/axisSelectors.ts
Replaced makeRechartsScale with rechartsScaleFactory. Updated categorical domain typing from ReadonlyArray<unknown> to ReadonlyArray<CategoricalDomainItem>. Changed scale invocations from scale(entry) to scale.map(entry) across tick generation paths. Updated combineAxisTicks and combineGraphicalItemTicks signatures.
Cartesian chart components (scale.map migration)
src/cartesian/Area.tsx, src/cartesian/Bar.tsx, src/cartesian/Line.tsx, src/cartesian/Scatter.tsx, src/cartesian/ErrorBar.tsx
Replaced direct scale(value) calls with scale.map(value) for coordinate computation in computeArea, stackedBarStart, line points, scatter point sizing, and error bar bounds. No changes to control flow or function signatures.
Reference components with scale helper integration
src/cartesian/ReferenceArea.tsx, src/cartesian/ReferenceDot.tsx
Replaced createLabeledScales with CartesianScaleHelperImpl. Updated coordinate handling to use map() and mapWithFallback() with fallback to rangeMin/rangeMax. Changed return types to NullableCoordinate where applicable.
ReferenceLine scale refactoring
src/cartesian/ReferenceLine.tsx
Replaced createLabeledScales and generic scales object with explicit RechartsScale-based parameters. Updated end-point computations to use map(), isInRange(), and CartesianScaleHelperImpl. Changed ReferenceLineProps.position type from ReferenceLinePosition to BandPosition (breaking change). Removed deprecated ReferenceLinePosition type export. Updated imports for new scale abstractions.
Polar chart components
src/polar/Radar.tsx, src/polar/RadialBar.tsx
Replaced angleAxis.scale(value) and radiusAxis.scale(value) with scale.map(value) variants for angle and radius calculations.
Utility improvements
src/util/ChartUtils.ts, src/util/scale/CustomScaleDefinition.ts, src/util/types.ts
Updated checkDomainOfScale to generic signature with CustomScaleDefinition<T>. Changed scale invocations to scale.map() in ChartUtils. Expanded JSDoc for CustomScaleDefinition.ticks() and TickItem.offset.
Snapshot files
scripts/snapshots/es6Files.txt, scripts/snapshots/libFiles.txt, scripts/snapshots/typesFiles.txt
Added new file entries for CartesianScaleHelper.js (es6), CartesianScaleHelper.js (lib), and CartesianScaleHelper.d.ts (types).
CartesianGrid cleanup
src/cartesian/CartesianGrid.tsx
Removed file header comment block.
Tooltip selectors
src/state/selectors/tooltipSelectors.ts
Updated tick generation paths to use scale.map(entry) instead of scale(entry).
Test files (scale.map migration and mocking)
test/cartesian/Area.spec.tsx, test/cartesian/getTicks.spec.ts, test/cartesian/getEquidistantTicks.spec.ts, test/cartesian/XAxis/XAxis.barSize.spec.tsx, test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx, test/helper/expectScale.ts
Updated test mocks and assertions to use scale.map() API instead of direct function calls. Updated expectScale to validate scale.map function.
Test helper updates
test/helper/mockAxes.ts, test/chart/ScatterChart.spec.tsx
Updated mockScale to use d3ScaleToRechartsScale() wrapper; type changed from CustomScaleDefinition<number> to RechartsScale<number>. Updated selector test expectations to include index field in tick items.
Reference tests with real scales
test/cartesian/ReferenceLine/getEndPoints.spec.tsx
Replaced manual mock scales with concrete d3ScaleToRechartsScale() instances. Expanded test coverage for overflow scenarios. Added imports for BandPosition, d3ScaleToRechartsScale, RechartsScale.
Polar axis tests
test/polar/PolarAngleAxis.spec.tsx, test/polar/PolarGrid.spec.tsx
Updated test expectations to include index field in TickItem objects returned by selectors.
CartesianUtils tests
test/util/CartesianUtils/CartesianUtils.spec.ts
Replaced ScaleHelper and createLabeledScales tests with CartesianScaleHelperImpl-based tests. Added structured tests for map(), mapWithFallback(), and isInRange() with positional variants ('start', 'middle', 'end') and fallback scenarios.
ChartUtils tests
test/util/ChartUtils.spec.tsx, test/util/ChartUtils/checkDomainOfScale.spec.ts, test/util/ChartUtils/getCateCoordinateOfLine.spec.ts
Updated test setup to wrap D3 scales with d3ScaleToRechartsScale(). Added @ts-expect-error comments for type strictness. Updated mock scales to use object-based interface with map().

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~60 minutes

Areas requiring extra attention:

  • src/util/scale/RechartsScale.ts: Review the new map() signature with optional BandPosition, the d3ScaleToRechartsScale() adapter implementation, and the rechartsScaleFactory() rename to ensure backward compatibility and correct delegation to underlying D3 scales.
  • src/state/selectors/axisSelectors.ts: Verify that the categorical domain typing (CategoricalDomainItem) is correctly applied throughout all tick generation paths and that the scale.map() migration preserves original scaling behavior.
  • src/cartesian/ReferenceLine.tsx: Confirm the breaking change to ReferenceLineProps.position type (now BandPosition instead of ReferenceLinePosition) and validate that the new CartesianScaleHelperImpl-based end-point computation is correct across all layout orientations.
  • Scale.map() consistency: Audit all component changes (Area, Bar, Line, Scatter, ErrorBar, Radar, RadialBar) to ensure scale.map() returns are handled identically and that nullish checks remain effective.
  • Test coverage: Verify that new TickItem.offset field is correctly populated across all tick generation and selector paths, and confirm that test migrations from legacy ScaleHelper to CartesianScaleHelperImpl are comprehensive.

Possibly related PRs

  • Split scale definition into two parts #6783: Directly related—modifies scale abstraction (expanding RechartsScale and CustomScaleDefinition APIs; switching callers from direct scale(...) to scale.map(...)) with overlapping changes to core scale handling.
  • Ts strict #6750: Overlapping changes to src/state/selectors/axisSelectors.ts (axis-type unions and related function signatures), creating potential merge conflicts or coordination needs.
  • Allow extending domain if ReferenceLine is defined by segment #6592: Related through src/cartesian/ReferenceLine.tsx modifications (scale/apply logic refactoring vs. segment-type and domain-extension behavior).

Suggested labels

typescript, refactor

Suggested reviewers

  • ckifer

Pre-merge checks and finishing touches

❌ Failed checks (1 warning)
Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 12.50% which is insufficient. The required threshold is 80.00%. You can run @coderabbitai generate docstrings to improve docstring coverage.
✅ Passed checks (2 passed)
Check name Status Explanation
Title check ✅ Passed The pull request title '[Refactor] Replace ScaleHelper and createLabeledScales with RechartsScale and CartesianScaleHelper' directly and specifically describes the main refactoring changes—removing old scale utilities and replacing them with new ones.
Description check ✅ Passed The pull request description covers key aspects of the change: motivation (removing 'any' types), main changes (renaming apply to map, removing @ts-expect-error, adding position argument, replacing createLabeledScales with CartesianScaleHelper), and related issue. It is substantially complete despite not explicitly filling every template section.
✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch ts-strict

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

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

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Actionable comments posted: 0

🧹 Nitpick comments (6)
src/cartesian/ReferenceArea.tsx (1)

74-91: Consider using mapWithFallback for cleaner implementation.

The CartesianScaleHelperImpl provides a mapWithFallback method that handles the fallback logic you're implementing manually. This would eliminate the need for the @ts-expect-error comment.

🔎 Proposed refactor using mapWithFallback
-  const scales = new CartesianScaleHelperImpl({ x: xAxisScale, y: yAxisScale });
-
-  const p1: NullableCoordinate = {
-    x: hasX1 ? (xAxisScale.map(xValue1, { position: 'start' }) ?? null) : xAxisScale.rangeMin(),
-    y: hasY1 ? (yAxisScale.map(yValue1, { position: 'start' }) ?? null) : yAxisScale.rangeMin(),
-  };
-
-  const p2: NullableCoordinate = {
-    x: hasX2 ? (xAxisScale.map(xValue2, { position: 'end' }) ?? null) : xAxisScale.rangeMax(),
-    y: hasY2 ? (yAxisScale.map(yValue2, { position: 'end' }) ?? null) : yAxisScale.rangeMax(),
-  };
+  const scales = new CartesianScaleHelperImpl({ x: xAxisScale, y: yAxisScale });
+
+  const p1 = scales.mapWithFallback(
+    { x: hasX1 ? xValue1 : undefined, y: hasY1 ? yValue1 : undefined },
+    { position: 'start', fallback: 'rangeMin' },
+  );
+
+  const p2 = scales.mapWithFallback(
+    { x: hasX2 ? xValue2 : undefined, y: hasY2 ? yValue2 : undefined },
+    { position: 'end', fallback: 'rangeMax' },
+  );
 
   if (props.ifOverflow === 'discard' && (!scales.isInRange(p1) || !scales.isInRange(p2))) {
     return null;
   }
 
-  // @ts-expect-error we're sending nullable coordinates but rectWithPoints expects non-nullable Coordinate
   return rectWithPoints(p1, p2);

Note: The mapWithFallback method returns Coordinate (non-nullable), which would eliminate the type mismatch with rectWithPoints. However, this changes behavior slightly - values that fail to map would get fallback values instead of null. Verify this aligns with the intended behavior.

src/cartesian/ReferenceDot.tsx (1)

139-140: Unnecessary nullish coalescing operators.

The Coordinate type returned by scales.map() guarantees x and y are numbers (never null/undefined), as CartesianScaleHelperImpl.map() uses ?? 0 internally. The ?? undefined fallback will never be triggered.

🔎 Proposed simplification
   const dotProps: DotProps = {
     clipPath,
     ...svgPropertiesAndEvents(props),
-    cx: cx ?? undefined,
-    cy: cy ?? undefined,
+    cx,
+    cy,
   };
test/cartesian/ReferenceLine/getEndPoints.spec.tsx (1)

118-131: Dead code: unused variables from previous test setup.

The coord, scales, and beforeEach setup are no longer used after the refactor to real scales. These should be removed to avoid confusion.

🔎 Proposed fix
   describe('fixed Y location when in range', () => {
     const position = 'start';
     const lineLocationY = 9;
     const yScale = d3ScaleToRechartsScale<number>(scaleLinear().domain([0, 15]).range([0, 150]));
-    const coord = Symbol('coord');
-    const scales = {
-      y: {
-        apply: vi.fn(),
-        isInRange: vi.fn(),
-      },
-    };
-
-    beforeEach(() => {
-      scales.y.apply.mockReset();
-      scales.y.apply.mockImplementation(() => coord);
-      scales.y.isInRange.mockReset();
-      scales.y.isInRange.mockImplementation(() => true);
-    });

     it('should return coordinates when set to discard overflow', () => {
src/cartesian/ReferenceLine.tsx (1)

236-241: Consider extracting CartesianScaleHelperImpl creation.

The inline instantiation of CartesianScaleHelperImpl works, but could be created earlier in getEndPoints and passed to getSegmentLineEndPoints for consistency with how the individual axis scales are passed to the horizontal/vertical line functions.

This is a minor structural observation - the current approach is functionally correct.

src/util/scale/RechartsScale.ts (1)

87-95: Consider improving type safety for d3 scale lookup.

The two @ts-expect-error comments indicate that the dynamic scale lookup from d3Scales lacks proper type verification. While functional, this could be improved with a type-safe lookup map.

This is a pre-existing pattern in the codebase, so addressing it could be deferred to a future improvement.

src/util/scale/CartesianScaleHelper.ts (1)

41-64: Consider reducing duplication in fallback computation.

The if-else blocks for computing fallbackY (lines 46-52) and fallbackX (lines 53-59) are nearly identical. This could be refactored into a helper function for clarity.

🔎 Proposed refactor
+  private getFallback(scale: RechartsScale<unknown>, fallback: 'rangeMin' | 'rangeMax'): number {
+    if (fallback === 'rangeMin') {
+      return scale.rangeMin();
+    }
+    if (fallback === 'rangeMax') {
+      return scale.rangeMax();
+    }
+    return 0;
+  }
+
   mapWithFallback(
     value: { x?: XDomain | null | undefined; y?: YDomain | null | undefined },
     { position, fallback }: { position?: BandPosition; fallback: 'rangeMin' | 'rangeMax' },
   ): Coordinate {
-    let fallbackY: number, fallbackX: number;
-    if (fallback === 'rangeMin') {
-      fallbackY = this.yAxisScale.rangeMin();
-    } else if (fallback === 'rangeMax') {
-      fallbackY = this.yAxisScale.rangeMax();
-    } else {
-      fallbackY = 0;
-    }
-    if (fallback === 'rangeMin') {
-      fallbackX = this.xAxisScale.rangeMin();
-    } else if (fallback === 'rangeMax') {
-      fallbackX = this.xAxisScale.rangeMax();
-    } else {
-      fallbackX = 0;
-    }
+    const fallbackX = this.getFallback(this.xAxisScale, fallback);
+    const fallbackY = this.getFallback(this.yAxisScale, fallback);
     return {
       x: this.xAxisScale.map(value.x, { position }) ?? fallbackX,
       y: this.yAxisScale.map(value.y, { position }) ?? fallbackY,
     };
   }
📜 Review details

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 499a165 and 06163f4.

📒 Files selected for processing (38)
  • scripts/snapshots/es6Files.txt
  • scripts/snapshots/libFiles.txt
  • scripts/snapshots/typesFiles.txt
  • src/cartesian/Area.tsx
  • src/cartesian/Bar.tsx
  • src/cartesian/CartesianGrid.tsx
  • src/cartesian/ErrorBar.tsx
  • src/cartesian/Line.tsx
  • src/cartesian/ReferenceArea.tsx
  • src/cartesian/ReferenceDot.tsx
  • src/cartesian/ReferenceLine.tsx
  • src/cartesian/Scatter.tsx
  • src/polar/Radar.tsx
  • src/polar/RadialBar.tsx
  • src/state/selectors/axisSelectors.ts
  • src/state/selectors/tooltipSelectors.ts
  • src/util/CartesianUtils.ts
  • src/util/ChartUtils.ts
  • src/util/scale/CartesianScaleHelper.ts
  • src/util/scale/CustomScaleDefinition.ts
  • src/util/scale/RechartsScale.ts
  • src/util/types.ts
  • test/cartesian/Area.spec.tsx
  • test/cartesian/CartesianAxis.spec.tsx
  • test/cartesian/ReferenceLine/getEndPoints.spec.tsx
  • test/cartesian/XAxis/XAxis.barSize.spec.tsx
  • test/cartesian/getEquidistantTicks.spec.ts
  • test/cartesian/getTicks.spec.ts
  • test/chart/ScatterChart.spec.tsx
  • test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx
  • test/helper/expectScale.ts
  • test/helper/mockAxes.ts
  • test/polar/PolarAngleAxis.spec.tsx
  • test/polar/PolarGrid.spec.tsx
  • test/util/CartesianUtils/CartesianUtils.spec.ts
  • test/util/ChartUtils.spec.tsx
  • test/util/ChartUtils/checkDomainOfScale.spec.ts
  • test/util/ChartUtils/getCateCoordinateOfLine.spec.ts
💤 Files with no reviewable changes (2)
  • src/cartesian/CartesianGrid.tsx
  • src/util/CartesianUtils.ts
🧰 Additional context used
📓 Path-based instructions (8)
**/*.{ts,tsx}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.{ts,tsx}: Never use any type (implicit or explicit) in TypeScript code
Prefer unknown over any and refine the type in TypeScript
Type function parameters and return values explicitly in TypeScript, do not rely on implicit any or inference; exceptions are React components and trivial functions
Do not use as type assertions in TypeScript; the only exception is as const

Files:

  • test/helper/expectScale.ts
  • src/cartesian/ErrorBar.tsx
  • src/cartesian/Line.tsx
  • src/util/types.ts
  • test/cartesian/getTicks.spec.ts
  • test/util/ChartUtils.spec.tsx
  • src/util/scale/CartesianScaleHelper.ts
  • src/polar/Radar.tsx
  • test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx
  • test/polar/PolarGrid.spec.tsx
  • src/util/scale/CustomScaleDefinition.ts
  • test/util/ChartUtils/checkDomainOfScale.spec.ts
  • src/state/selectors/tooltipSelectors.ts
  • test/cartesian/Area.spec.tsx
  • src/cartesian/ReferenceLine.tsx
  • test/util/ChartUtils/getCateCoordinateOfLine.spec.ts
  • src/cartesian/Area.tsx
  • test/cartesian/ReferenceLine/getEndPoints.spec.tsx
  • test/chart/ScatterChart.spec.tsx
  • src/util/scale/RechartsScale.ts
  • src/polar/RadialBar.tsx
  • test/polar/PolarAngleAxis.spec.tsx
  • src/cartesian/ReferenceArea.tsx
  • test/cartesian/CartesianAxis.spec.tsx
  • src/cartesian/ReferenceDot.tsx
  • test/cartesian/XAxis/XAxis.barSize.spec.tsx
  • src/cartesian/Scatter.tsx
  • src/state/selectors/axisSelectors.ts
  • test/cartesian/getEquidistantTicks.spec.ts
  • src/cartesian/Bar.tsx
  • test/util/CartesianUtils/CartesianUtils.spec.ts
  • test/helper/mockAxes.ts
  • src/util/ChartUtils.ts
**/*.{js,ts,tsx}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Ensure code lints by running npm run lint and follows Airbnb's Style Guide

Files:

  • test/helper/expectScale.ts
  • src/cartesian/ErrorBar.tsx
  • src/cartesian/Line.tsx
  • src/util/types.ts
  • test/cartesian/getTicks.spec.ts
  • test/util/ChartUtils.spec.tsx
  • src/util/scale/CartesianScaleHelper.ts
  • src/polar/Radar.tsx
  • test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx
  • test/polar/PolarGrid.spec.tsx
  • src/util/scale/CustomScaleDefinition.ts
  • test/util/ChartUtils/checkDomainOfScale.spec.ts
  • src/state/selectors/tooltipSelectors.ts
  • test/cartesian/Area.spec.tsx
  • src/cartesian/ReferenceLine.tsx
  • test/util/ChartUtils/getCateCoordinateOfLine.spec.ts
  • src/cartesian/Area.tsx
  • test/cartesian/ReferenceLine/getEndPoints.spec.tsx
  • test/chart/ScatterChart.spec.tsx
  • src/util/scale/RechartsScale.ts
  • src/polar/RadialBar.tsx
  • test/polar/PolarAngleAxis.spec.tsx
  • src/cartesian/ReferenceArea.tsx
  • test/cartesian/CartesianAxis.spec.tsx
  • src/cartesian/ReferenceDot.tsx
  • test/cartesian/XAxis/XAxis.barSize.spec.tsx
  • src/cartesian/Scatter.tsx
  • src/state/selectors/axisSelectors.ts
  • test/cartesian/getEquidistantTicks.spec.ts
  • src/cartesian/Bar.tsx
  • test/util/CartesianUtils/CartesianUtils.spec.ts
  • test/helper/mockAxes.ts
  • src/util/ChartUtils.ts
**/*.{ts,tsx,js,jsx}

📄 CodeRabbit inference engine (DEVELOPING.md)

All imports from recharts must use the public API entry point; imports from internal paths like recharts/types/* or recharts/src/* are not allowed

Files:

  • test/helper/expectScale.ts
  • src/cartesian/ErrorBar.tsx
  • src/cartesian/Line.tsx
  • src/util/types.ts
  • test/cartesian/getTicks.spec.ts
  • test/util/ChartUtils.spec.tsx
  • src/util/scale/CartesianScaleHelper.ts
  • src/polar/Radar.tsx
  • test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx
  • test/polar/PolarGrid.spec.tsx
  • src/util/scale/CustomScaleDefinition.ts
  • test/util/ChartUtils/checkDomainOfScale.spec.ts
  • src/state/selectors/tooltipSelectors.ts
  • test/cartesian/Area.spec.tsx
  • src/cartesian/ReferenceLine.tsx
  • test/util/ChartUtils/getCateCoordinateOfLine.spec.ts
  • src/cartesian/Area.tsx
  • test/cartesian/ReferenceLine/getEndPoints.spec.tsx
  • test/chart/ScatterChart.spec.tsx
  • src/util/scale/RechartsScale.ts
  • src/polar/RadialBar.tsx
  • test/polar/PolarAngleAxis.spec.tsx
  • src/cartesian/ReferenceArea.tsx
  • test/cartesian/CartesianAxis.spec.tsx
  • src/cartesian/ReferenceDot.tsx
  • test/cartesian/XAxis/XAxis.barSize.spec.tsx
  • src/cartesian/Scatter.tsx
  • src/state/selectors/axisSelectors.ts
  • test/cartesian/getEquidistantTicks.spec.ts
  • src/cartesian/Bar.tsx
  • test/util/CartesianUtils/CartesianUtils.spec.ts
  • test/helper/mockAxes.ts
  • src/util/ChartUtils.ts
src/**/*.{ts,tsx}

📄 CodeRabbit inference engine (AGENTS.md)

Do not hardcode any strings or formatting choices in library code; users should provide localized strings as desired

Files:

  • src/cartesian/ErrorBar.tsx
  • src/cartesian/Line.tsx
  • src/util/types.ts
  • src/util/scale/CartesianScaleHelper.ts
  • src/polar/Radar.tsx
  • src/util/scale/CustomScaleDefinition.ts
  • src/state/selectors/tooltipSelectors.ts
  • src/cartesian/ReferenceLine.tsx
  • src/cartesian/Area.tsx
  • src/util/scale/RechartsScale.ts
  • src/polar/RadialBar.tsx
  • src/cartesian/ReferenceArea.tsx
  • src/cartesian/ReferenceDot.tsx
  • src/cartesian/Scatter.tsx
  • src/state/selectors/axisSelectors.ts
  • src/cartesian/Bar.tsx
  • src/util/ChartUtils.ts
test/**/*.spec.{ts,tsx}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Aim for 100% unit test code coverage when writing new code

Files:

  • test/cartesian/getTicks.spec.ts
  • test/util/ChartUtils.spec.tsx
  • test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx
  • test/polar/PolarGrid.spec.tsx
  • test/util/ChartUtils/checkDomainOfScale.spec.ts
  • test/cartesian/Area.spec.tsx
  • test/util/ChartUtils/getCateCoordinateOfLine.spec.ts
  • test/cartesian/ReferenceLine/getEndPoints.spec.tsx
  • test/chart/ScatterChart.spec.tsx
  • test/polar/PolarAngleAxis.spec.tsx
  • test/cartesian/CartesianAxis.spec.tsx
  • test/cartesian/XAxis/XAxis.barSize.spec.tsx
  • test/cartesian/getEquidistantTicks.spec.ts
  • test/util/CartesianUtils/CartesianUtils.spec.ts
test/**/*.{test,spec}.{ts,tsx}

📄 CodeRabbit inference engine (test/README.md)

test/**/*.{test,spec}.{ts,tsx}: Aim for 100% unit test code coverage when writing new code
Prefer to use the createSelectorTestCase helper function when writing or modifying tests
Use the expectLastCalledWith helper function instead of expect(spy).toHaveBeenLastCalledWith(...) for better typing and autocompletion
Verify the number of selector calls using the spy object from createSelectorTestCase to spot unnecessary re-renders and improve performance
Mock getBoundingClientRect in tests using the helper function provided in test/helper/MockGetBoundingClientRect.ts
Use vi.useFakeTimers() in all tests due to Redux autoBatchEnhancer dependency on timers and requestAnimationFrame
Call vi.runOnlyPendingTimers() to advance timers after renders when not using createSelectorTestCase helper, and avoid vi.runAllTimers() to prevent infinite loops
Use userEvent.setup({ advanceTimers: vi.runOnlyPendingTimers }) or the userEventSetup helper function from test/helper/userEventSetup.ts when creating userEvent instances
When testing tooltips on hover, use vi.runOnlyPendingTimers() after each userEvent.hover() call or use the showTooltip helper function from tooltipTestHelpers.ts to account for requestAnimationFrame delays

Files:

  • test/cartesian/getTicks.spec.ts
  • test/util/ChartUtils.spec.tsx
  • test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx
  • test/polar/PolarGrid.spec.tsx
  • test/util/ChartUtils/checkDomainOfScale.spec.ts
  • test/cartesian/Area.spec.tsx
  • test/util/ChartUtils/getCateCoordinateOfLine.spec.ts
  • test/cartesian/ReferenceLine/getEndPoints.spec.tsx
  • test/chart/ScatterChart.spec.tsx
  • test/polar/PolarAngleAxis.spec.tsx
  • test/cartesian/CartesianAxis.spec.tsx
  • test/cartesian/XAxis/XAxis.barSize.spec.tsx
  • test/cartesian/getEquidistantTicks.spec.ts
  • test/util/CartesianUtils/CartesianUtils.spec.ts
**/*.spec.{ts,tsx}

📄 CodeRabbit inference engine (AGENTS.md)

When running unit tests, prefer to run a single test file using npm run test -- path/to/TestFile.spec.tsx rather than running all tests with npm test

Files:

  • test/cartesian/getTicks.spec.ts
  • test/util/ChartUtils.spec.tsx
  • test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx
  • test/polar/PolarGrid.spec.tsx
  • test/util/ChartUtils/checkDomainOfScale.spec.ts
  • test/cartesian/Area.spec.tsx
  • test/util/ChartUtils/getCateCoordinateOfLine.spec.ts
  • test/cartesian/ReferenceLine/getEndPoints.spec.tsx
  • test/chart/ScatterChart.spec.tsx
  • test/polar/PolarAngleAxis.spec.tsx
  • test/cartesian/CartesianAxis.spec.tsx
  • test/cartesian/XAxis/XAxis.barSize.spec.tsx
  • test/cartesian/getEquidistantTicks.spec.ts
  • test/util/CartesianUtils/CartesianUtils.spec.ts
test/component/**/*.spec.tsx

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Use React Testing Library for testing component interactions and behavior upon rendering

Files:

  • test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx
🧠 Learnings (21)
📓 Common learnings
Learnt from: PavelVanecek
Repo: recharts/recharts PR: 6783
File: test/util/ChartUtils.spec.tsx:15-16
Timestamp: 2025-12-16T08:12:13.355Z
Learning: In the recharts codebase, files in the `test` folder are allowed to import from internal paths (e.g., `../../src/state/cartesianAxisSlice`) and do not need to use the public API entry point (`src/index.ts`). The public API import restriction applies only to non-test code.
📚 Learning: 2025-11-25T01:23:08.250Z
Learnt from: CR
Repo: recharts/recharts PR: 0
File: test/README.md:0-0
Timestamp: 2025-11-25T01:23:08.250Z
Learning: Applies to test/**/*.{test,spec}.{ts,tsx} : Use the `expectLastCalledWith` helper function instead of `expect(spy).toHaveBeenLastCalledWith(...)` for better typing and autocompletion

Applied to files:

  • test/helper/expectScale.ts
  • test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx
  • test/polar/PolarGrid.spec.tsx
  • test/util/ChartUtils/checkDomainOfScale.spec.ts
  • test/cartesian/Area.spec.tsx
  • test/util/ChartUtils/getCateCoordinateOfLine.spec.ts
  • test/chart/ScatterChart.spec.tsx
  • test/polar/PolarAngleAxis.spec.tsx
  • test/cartesian/XAxis/XAxis.barSize.spec.tsx
  • test/util/CartesianUtils/CartesianUtils.spec.ts
📚 Learning: 2025-12-16T08:12:13.355Z
Learnt from: PavelVanecek
Repo: recharts/recharts PR: 6783
File: test/util/ChartUtils.spec.tsx:15-16
Timestamp: 2025-12-16T08:12:13.355Z
Learning: In the recharts codebase, files in the `test` folder are allowed to import from internal paths (e.g., `../../src/state/cartesianAxisSlice`) and do not need to use the public API entry point (`src/index.ts`). The public API import restriction applies only to non-test code.

Applied to files:

  • test/helper/expectScale.ts
  • test/cartesian/getTicks.spec.ts
  • src/util/scale/CartesianScaleHelper.ts
  • src/polar/Radar.tsx
  • test/util/ChartUtils/checkDomainOfScale.spec.ts
  • scripts/snapshots/es6Files.txt
  • src/cartesian/ReferenceLine.tsx
  • test/util/ChartUtils/getCateCoordinateOfLine.spec.ts
  • src/cartesian/Area.tsx
  • src/util/scale/RechartsScale.ts
  • scripts/snapshots/typesFiles.txt
  • scripts/snapshots/libFiles.txt
  • src/polar/RadialBar.tsx
  • src/cartesian/ReferenceArea.tsx
  • src/cartesian/ReferenceDot.tsx
  • src/state/selectors/axisSelectors.ts
  • src/cartesian/Bar.tsx
  • test/util/CartesianUtils/CartesianUtils.spec.ts
  • test/helper/mockAxes.ts
  • src/util/ChartUtils.ts
📚 Learning: 2025-11-25T01:23:08.250Z
Learnt from: CR
Repo: recharts/recharts PR: 0
File: test/README.md:0-0
Timestamp: 2025-11-25T01:23:08.250Z
Learning: Applies to test/**/*.{test,spec}.{ts,tsx} : Verify the number of selector calls using the spy object from `createSelectorTestCase` to spot unnecessary re-renders and improve performance

Applied to files:

  • test/helper/expectScale.ts
  • test/util/ChartUtils.spec.tsx
  • test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx
  • test/polar/PolarGrid.spec.tsx
  • test/util/ChartUtils/checkDomainOfScale.spec.ts
  • test/cartesian/Area.spec.tsx
  • test/util/ChartUtils/getCateCoordinateOfLine.spec.ts
  • test/cartesian/ReferenceLine/getEndPoints.spec.tsx
  • test/chart/ScatterChart.spec.tsx
  • test/polar/PolarAngleAxis.spec.tsx
  • test/cartesian/XAxis/XAxis.barSize.spec.tsx
  • test/util/CartesianUtils/CartesianUtils.spec.ts
📚 Learning: 2025-11-25T01:23:08.250Z
Learnt from: CR
Repo: recharts/recharts PR: 0
File: test/README.md:0-0
Timestamp: 2025-11-25T01:23:08.250Z
Learning: Applies to test/**/*.{test,spec}.{ts,tsx} : Prefer to use the `createSelectorTestCase` helper function when writing or modifying tests

Applied to files:

  • test/helper/expectScale.ts
  • test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx
  • test/polar/PolarGrid.spec.tsx
  • test/chart/ScatterChart.spec.tsx
  • test/polar/PolarAngleAxis.spec.tsx
  • test/util/CartesianUtils/CartesianUtils.spec.ts
📚 Learning: 2025-11-25T01:23:08.250Z
Learnt from: CR
Repo: recharts/recharts PR: 0
File: test/README.md:0-0
Timestamp: 2025-11-25T01:23:08.250Z
Learning: Applies to test/**/*.{test,spec}.{ts,tsx} : Mock `getBoundingClientRect` in tests using the helper function provided in `test/helper/MockGetBoundingClientRect.ts`

Applied to files:

  • test/helper/expectScale.ts
  • test/cartesian/getTicks.spec.ts
  • test/util/ChartUtils.spec.tsx
  • test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx
  • test/util/ChartUtils/checkDomainOfScale.spec.ts
  • test/cartesian/Area.spec.tsx
  • test/util/ChartUtils/getCateCoordinateOfLine.spec.ts
  • test/cartesian/ReferenceLine/getEndPoints.spec.tsx
  • test/chart/ScatterChart.spec.tsx
  • test/cartesian/getEquidistantTicks.spec.ts
  • test/util/CartesianUtils/CartesianUtils.spec.ts
  • test/helper/mockAxes.ts
📚 Learning: 2025-12-14T13:58:49.197Z
Learnt from: PavelVanecek
Repo: recharts/recharts PR: 6771
File: src/shape/Curve.tsx:39-40
Timestamp: 2025-12-14T13:58:49.197Z
Learning: In the recharts codebase, hooks like useAppSelector and other hooks (e.g., useChartLayout()) return undefined when used outside Redux Provider context, instead of throwing. This enables components that call these hooks, such as Curve, to operate in standalone mode by falling back to prop values. During code reviews, ensure TSX files gracefully handle undefined results from hooks and implement fallbacks (e.g., via default props or explicit prop-based values) rather than assuming the hook is always within Provider.

Applied to files:

  • src/cartesian/ErrorBar.tsx
  • src/cartesian/Line.tsx
  • src/polar/Radar.tsx
  • src/cartesian/ReferenceLine.tsx
  • src/cartesian/Area.tsx
  • src/polar/RadialBar.tsx
  • src/cartesian/ReferenceArea.tsx
  • src/cartesian/ReferenceDot.tsx
  • src/cartesian/Scatter.tsx
  • src/cartesian/Bar.tsx
📚 Learning: 2025-11-25T01:23:08.250Z
Learnt from: CR
Repo: recharts/recharts PR: 0
File: test/README.md:0-0
Timestamp: 2025-11-25T01:23:08.250Z
Learning: Applies to test/**/*.{test,spec}.{ts,tsx} : When testing tooltips on hover, use `vi.runOnlyPendingTimers()` after each `userEvent.hover()` call or use the `showTooltip` helper function from `tooltipTestHelpers.ts` to account for requestAnimationFrame delays

Applied to files:

  • test/cartesian/getTicks.spec.ts
  • test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx
  • test/polar/PolarGrid.spec.tsx
  • test/util/ChartUtils/checkDomainOfScale.spec.ts
  • src/state/selectors/tooltipSelectors.ts
  • test/chart/ScatterChart.spec.tsx
  • test/polar/PolarAngleAxis.spec.tsx
📚 Learning: 2025-12-16T08:12:06.809Z
Learnt from: PavelVanecek
Repo: recharts/recharts PR: 6783
File: test/util/ChartUtils.spec.tsx:15-16
Timestamp: 2025-12-16T08:12:06.809Z
Learning: In tests (files under any test directory, e.g., test/, __tests__/, etc.), allow importing internal module paths (e.g., ../../src/...) and do not require imports to use the public API entry point (src/index.ts). The public API import restriction should apply only to non-test code. During reviews, accept internal imports in test files and enforce the public API pattern only for non-test code.

Applied to files:

  • test/util/ChartUtils.spec.tsx
  • test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx
  • test/polar/PolarGrid.spec.tsx
  • test/cartesian/Area.spec.tsx
  • test/cartesian/ReferenceLine/getEndPoints.spec.tsx
  • test/chart/ScatterChart.spec.tsx
  • test/polar/PolarAngleAxis.spec.tsx
  • test/cartesian/CartesianAxis.spec.tsx
  • test/cartesian/XAxis/XAxis.barSize.spec.tsx
📚 Learning: 2025-12-06T03:36:59.377Z
Learnt from: CR
Repo: recharts/recharts PR: 0
File: DEVELOPING.md:0-0
Timestamp: 2025-12-06T03:36:59.377Z
Learning: Applies to **/*.{ts,tsx,js,jsx} : All imports from `recharts` must use the public API entry point; imports from internal paths like `recharts/types/*` or `recharts/src/*` are not allowed

Applied to files:

  • test/util/ChartUtils.spec.tsx
  • scripts/snapshots/es6Files.txt
  • test/cartesian/ReferenceLine/getEndPoints.spec.tsx
  • src/util/scale/RechartsScale.ts
  • scripts/snapshots/typesFiles.txt
  • scripts/snapshots/libFiles.txt
  • src/state/selectors/axisSelectors.ts
  • test/util/CartesianUtils/CartesianUtils.spec.ts
  • test/helper/mockAxes.ts
📚 Learning: 2025-11-23T13:30:10.395Z
Learnt from: PavelVanecek
Repo: recharts/recharts PR: 6669
File: www/src/docs/exampleComponents/ScatterChart/ScatterChartWithLabels.tsx:2-2
Timestamp: 2025-11-23T13:30:10.395Z
Learning: The `TooltipIndex` type from recharts is defined in `src/state/tooltipSlice.ts` but is not currently exported from the public API entry points. It should not be imported from `recharts/types/state/tooltipSlice` as this is an internal implementation path. An ESLint rule is needed to prevent regressions.

Applied to files:

  • test/util/ChartUtils.spec.tsx
  • test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx
  • test/util/ChartUtils/checkDomainOfScale.spec.ts
  • src/state/selectors/tooltipSelectors.ts
  • test/chart/ScatterChart.spec.tsx
  • src/util/scale/RechartsScale.ts
  • scripts/snapshots/typesFiles.txt
  • test/cartesian/XAxis/XAxis.barSize.spec.tsx
  • src/state/selectors/axisSelectors.ts
  • test/helper/mockAxes.ts
  • src/util/ChartUtils.ts
📚 Learning: 2025-11-19T14:08:01.728Z
Learnt from: PavelVanecek
Repo: recharts/recharts PR: 6659
File: www/src/components/GuideView/Performance/index.tsx:232-250
Timestamp: 2025-11-19T14:08:01.728Z
Learning: In Recharts version 3.4.2, object-as-prop optimizations were introduced to reduce unnecessary re-renders when new object references are passed as props. This affects the recommendation for the `react-perf/jsx-no-new-object-as-prop` ESLint rule.

Applied to files:

  • test/util/ChartUtils.spec.tsx
  • src/cartesian/ReferenceLine.tsx
📚 Learning: 2025-11-25T01:22:59.729Z
Learnt from: CR
Repo: recharts/recharts PR: 0
File: CONTRIBUTING.md:0-0
Timestamp: 2025-11-25T01:22:59.729Z
Learning: Applies to storybook/stories/**/*.stories.tsx : Update Storybook stories when APIs have been changed to ensure they work as expected

Applied to files:

  • test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx
  • test/cartesian/Area.spec.tsx
📚 Learning: 2025-11-25T01:23:08.250Z
Learnt from: CR
Repo: recharts/recharts PR: 0
File: test/README.md:0-0
Timestamp: 2025-11-25T01:23:08.250Z
Learning: Applies to test/**/*.{test,spec}.{ts,tsx} : Call `vi.runOnlyPendingTimers()` to advance timers after renders when not using `createSelectorTestCase` helper, and avoid `vi.runAllTimers()` to prevent infinite loops

Applied to files:

  • test/polar/PolarGrid.spec.tsx
  • test/chart/ScatterChart.spec.tsx
  • test/polar/PolarAngleAxis.spec.tsx
📚 Learning: 2025-11-25T01:22:59.729Z
Learnt from: CR
Repo: recharts/recharts PR: 0
File: CONTRIBUTING.md:0-0
Timestamp: 2025-11-25T01:22:59.729Z
Learning: Applies to test/component/**/*.spec.tsx : Use React Testing Library for testing component interactions and behavior upon rendering

Applied to files:

  • test/polar/PolarGrid.spec.tsx
  • test/chart/ScatterChart.spec.tsx
  • test/polar/PolarAngleAxis.spec.tsx
📚 Learning: 2025-11-25T01:22:59.729Z
Learnt from: CR
Repo: recharts/recharts PR: 0
File: CONTRIBUTING.md:0-0
Timestamp: 2025-11-25T01:22:59.729Z
Learning: Applies to **/*.{ts,tsx} : Type function parameters and return values explicitly in TypeScript, do not rely on implicit any or inference; exceptions are React components and trivial functions

Applied to files:

  • test/util/ChartUtils/checkDomainOfScale.spec.ts
📚 Learning: 2025-11-25T01:22:59.729Z
Learnt from: CR
Repo: recharts/recharts PR: 0
File: CONTRIBUTING.md:0-0
Timestamp: 2025-11-25T01:22:59.729Z
Learning: Applies to **/*.{ts,tsx} : Do not use `as` type assertions in TypeScript; the only exception is `as const`

Applied to files:

  • test/util/ChartUtils/checkDomainOfScale.spec.ts
📚 Learning: 2025-11-25T01:23:08.250Z
Learnt from: CR
Repo: recharts/recharts PR: 0
File: test/README.md:0-0
Timestamp: 2025-11-25T01:23:08.250Z
Learning: Applies to test/**/*.{test,spec}.{ts,tsx} : Use `vi.useFakeTimers()` in all tests due to Redux autoBatchEnhancer dependency on timers and `requestAnimationFrame`

Applied to files:

  • test/util/ChartUtils/checkDomainOfScale.spec.ts
  • test/cartesian/Area.spec.tsx
  • test/util/CartesianUtils/CartesianUtils.spec.ts
📚 Learning: 2025-11-25T01:22:59.729Z
Learnt from: CR
Repo: recharts/recharts PR: 0
File: CONTRIBUTING.md:0-0
Timestamp: 2025-11-25T01:22:59.729Z
Learning: Applies to test/**/*.spec.{ts,tsx} : Aim for 100% unit test code coverage when writing new code

Applied to files:

  • test/util/ChartUtils/checkDomainOfScale.spec.ts
📚 Learning: 2025-12-14T13:58:58.361Z
Learnt from: PavelVanecek
Repo: recharts/recharts PR: 6771
File: src/shape/Curve.tsx:39-40
Timestamp: 2025-12-14T13:58:58.361Z
Learning: In the recharts codebase, `useAppSelector` and hooks like `useChartLayout()` are designed to return `undefined` when used outside Redux Provider context, rather than throwing errors. This allows components like `Curve` that call these hooks to work standalone by falling back to prop values.

Applied to files:

  • scripts/snapshots/es6Files.txt
  • scripts/snapshots/libFiles.txt
  • src/state/selectors/axisSelectors.ts
  • test/helper/mockAxes.ts
📚 Learning: 2025-11-25T01:22:59.729Z
Learnt from: CR
Repo: recharts/recharts PR: 0
File: CONTRIBUTING.md:0-0
Timestamp: 2025-11-25T01:22:59.729Z
Learning: Extract pure helper functions for data processing and write unit tests for them

Applied to files:

  • test/util/CartesianUtils/CartesianUtils.spec.ts
🧬 Code graph analysis (15)
src/cartesian/Line.tsx (1)
src/util/DataUtils.ts (1)
  • isNullish (180-182)
test/cartesian/getTicks.spec.ts (1)
src/util/types.ts (1)
  • TickItem (832-844)
test/util/ChartUtils.spec.tsx (2)
src/util/ChartUtils.ts (1)
  • AxisPropsNeededForTicksGenerator (153-168)
src/util/scale/RechartsScale.ts (1)
  • d3ScaleToRechartsScale (99-139)
src/util/scale/CartesianScaleHelper.ts (2)
src/util/types.ts (3)
  • CategoricalDomainItem (732-732)
  • Coordinate (100-103)
  • NullableCoordinate (105-108)
src/util/scale/RechartsScale.ts (2)
  • BandPosition (82-82)
  • RechartsScale (15-74)
src/polar/Radar.tsx (1)
src/util/DataUtils.ts (1)
  • isNullish (180-182)
test/util/ChartUtils/checkDomainOfScale.spec.ts (1)
src/util/ChartUtils.ts (1)
  • checkDomainOfScale (284-301)
test/cartesian/Area.spec.tsx (1)
test/helper/mockAxes.ts (1)
  • mockScale (5-5)
src/cartesian/ReferenceLine.tsx (5)
src/util/scale/RechartsScale.ts (2)
  • BandPosition (82-82)
  • RechartsScale (15-74)
src/util/types.ts (2)
  • CartesianViewBoxRequired (866-866)
  • Coordinate (100-103)
src/util/isWellBehavedNumber.ts (1)
  • isWellBehavedNumber (1-3)
src/util/scale/CartesianScaleHelper.ts (2)
  • CartesianScaleHelper (4-16)
  • CartesianScaleHelperImpl (21-71)
src/util/DataUtils.ts (1)
  • isNumOrStr (27-27)
test/cartesian/ReferenceLine/getEndPoints.spec.tsx (2)
src/util/scale/RechartsScale.ts (3)
  • RechartsScale (15-74)
  • d3ScaleToRechartsScale (99-139)
  • BandPosition (82-82)
src/cartesian/ReferenceLine.tsx (2)
  • getEndPoints (216-245)
  • ReferenceLineSegment (38-47)
src/cartesian/ReferenceArea.tsx (2)
src/util/scale/CartesianScaleHelper.ts (1)
  • CartesianScaleHelperImpl (21-71)
src/util/types.ts (1)
  • NullableCoordinate (105-108)
src/cartesian/ReferenceDot.tsx (2)
src/util/types.ts (1)
  • Coordinate (100-103)
src/util/scale/CartesianScaleHelper.ts (1)
  • CartesianScaleHelperImpl (21-71)
src/state/selectors/axisSelectors.ts (4)
src/util/scale/RechartsScale.ts (1)
  • rechartsScaleFactory (147-171)
src/util/types.ts (2)
  • CategoricalDomainItem (732-732)
  • TickItem (832-844)
src/util/isWellBehavedNumber.ts (1)
  • isWellBehavedNumber (1-3)
src/util/DataUtils.ts (1)
  • isNotNil (202-204)
test/util/CartesianUtils/CartesianUtils.spec.ts (2)
src/util/scale/CartesianScaleHelper.ts (1)
  • CartesianScaleHelperImpl (21-71)
src/util/scale/RechartsScale.ts (1)
  • d3ScaleToRechartsScale (99-139)
test/helper/mockAxes.ts (1)
src/util/scale/RechartsScale.ts (2)
  • RechartsScale (15-74)
  • d3ScaleToRechartsScale (99-139)
src/util/ChartUtils.ts (5)
src/util/isWellBehavedNumber.ts (1)
  • isWellBehavedNumber (1-3)
src/util/types.ts (2)
  • CategoricalDomainItem (732-732)
  • TickItem (832-844)
src/util/scale/CustomScaleDefinition.ts (1)
  • CustomScaleDefinition (13-71)
src/index.ts (1)
  • CustomScaleDefinition (97-97)
src/util/DataUtils.ts (2)
  • isNumber (24-25)
  • isNullish (180-182)
⏰ 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). (2)
  • GitHub Check: Build, Test, Pack
  • GitHub Check: Analyze (javascript-typescript)
🔇 Additional comments (67)
scripts/snapshots/typesFiles.txt (1)

240-240: LGTM - Snapshot correctly updated for new CartesianScaleHelper.

The addition of the CartesianScaleHelper type definition file to the snapshot is correct and aligns with the introduction of the new scale helper utility.

scripts/snapshots/libFiles.txt (1)

240-240: LGTM - Snapshot correctly updated for new CartesianScaleHelper.

The addition of the CartesianScaleHelper library file to the snapshot is correct and aligns with the introduction of the new scale helper utility.

src/util/types.ts (1)

836-843: LGTM - Clear documentation for the offset field.

The JSDoc comment clearly explains the purpose of the offset field and its role in the external API. The note about Recharts not reading it internally is helpful context for maintainers.

test/component/Tooltip/Tooltip.multipleDataArrays.spec.tsx (1)

134-141: LGTM - Test correctly updated to use map-based scale API.

The change from scale(value) to scale.map(value) correctly adopts the new scale API pattern while maintaining the same expected behavior.

test/cartesian/getEquidistantTicks.spec.ts (2)

29-29: LGTM - Test data correctly includes offset field.

The addition of offset: 0 to tick objects correctly reflects the updated TickItem type. For non-band scales, the offset is always 0, which is the correct default value.


48-54: LGTM - Test data correctly structured with offset and index fields.

The CartesianTickItem objects now properly include the offset field, and the index is correctly added via the map transformation. This aligns with the updated TickItem interface.

scripts/snapshots/es6Files.txt (1)

240-240: LGTM - Snapshot correctly updated for new CartesianScaleHelper.

The addition of the CartesianScaleHelper ES6 module file to the snapshot is correct and aligns with the introduction of the new scale helper utility.

test/util/ChartUtils/checkDomainOfScale.spec.ts (1)

161-207: LGTM - Type suppressions necessary for comprehensive scale testing.

The @ts-expect-error annotations are appropriate here. The test arrays contain various D3 scale types with incompatible generic parameters (numbers, dates, strings), while checkDomainOfScale has a generic constraint. The runtime behavior is correct; these suppressions allow comprehensive testing across all scale types without splitting into multiple type-specific test cases.

test/util/ChartUtils/getCateCoordinateOfLine.spec.ts (1)

6-6: LGTM - Test mock correctly updated to RechartsScale interface.

The mock scale has been properly updated from a callable function to an object with a map method, aligning with the new RechartsScale API. The behavior remains identical (multiplying by 2), ensuring test continuity.

test/cartesian/XAxis/XAxis.barSize.spec.tsx (1)

148-185: LGTM! Test expectations correctly updated for the new TickItem shape.

The test expectations now include the index field for each tick, with sequential values from 0 to 5. This aligns with the broader TickItem type enhancement mentioned in the AI summary.

src/util/scale/CustomScaleDefinition.ts (1)

51-62: LGTM! Excellent documentation improvement.

The expanded JSDoc provides valuable context about the ticks method, including when it's available (quantitative scales only) and references to d3 documentation. This helps developers understand the method's behavior and limitations.

test/cartesian/CartesianAxis.spec.tsx (1)

23-29: LGTM! Test data correctly updated for the new TickItem shape.

The tick objects now include index (sequential 0-4) and offset (consistently 0) fields, matching the enhanced TickItem type signature mentioned in the PR objectives.

src/cartesian/Scatter.tsx (1)

748-748: LGTM! Scale API usage correctly updated.

The change from zAxis.scale(z) to zAxis.scale.map(z) aligns with the PR's goal to replace the implicit call signature with an explicit map method for better searchability and to avoid passing this.

test/helper/expectScale.ts (1)

23-23: LGTM! Test helper correctly updated for the new scale API.

The change from validating scale as a function to validating scale.map as a function correctly reflects the new RechartsScale API where scales are objects with a map method rather than callable functions.

test/cartesian/Area.spec.tsx (1)

1214-1215: LGTM! Test mocks correctly updated for the new scale API.

The mock scales now expose a map method instead of being callable functions themselves, matching the new RechartsScale interface. The scaling behavior is preserved (multiplying by 2 and 3 respectively).

src/cartesian/ErrorBar.tsx (2)

169-187: LGTM! Scale API usage correctly updated for x-direction error bars.

The change from scale(value ± bound) to scale.map(value ± bound) aligns with the PR's scale API refactor. The null checking and line construction logic remain unchanged, preserving the existing behavior.


188-207: LGTM! Scale API usage correctly updated for y-direction error bars.

The y-direction error bar calculation is updated consistently with the x-direction changes. The use of scale.map(value ± bound) replaces the previous direct invocation while maintaining the same behavior.

src/cartesian/Line.tsx (2)

933-942: LGTM! Scale API usage correctly updated for horizontal layout.

The change from yAxis.scale(value) to yAxis.scale.map(value) aligns with the PR's scale API refactor. The null handling with isNullish check is preserved, maintaining the existing behavior for handling missing or invalid data.


944-955: LGTM! Scale API usage correctly updated for vertical layout.

The vertical layout is updated consistently with the horizontal layout, using xAxis.scale.map(value) instead of direct invocation. The null handling and filtering logic remain unchanged, preserving the component's behavior.

src/cartesian/Area.tsx (1)

1034-1070: computeArea migration to scale.map looks correct and preserves semantics

Using xAxis.scale.map(...) / yAxis.scale.map(...) with ?? null and the existing baseLine ?? 0 fallback matches the new RechartsScale API while keeping previous behavior for out-of-domain or nullish values. No issues spotted.

src/state/selectors/tooltipSelectors.ts (1)

355-387: Tick generation now correctly uses RechartsScale.map

Replacing scale(entry) with scale.map(entry) in both categorical and non-categorical branches aligns this selector with the new RechartsScale interface, while the existing isWellBehavedNumber guard keeps invalid mappings filtered out. Looks good.

test/polar/PolarAngleAxis.spec.tsx (1)

181-234: Tick expectations updated coherently to the richer TickItem shape

Adding explicit index (and offset where applicable) to TickItem expectations and tick payloads keeps these tests in sync with the extended TickItem type and new scale/tick logic. Indexing and coordinates are consistent across the various radar and radial bar cases.

Also applies to: 716-745, 1069-1222, 1780-1796, 1894-1906, 2737-2776

test/helper/mockAxes.ts (1)

3-6: Mock axes now use the same RechartsScale abstraction as production code

Wrapping the linear D3 scale with d3ScaleToRechartsScale and typing mockScale as RechartsScale<number> aligns the test helper with the new axis scale contract and should make future refactors around map-based usage smoother.

src/polar/Radar.tsx (1)

236-267: computeRadarPoints safely migrates to scale.map for angle and radius

Angle and radius computations now use angleAxis.scale.map / radiusAxis.scale.map with a ?? 0 fallback, which integrates with RechartsScale and avoids leaking undefined into the polar coordinate math. The range-handling for baseline points is updated consistently too.

test/util/ChartUtils.spec.tsx (2)

16-22: Tests now construct scales via d3ScaleToRechartsScale, matching production types

Wrapping scaleLinear, scaleBand, and scalePoint with d3ScaleToRechartsScale brings the test AxisPropsNeededForTicksGenerator.scale and BaseAxisWithScale.scale into alignment with the RechartsScale interface used in ChartUtils, so tick-related helpers exercise the same abstraction as real axes.

Also applies to: 34-41, 94-97, 114-127, 131-144


145-151: Tick fixtures updated to include index/offset in line with the new TickItem contract

Adding index (and offset: 0 where relevant) to TickItem arrays used in getBandSizeOfAxis and calculateActiveTickIndex tests keeps these expectations compatible with the enriched TickItem type and with how ticks are produced elsewhere.

Also applies to: 246-252

src/polar/RadialBar.tsx (1)

587-621: Radial bar sector geometry correctly moved to scale.map

Using angleAxis.scale.map and radiusAxis.scale.map in computeRadialBarDataItems aligns radial bar geometry with the new scale abstraction while preserving the existing minPointSize and background-sector logic. Fallback to rootStartAngle/rootEndAngle on failed angle mapping is a reasonable safety net.

test/polar/PolarGrid.spec.tsx (1)

689-717: Polar grid tick expectations updated consistently with new TickItem shape

The various polar grid tests now assert full TickItem objects (coordinate, value, index, offset), which matches the updated selector behavior and shared TickItem type. The values look internally consistent across implicit and multi-axis scenarios.

Also applies to: 775-788, 938-959, 1012-1022, 1218-1262

test/chart/ScatterChart.spec.tsx (2)

796-803: Test expectations correctly updated for new TickItem shape.

The updated expectations now include index and offset properties, aligning with the enhanced TickItem type. The offset: 0 is correct for numerical axes without bands.


938-943: Consistent update for YAxis tick expectations.

The test expectations correctly include index and offset fields matching the updated TickItem type.

src/cartesian/Bar.tsx (3)

959-959: Correct migration to map-based scale access.

The stackedBarStart computation correctly uses scale.map() instead of direct invocation.


983-984: Proper null handling preserved after map() migration.

The existing null checks on lines 985-987 correctly handle potential undefined returns from scale.map().


1009-1010: Consistent map-based access for vertical layout.

The vertical layout path mirrors the horizontal path correctly, with null checks on lines 1011-1013.

src/cartesian/ReferenceDot.tsx (1)

83-85: Clean migration to CartesianScaleHelperImpl.

The use of scales.map() with position: 'middle' correctly centers the dot on band scales.

src/util/ChartUtils.ts (4)

215-227: Correct migration to map-based scaling with proper null handling.

The scale.map() invocation with isWellBehavedNumber check ensures only valid coordinates are used for tick generation.


284-301: Well-designed generic signature for checkDomainOfScale.

The generic <T extends CategoricalDomainItem> constraint ensures type safety while supporting all domain types. The added null check on line 298 properly guards against scales that return undefined for boundary values.


540-545: Improved null safety in getCateCoordinateOfLine.

The explicit isNumber check after scale.map() correctly handles cases where the scale returns undefined, returning null instead of potentially propagating undefined values.


565-577: Consistent map-based access in getCateCoordinateOfBar.

The null safety pattern is consistent with other scale usages in this file.

test/cartesian/ReferenceLine/getEndPoints.spec.tsx (2)

8-27: Well-designed mock for testing scale isolation.

The throwingScale mock is a good pattern to ensure that certain code paths don't invoke scale methods when they shouldn't. This provides clear test isolation.


352-384: Good use of parameterized tests for overflow scenarios.

Using it.each for testing multiple overflow values (hidden, visible, extendDomain, discard) is a clean approach that ensures consistent behavior across all modes while keeping the tests DRY.

test/cartesian/getTicks.spec.ts (2)

14-20: Test fixtures correctly updated with offset field.

The addition of offset: 0 to all tick items aligns with the updated TickItem type. For non-banded scales, an offset of 0 is the expected value.


224-231: Consistent offset handling in dynamically generated tick items.

The offset field is correctly added in the dynamically created tick items within the test helper function.

test/util/CartesianUtils/CartesianUtils.spec.ts (4)

8-12: Comprehensive test setup with parameterized position variants.

Using describe.each for testing all three position values ('start', 'middle', 'end') is an efficient approach that ensures consistent behavior across all band positions.


61-92: Thorough isInRange edge case coverage.

The tests cover important edge cases including:

  • Values in range
  • Values out of range on individual axes
  • Missing/null coordinates (which are treated as "in range")
  • Empty coordinate objects

This is excellent coverage for the isInRange method.


114-117: Good test for unmapped values in band scales.

Testing that unmapped values (values not in the domain like 'Z' and '5') return { x: 0, y: 0 } validates the fallback behavior of the map method.


150-159: Good coverage for fallback behavior with unmapped values.

Testing both 'rangeMin' and 'rangeMax' fallbacks for unmapped domain values ensures the mapWithFallback method correctly falls back when the scale can't map a value.

src/cartesian/ReferenceLine.tsx (3)

146-170: Clean refactor using new scale abstraction.

The getHorizontalLineEndPoints function now properly uses scale.map() for coordinate calculation and scale.isInRange() for overflow detection. The early return pattern with isWellBehavedNumber validation is a good defensive practice.


198-214: Consistent use of CartesianScaleHelper for segment handling.

Using scales.mapWithFallback() with appropriate fallback values ('rangeMin' for start point, 'rangeMax' for end point) is a sensible approach for handling partial segment coordinates. The isInRange check properly validates both points.


274-282: Clean integration with the new scale API.

The ReferenceLineImpl now correctly passes xAxisScale and yAxisScale directly to getEndPoints, aligning with the refactored function signature.

src/util/scale/RechartsScale.ts (5)

33-47: Well-documented interface extensions.

The new rangeMin(), rangeMax(), and isInRange() methods are clearly documented and provide useful utilities for range validation. This is a clean addition to the interface.


76-82: Good inline documentation for BandPosition type.

The @inline JSDoc tag and clear description make the type self-documenting.


110-114: Robust isInRange implementation handling reversed ranges.

The implementation correctly handles both normal ranges (where first <= last) and reversed ranges. Using range[range.length - 1] is defensive, though range[1] would work given the range is always a tuple of two numbers.


117-137: Correct band position offset calculation.

The map method properly applies band position offsets:

  • 'start': no adjustment (default)
  • 'middle': adds half bandwidth
  • 'end': adds full bandwidth

The null check on baseValue ensures undefined is returned for unmapped domain values.


147-153: Good immutability pattern with copy().

Using scale.copy() before applying domain and range ensures the original scale is not mutated. This is important for React integration as noted in the interface documentation.

src/util/scale/CartesianScaleHelper.ts (3)

1-16: Well-designed interface with proper generic typing.

The CartesianScaleHelper interface cleanly abstracts the coordinate mapping operations with appropriate domain type parameters. The method signatures properly handle optional/nullable values in mapWithFallback and isInRange.


18-39: Implementation looks correct.

The class properly implements the interface, and the map method correctly falls back to 0 when the underlying scale returns undefined, which aligns with the Coordinate type requiring concrete numbers.


66-70: Correct null-handling logic in isInRange.

Treating null/undefined coordinates as "in range" is appropriate since partial coordinates should not fail the range check. The implementation correctly delegates to the underlying scale's isInRange method.

src/state/selectors/axisSelectors.ts (10)

89-89: Import updated to use new scale factory.

The import correctly reflects the rename from makeRechartsScale to rechartsScaleFactory.


1144-1158: Scale factory usage is correct.

The function properly delegates to rechartsScaleFactory for both custom scale functions and string-based scale types, maintaining the expected return type.


1845-1845: Type annotation improved.

Changing categoricalDomain from ReadonlyArray<unknown> to ReadonlyArray<CategoricalDomainItem> provides better type safety and aligns with the coding guidelines to avoid any and unknown where possible.


1869-1886: Scale mapping refactored correctly.

The transition from direct scale invocation to scale.map() is correctly applied. The null check via isWellBehavedNumber appropriately handles cases where map() returns undefined.


1888-1904: Categorical domain handling updated with proper typing.

The entry parameter is now correctly typed as CategoricalDomainItem, and the scale.map(entry) call follows the new API pattern.


1906-1917: Tick generation with scale.ticks() correctly uses map().

The refactored code properly chains scale.ticks(tickCount) with .map() and uses scale.map(entry) for coordinate calculation.


1919-1936: Domain-based tick generation updated correctly.

The fallback path using scale.domain() properly applies scale.map(entry) with the typed CategoricalDomainItem. The remaining @ts-expect-error on line 1929-1930 is an acknowledged limitation with Date indexing.


1965-1976: Function signature properly updated.

The categoricalDomain parameter type is correctly changed to ReadonlyArray<CategoricalDomainItem>, consistent with combineAxisTicks.


1987-2015: Tick generation paths correctly use scale.map().

Both the categorical domain path and the scale.ticks() path correctly apply the new scale.map(entry) pattern with proper null handling.


2017-2034: Domain fallback path updated consistently.

The domain-based tick generation mirrors the pattern in combineAxisTicks, with the same acknowledged limitation for Date indexing preserved via @ts-expect-error.

@codecov

codecov Bot commented Dec 22, 2025

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 95.85253% with 9 lines in your changes missing coverage. Please review.
✅ Project coverage is 93.44%. Comparing base (499a165) to head (06163f4).
⚠️ Report is 4 commits behind head on main.

Files with missing lines Patch % Lines
src/util/scale/CartesianScaleHelper.ts 90.47% 4 Missing ⚠️
src/cartesian/ReferenceLine.tsx 95.34% 2 Missing ⚠️
src/polar/RadialBar.tsx 50.00% 2 Missing ⚠️
src/polar/Radar.tsx 66.66% 1 Missing ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##             main    #6811      +/-   ##
==========================================
- Coverage   93.44%   93.44%   -0.01%     
==========================================
  Files         522      523       +1     
  Lines       45580    45622      +42     
  Branches     5047     5056       +9     
==========================================
+ Hits        42594    42632      +38     
- Misses       2979     2983       +4     
  Partials        7        7              

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

@github-actions

Copy link
Copy Markdown
Contributor

Staging Deployment Details

These deployments will remain available for 30 days.

To update snapshots: Comment /update-snapshots on this PR to automatically update the baseline screenshots.

@ckifer ckifer left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

nice readability win

@ckifer
ckifer merged commit 00832cf into main Dec 22, 2025
43 checks passed
@ckifer
ckifer deleted the ts-strict branch December 22, 2025 17:05
@codecov

codecov Bot commented Dec 22, 2025

Copy link
Copy Markdown

Bundle Report

Changes will increase total bundle size by 2.61kB (0.1%) ⬆️. This is within the configured threshold ✅

Detailed changes
Bundle name Size Change
recharts/bundle-cjs 1.18MB 1.62kB (0.14%) ⬆️
recharts/bundle-es6 1.02MB 1.38kB (0.14%) ⬆️
recharts/bundle-umd 522.72kB -390 bytes (-0.07%) ⬇️

Affected Assets, Files, and Routes:

view changes for bundle: recharts/bundle-umd

Assets Changed:

Asset Name Size Change Total Size Change (%)
Recharts.js -390 bytes 522.72kB -0.07%
view changes for bundle: recharts/bundle-cjs

Assets Changed:

Asset Name Size Change Total Size Change (%)
state/selectors/axisSelectors.js 268 bytes 63.82kB 0.42%
cartesian/Area.js 88 bytes 29.46kB 0.3%
cartesian/Bar.js 20 bytes 27.81kB 0.07%
cartesian/Line.js 8 bytes 26.36kB 0.03%
cartesian/Scatter.js 4 bytes 24.2kB 0.02%
polar/RadialBar.js 48 bytes 21.25kB 0.23%
util/ChartUtils.js 100 bytes 20.46kB 0.49%
polar/Radar.js 60 bytes 17.87kB 0.34%
state/selectors/tooltipSelectors.js 8 bytes 17.68kB 0.05%
cartesian/CartesianGrid.js -40 bytes 16.5kB -0.24%
cartesian/ReferenceLine.js 301 bytes 10.56kB 2.93%
cartesian/ErrorBar.js 16 bytes 10.2kB 0.16%
cartesian/ReferenceArea.js 628 bytes 8.34kB 8.14% ⚠️
cartesian/ReferenceDot.js 123 bytes 7.02kB 1.78%
util/scale/RechartsScale.js 1.67kB 4.41kB 61.21% ⚠️
util/CartesianUtils.js -3.75kB 2.36kB -61.39%
util/scale/CartesianScaleHelper.js (New) 2.06kB 2.06kB 100.0% 🚀
view changes for bundle: recharts/bundle-es6

Assets Changed:

Asset Name Size Change Total Size Change (%)
state/selectors/axisSelectors.js 197 bytes 53.84kB 0.37%
cartesian/Area.js 88 bytes 27.59kB 0.32%
cartesian/Bar.js 20 bytes 26.1kB 0.08%
cartesian/Line.js 8 bytes 24.75kB 0.03%
cartesian/Scatter.js 4 bytes 22.58kB 0.02%
polar/RadialBar.js 48 bytes 19.8kB 0.24%
util/ChartUtils.js 100 bytes 18.37kB 0.55%
polar/Radar.js 60 bytes 16.4kB 0.37%
cartesian/CartesianGrid.js -40 bytes 15.21kB -0.26%
state/selectors/tooltipSelectors.js 8 bytes 14.21kB 0.06%
cartesian/ErrorBar.js 16 bytes 9.2kB 0.17%
cartesian/ReferenceLine.js 256 bytes 9.15kB 2.88%
cartesian/ReferenceArea.js 610 bytes 7.16kB 9.32% ⚠️
cartesian/ReferenceDot.js 121 bytes 5.9kB 2.09%
util/scale/RechartsScale.js 1.62kB 3.54kB 84.01% ⚠️
util/CartesianUtils.js -3.62kB 2.05kB -63.89%
util/scale/CartesianScaleHelper.js (New) 1.89kB 1.89kB 100.0% 🚀

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