Skip to content

chore: Add sentry-analytics Claude skill#107537

Open
JoshFerge wants to merge 1 commit intomasterfrom
jferg/sentry-analytics-skill
Open

chore: Add sentry-analytics Claude skill#107537
JoshFerge wants to merge 1 commit intomasterfrom
jferg/sentry-analytics-skill

Conversation

@JoshFerge
Copy link
Member

Summary

Adds a Claude Code skill for adding frontend analytics events to the Sentry codebase.

What the skill covers

  • Button click analytics - Using analyticsEventKey, analyticsEventName, and analyticsParams props (preferred approach)
  • Manual trackAnalytics() - For non-button events like form submissions, effects
  • Event type definitions - Where to define types and event maps
  • Naming conventions - Event key and Amplitude name formats

Usage

The skill will be automatically triggered when asking Claude to add analytics events. It provides guidance on:

  1. Using button props for click tracking (preferred)
  2. When to use trackAnalytics() instead
  3. How to define event types in seerAnalyticsEvents.tsx or similar
  4. Testing with DEBUG_ANALYTICS=1

Test plan

  • Verify skill loads correctly with /sentry-analytics
  • Ask Claude to add an analytics event and verify it follows the patterns

Adds a Claude Code skill for adding frontend analytics events to the
Sentry codebase. Covers:

- Button click analytics (analyticsEventKey/analyticsEventName props)
- Manual trackAnalytics() for non-button events
- Event type definitions and naming conventions
**Use button props for click tracking whenever possible.** This is the simplest approach and provides automatic tracking.

```tsx
<Button
Copy link
Member Author

Choose a reason for hiding this comment

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

do this button prop analytic event tracking pick up default params like user id and org and whatnot?

@@ -0,0 +1,118 @@
---
name: sentry-analytics
Copy link
Member Author

Choose a reason for hiding this comment

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

maybe rename to sentry-frontend-analytics?

Copy link
Member

Choose a reason for hiding this comment

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

Agree, that would be better!

Comment on lines +42 to +86
### 1. Define event types

Add to appropriate file in `static/app/utils/analytics/` (e.g., `featureAnalyticsEvents.tsx`):

```typescript
export type FeatureEventParameters = {
'feature_name.action_performed': {
source: string;
};
'feature_name.modal_opened': Record<string, unknown>; // No params
};

export const featureEventMap: Record<keyof FeatureEventParameters, string | null> = {
'feature_name.action_performed': 'Feature Name: Action Performed', // Amplitude name
'feature_name.modal_opened': null, // null = don't send to Amplitude
};
```

### 2. Register in index

Add to `static/app/utils/analytics/index.tsx`:

```typescript
import {featureEventMap, type FeatureEventParameters} from './featureAnalyticsEvents';

export type EventParameters =
// ... existing types
FeatureEventParameters;

export const allEventMap = {
// ... existing maps
...featureEventMap,
};
```

### 3. Track the event

```typescript
import {trackAnalytics} from 'sentry/utils/analytics';

trackAnalytics('feature_name.action_performed', {
organization,
source: 'modal',
});
```
Copy link
Member Author

Choose a reason for hiding this comment

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

i assume this is only needed if we don't use the button props stuff?

Copy link
Member

Choose a reason for hiding this comment

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

Exactly, but tbh, I'd prefer to just have explicit trackAnalytics calls, it will work cross all different components and be more explicit. These props are only supported on the button component too, which is super wonky from an API consistency pov

Copy link
Member Author

Choose a reason for hiding this comment

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

gotcha, so maybe it sounds like for simple buttons it makes sense to use them, but if you need any additional props you should use trackAnalyticsEvents in the onclick handler?

Copy link
Member

Choose a reason for hiding this comment

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

I'd go even further and just say use the trackAnalyticsEvent function all the time. Nobody ever knows these props exist, and what seems like a convenience thing turns into confusion.

I'd bet that even for simple stuff, people end up calling trackAnalyticsEvent and it's the same reason why people write <Tooltip><Button/></Tooltip> even thought they could use tooltipProps from the button.

Comment on lines +103 to +106
```typescript
useEffect(() => {
trackAnalytics('feature.viewed', {organization});
}, [organization]);
Copy link
Member

Choose a reason for hiding this comment

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

we don't want people to create effects for this since really what you want is a debounce for things like loading. we have a useRouteAnalyticsEventNames and useRouteAnalyticsParams

Copy link
Member

Choose a reason for hiding this comment

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

i guess that mostly only makes sense for page level analytics, but most are when counting views

@JonasBa
Copy link
Member

JonasBa commented Feb 3, 2026

@JoshFerge I would add one thing here which is to guide AI away from useEffect and observing state, and to instead add trackAnalyticsEvent to the existing callbacks.

For example

const [toggle, setToggle] = useState()

<input type="radio" onChange={() => setToggle(!toggle)}

shouldn't become (also likely unwanted as it will fire on initial render)

const [toggle, setToggle] = useState();

useEffect(() => trackAnalytics(...), [toggle])

<input type="radio" onChange={() => setToggle(!toggle)}/>

but should instead just be

const [toggle, setToggle] = useState()

<input type="radio" onChange={() => {
	trackAnalytics(!toggle)
	setToggle(!toggle)
}}/>

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.

3 participants