Add analytics on links in React.
The problem: #
Recently I joined a team with with a large React front-end. I was tasked with figuring out how to add analytics to a ton of buttons and links throughout the application. I wanted an easy way to add analytics without having to write onClick
event handlers which would fire events from a library like react-ga.
For the sake of this demo, I’ll be talking about how I added Google Analytics for user-driven event tracking, but you can bring whichever fancy analytics library satisfies you.
The solution: #
The easiest solution I thought of was to create a new <A>
React component which would substitute html <a>
links. It would do so by intercepting the <a>
link’s onClick()
event, running the analytics library code, and then continuing to the the child’s onClick()
event if it existed. Clicked links open normally if the href
property is present, and all the regular properties (such as className
and style
) can simply be set on the <A>
component. Here is the code for the component along with comments that walk through the code:
import React from 'react';
// This <A/> component replaces <a href=""></a> links.
export default class A extends React.Component {
static propTypes = {
gacategory: PropTypes.string.isRequired,
href: PropTypes.string,
onClick: PropTypes.func
};
handleClick = () => {
// We handle onClick events by first running our analytics code
console.log("Fire off the analytics event: ", this.props.gacategory)
// Then we can run the child's onClick code
if(this.props.onClick) this.props.onClick();
}
render(){
let props = {};
// We have to intercept the onClick event of the child so we can
// use our own onClick event before the childs
// event is fired. To do this we loop through all
// the props to exclude the childs onClick prop
Object.keys(this.props).map(key => {
if(key !== "onClick"){
const newProp = {}
newProp[key] = this.props[key]
props = Object.assign(newProp, props)
}
});
return (<a {...props} onClick={this.handleClick}>
{this.props.children}
</a>)
}
}
Here is how you use this component:
import {A} from './A';
// Links in the application can be replaced with <A> components.
// The component can take in props like `gacategory` which will be the
// Google analytics category
export default () => (
<A href="http://google.com"
target="_blank"
style={{fontSize:"30pt"}}
onClick={() => console.log('Get called after analytics')}
gacategory="analytics category">Test link.</A>
);
Now I simply need to go through converting <a onClick={this.showModal}>Show modal</a>
links to <A onClick={this.showModal} gacategory="modal category">Show modal</A>
Just an easy little hack I thought I’d share.