WOOA7S-1513: Port Stats Subscriber highlights widget#50299
Conversation
|
Thank you for your PR! When contributing to Jetpack, we have a few suggestions that can help us test and review your patch:
This comment will be updated as you work on your PR and make changes. If you think that some of those checks are not needed for your PR, please explain why you think so. Thanks for cooperation 🤖 Follow this PR Review Process:
If you have questions about anything, reach out in #jetpack-developers for guidance! |
Code Coverage SummaryThis PR did not change code coverage! That could be good or bad, depending on the situation. Everything covered before, and still is? Great! Nothing was covered before? Not so great. 🤷 |
There was a problem hiding this comment.
Pull request overview
Ports the existing Stats “Subscriber highlights” UI into Premium Analytics as a new jpa/subscriber-highlights widget, matching the established “Annual highlights” widget patterns (framed presentation, metric tiles, per-metric visibility toggles), backed by the existing subscribers/counts Stats proxy hook.
Changes:
- Added the new Subscriber highlights widget (definition, render, styles, package metadata) with per-tile visibility attributes.
- Added Storybook stories and Storybook mock handling/fixture data for the
subscribers/countsendpoint. - Added Jest tests for fetching and visibility-toggle behavior, plus a Premium Analytics changelog entry.
Reviewed changes
Copilot reviewed 11 out of 11 changed files in this pull request and generated no comments.
Show a summary per file
| File | Description |
|---|---|
| projects/packages/premium-analytics/widgets/subscriber-highlights/widget.ts | Defines the widget type and per-metric boolean attribute schema with defaults. |
| projects/packages/premium-analytics/widgets/subscriber-highlights/widget.json | Declares widget metadata (name/title/description/category/presentation) for the host. |
| projects/packages/premium-analytics/widgets/subscriber-highlights/style.module.css | Implements the framed widget layout and responsive tile grid styling. |
| projects/packages/premium-analytics/widgets/subscriber-highlights/render.tsx | Fetches subscribers/counts via useStatsSubscribersCounts and renders tiles with attribute-driven visibility. |
| projects/packages/premium-analytics/widgets/subscriber-highlights/stories/subscriber-highlights-widget.stories.tsx | Adds Storybook stories (Default/WithComparison/Dashboard harness) with controls matching widget settings. |
| projects/packages/premium-analytics/widgets/subscriber-highlights/tests/subscriber-highlights.test.tsx | Adds test coverage for data fetching, tile visibility toggles, and “no metrics selected” state. |
| projects/packages/premium-analytics/widgets/subscriber-highlights/package.json | Adds the widget package with dependencies consistent with other Premium Analytics widgets. |
| projects/packages/premium-analytics/packages/widgets-toolkit/src/stories/mocks/register-report-mocks.ts | Registers a Storybook mock handler for the v2 subscribers/counts proxy path. |
| projects/packages/premium-analytics/packages/widgets-toolkit/src/stories/mocks/data/subscriber-counts.ts | Adds fixture data for the raw subscribers/counts response shape. |
| projects/packages/premium-analytics/packages/widgets-toolkit/src/stories/mocks/data/index.ts | Exports the new subscriber counts fixture for Storybook mock registration. |
| projects/packages/premium-analytics/changelog/add-subscriber-highlights-widget | Adds a minor “added” changelog entry for the new widget. |
louwie17
left a comment
There was a problem hiding this comment.
Looks good and tested well! I left several comments, but they are mostly nitpicks and can also be done in follow ups. Especially the consolidation of the Widget tile work.
| <Icon icon={ tile.icon } size={ 24 } className={ styles.tileIcon } /> | ||
| <Text className={ styles.tileLabel }>{ tile.label }</Text> | ||
| </div> | ||
| <MetricWithComparison |
There was a problem hiding this comment.
We are using MetricWithComparison but don't support comparison on this component, unless this a future thing?
| export const WithComparison: Story = { | ||
| render: renderSubscriberHighlights, | ||
| args: { withComparison: true, ...ALL_METRICS_ARGS }, | ||
| decorators: [ withWidgetCanvas ], | ||
| }; |
There was a problem hiding this comment.
We can remove this storybook, given we don't show comparison.
| { | ||
| key: 'total', | ||
| icon: people, | ||
| label: __( 'Total subscribers', 'jetpack-premium-analytics' ), |
There was a problem hiding this comment.
We also define the names in widget.ts, maybe we should combine them? so we don't accidentally mismatch them.
| .grid { | ||
| display: grid; | ||
| grid-template-columns: 1fr; | ||
| gap: var(--wpds-dimension-gap-sm, 8px); | ||
| } | ||
|
|
||
| .tile { | ||
| display: flex; | ||
| flex-direction: row; | ||
| align-items: center; | ||
| justify-content: space-between; | ||
| gap: var(--wpds-dimension-gap-md, 12px); | ||
| padding: var(--wpds-dimension-padding-md, 12px) var(--wpds-dimension-padding-lg, 16px); | ||
| border: var(--wpds-border-width-xs, 1px) solid var(--wpds-color-stroke-surface-neutral-weak); | ||
| border-radius: var(--wpds-border-radius-lg, 8px); | ||
| } | ||
|
|
||
| .tileHeader { | ||
| display: flex; | ||
| flex-direction: row; | ||
| align-items: center; | ||
| gap: var(--wpds-dimension-gap-sm, 8px); | ||
| min-width: 0; | ||
| color: var(--wpds-color-foreground-content-neutral); | ||
| } | ||
|
|
||
| .tileIcon { | ||
| flex: 0 0 auto; | ||
| } | ||
|
|
||
| .tileLabel { | ||
| color: var(--wpds-color-foreground-content-neutral); | ||
| } | ||
|
|
||
| /* MetricValue emits the font-size token without a fallback, and the dashboard | ||
| * runtime does not always inject the WPDS typography tokens, so pin the metric | ||
| * total here with explicit fallbacks. */ | ||
| .tileValue span { | ||
| font-size: var(--wpds-typography-font-size-xl, 20px); | ||
| line-height: var(--wpds-typography-line-height-xl, 32px); | ||
| } |
There was a problem hiding this comment.
We end up having identical CSS also for the Annual highlights: https://github.com/Automattic/jetpack/blob/trunk/projects/packages/premium-analytics/widgets/annual-highlights/style.module.css#L44
It may be worth having a MetricTile component?
Proposed changes
Ports the Stats "Subscriber highlights" section into Premium Analytics as the
jpa/subscriber-highlightswidget, mirroring the shipped Annual highlights widget.widgets/subscriber-highlights/— four metric tiles (Total / Paid / Free / Social followers), each with a per-metric visibility toggle (default on).useStatsSubscribersCountshook (subscribers/counts, already-allow-listedsubscribersprefix). No new hook or proxy prefix.Default,WithComparison,WidgetDashboardWithWidget; added asubscribers/countsfixture + handler.Related product discussion/links
Does this pull request change what data or activity we track or use?
No.
Testing instructions
WithComparisonrenders the same asDefault.Screen.Recording.2026-07-08.at.4.03.35.PM.mov