feat(spinner): add resuable spinner component with size variant - #8
LikithaYadavG wants to merge 2 commits into
Conversation
Change SummaryThis PR adds an accessible, reusable Spinner component with three size variants (sm, md, lg) and corresponding unit tests. The Spinner exposes SpinnerProps, accepts a custom className, and uses Tailwind CSS utility classes for sizing, borders, and spin animation to provide a consistent loading indicator. File Changes
|
PR ScorecardScoreScoring MethodologyCommunication Scoring FrameworkThe overall communication score is a weighted average:
Formula: Code Scoring FrameworkThe scorecard evaluates code using 3 key reviewer questions:
PR Communication NotesDescription Quality
PR Size & Scope
Commit Messages
NotesCode Correctness & Design Quality
Test Quality & Coverage
Code Readability & Maintainability
|
| className?: string; | ||
| } | ||
|
|
||
| export const Spinner = ({ size = "md", className = "" }: SpinnerProps) => { |
There was a problem hiding this comment.
Severity: 🟠 Major
Make the spinner more reusable/accessibility-friendly by fixing the border-3 class, forwarding standard DOM props, and allowing the accessible label to be customized.
Suggested Change:
import type { HTMLAttributes } from "react";
const SIZE_STYLES = {
sm: "w-4 h-4 border-2",
md: "w-8 h-8 border-[3px]", // or a Tailwind-supported border width
lg: "w-12 h-12 border-4",
} as const;
export type SpinnerProps = {
size?: keyof typeof SIZE_STYLES;
ariaLabel?: string;
className?: string;
} & Omit<HTMLAttributes<HTMLSpanElement>, "aria-label">;
export const Spinner = ({
size = "md",
ariaLabel = "Loading",
className = "",
...rest
}: SpinnerProps) => {
const sizeClass = SIZE_STYLES[size] ?? SIZE_STYLES.md;
return (
<span
role="status"
aria-live="polite"
aria-label={ariaLabel}
className={`inline-block ${sizeClass} border-gray-200 border-t-blue-600 rounded-full animate-spin ${className}`.trim()}
{...rest}
/>
);
};| @@ -0,0 +1,62 @@ | |||
| import { render, screen } from "@testing-library/react"; | |||
There was a problem hiding this comment.
Severity: 🟠 Major
Update tests to actually verify the component’s default size behavior and remove the unused userEvent setup.
Suggested Change:
import { render, screen } from "@testing-library/react";
import { describe, it, expect } from "vitest";
import { Spinner, type SpinnerProps } from "./Spinner";
const renderSpinner = (props: Partial<SpinnerProps> = {}) => {
render(<Spinner {...props} />);
return screen.getByRole("status", { name: /loading/i });
};
describe("Spinner", () => {
it("should render medium size spinner by default", () => {
const spinner = renderSpinner(); // no size prop
expect(spinner).toHaveClass("w-8", "h-8");
});
it("should render small size spinner when size is sm", () => {
const spinner = renderSpinner({ size: "sm" });
expect(spinner).toHaveClass("w-4", "h-4");
});
it("should render large size spinner when size is lg", () => {
const spinner = renderSpinner({ size: "lg" });
expect(spinner).toHaveClass("w-12", "h-12");
});
});| it("should render medium size spinner by default", () => { | ||
| const { spinner } = renderSpinner(); | ||
|
|
||
| expect(spinner).toHaveClass("w-8 h-8"); |
There was a problem hiding this comment.
Severity: 💬 Minor [nitpick]
Prefer asserting individual class tokens in toHaveClass to avoid ambiguity if class ordering/spacing changes.
Suggested Change:
expect(spinner).toHaveClass("w-8", "h-8");
PR OverviewPR Type: Feature Focus Areas for Architect ReviewConfirm the Spinner’s intended accessibility contract (explicit Validate Tailwind border-width tokens (e.g., PR InsightsPotential PR Improvements
Strengths
|
|
Tip Need another review? Tag me and say rereview for re-analysis after you have fixed all the issues. @cw-pr-agent rereview |
PR Template & Definition of Done
What does this PR do?
What steps does your reviewer have to take to test this PR manually?
Pull Request standards checklist - Please check off
Testing checklist - Please check off
If you have not followed and completed any of the above, please explain why below.
N/A
Definition of Done - Please check off