Skip to content

Edvins Antonovs

Add social share buttons to Gatsby blog

In this short and sweet blog post, I will share how to implement social share buttons for your Gatsby blog. To simplify the implementation we will use react-share and react-feather packages.

I've implemented social share buttons for my blog. That's why I got inspired to write this blog post and share my approach.


Initial setup

Packages

I will make to the assumption that you already have a Gatsby blog up and running. So all you need to do is to add the next packages. If not - check out Gatsby starter themes.

1yarn add react-share react-feather

Short description of the packages we are going to use:

  • react-share is a package which contains social media share buttons and shares counts for React.
  • react-feather is a collection of simply beautiful open source icons based on Feather icon set for React.

Blog post template

My blog post template implementation may vary from yours. I will use the post template from the started theme which I used to build this blog.

This is how my post.js looks like before I've started the social share buttons implementation.

post.js
1// ...
2
3const px = [`32px`, `16px`, `8px`, `4px`];
4const shadow = px.map((v) => `rgba(0, 0, 0, 0.15) 0px ${v} ${v} 0px`);
5
6const Post = ({ data: { post } }) => {
7 const description = post.description ? post.description : post.excerpt;
8
9 return (
10 <Layout>
11 <SEO
12 title={post.title}
13 description={description}
14 image={post.banner ? post.banner.childImageSharp.resize.src : undefined}
15 pathname={post.slug}
16 canonicalUrl={post.canonicalUrl}
17 />
18
19 <Heading as="h1" variant="styles.h1">
20 {post.title}
21 </Heading>
22
23 <div
24 className="post-meta"
25 sx={{ color: `secondary`, mt: 3, a: { color: `secondary` }, fontSize: [1, 1, 2] }}
26 >
27 <div className="post-meta-share">{/* ... */}</div>
28 </div>
29
30 <section
31 sx={{
32 my: 5,
33 '.gatsby-resp-image-wrapper': { my: [4, 4, 5], boxShadow: shadow.join(`, `) },
34 variant: `layout.content`,
35 }}
36 >
37 <MDXRenderer>{post.body}</MDXRenderer>
38 </section>
39 </Layout>
40 );
41};
42
43// ...

Implementation

Implementing share buttons component

First of all, we will start with implementing <ShareButtons /> component, which we will use in the blog post template. We are doing this, to keep the code reusability to the highest possible level.

In my case I went with, I've gone with Facebook, Twitter, LinkedIn and Pocket buttons. But you can add any of the 19 buttons which react-share package offers.

share-buttons.js
1// ...
2
3import { Facebook, Twitter, Linkedin, Pocket } from 'react-feather';
4import {
5 FacebookShareButton,
6 LinkedinShareButton,
7 TwitterShareButton,
8 PocketShareButton,
9} from 'react-share';
10
11const ShareButtons = ({ url, title, description }) => (
12 <div className="post-meta-share-icons">
13 <FacebookShareButton url={url} quote={description}>
14 <Facebook strokeWidth={1.25} />
15 </FacebookShareButton>
16
17 <LinkedinShareButton url={url} title={title} summary={description}>
18 <Linkedin strokeWidth={1.25} />
19 </LinkedinShareButton>
20
21 <TwitterShareButton url={url} title={description}>
22 <Twitter strokeWidth={1.25} />
23 </TwitterShareButton>
24
25 <PocketShareButton url={url} title={description}>
26 <Pocket strokeWidth={1.25} />
27 </PocketShareButton>
28 </div>
29);
30
31// ...

Icon component (line 2) can be replaced with text or icon and text instead.

1<FacebookShareButton url={url} quote={description}>
2 <Facebook strokeWidth={1.25} />
3</FacebookShareButton>

Updating blog post template

Now, let's update the post.js and see our buttons in action!

Not all social share buttons will work localhost correctly. As an example, Facebook will throw an error while Twitter and LinkedIn should work fine.

post.js
1// ...
2
3const px = [`32px`, `16px`, `8px`, `4px`];
4const shadow = px.map((v) => `rgba(0, 0, 0, 0.15) 0px ${v} ${v} 0px`);
5
6const Post = ({ data: { post } }) => {
7 const url = typeof window !== 'undefined' ? window.location.href : '';
8 const description = post.description ? post.description : post.excerpt;
9
10 return (
11 <Layout>
12 <SEO
13 title={post.title}
14 description={description}
15 image={post.banner ? post.banner.childImageSharp.resize.src : undefined}
16 pathname={post.slug}
17 canonicalUrl={post.canonicalUrl}
18 />
19
20 <Heading as="h1" variant="styles.h1">
21 {post.title}
22 </Heading>
23
24 <div
25 className="post-meta"
26 sx={{ color: `secondary`, mt: 3, a: { color: `secondary` }, fontSize: [1, 1, 2] }}
27 >
28 <div className="post-meta-share">{/* ... */}</div>
29 </div>
30
31 <ShareButtons url={url} title={post.title} description={description} />
32
33 <section
34 sx={{
35 my: 5,
36 '.gatsby-resp-image-wrapper': { my: [4, 4, 5], boxShadow: shadow.join(`, `) },
37 variant: `layout.content`,
38 }}
39 >
40 <MDXRenderer>{post.body}</MDXRenderer>
41 </section>
42 </Layout>
43 );
44};
45
46// ...

To make it work, we do only two changes:

  1. Get the URL of the post (line 7)
  2. Render <ShareComponent /> component and pass url, title and description (line 53)

Adding styles

I've tried to keep the meta section and social share buttons to look as minimalistic as possible. Here are my styles for that section, but you can style it any way you like it.

1.post-meta-share-icons {
2 display: flex;
3 align-items: center;
4 margin-top: 16px;
5}
6
7.post-meta-share-icons button {
8 display: flex;
9 align-items: center;
10 margin-right: 10px;
11 transition: all 0.2s ease-out;
12}
13
14.post-meta-share-icons svg {
15 color: var(--theme-ui-colors-secondary, #5f6c80);
16}
17
18.post-meta-share-icons button:hover {
19 transform: scale(1.15);
20}
21
22.post-meta-share-icons button:focus {
23 outline: 0;
24}
25
26.post-meta-share-icons button:last-child {
27 margin-right: 0;
28}

See it in action

Social share buttons in Gatsby blog

Alternatively, you can open any post in my blog to see the social share buttons in the post header.

Appendix

Join the newsletter

For monthly notes on software development and entrepreneurship.

© 2021 by Edvins Antonovs. All rights reserved.