Social media buttons slow down website load time
Asked Answered
L

9

60

I'm creating a simple and fast website, and I'm trying to optimize the site as much as I can. I noticed that social media buttons are slowing down the website by quite a lot. I'm including the Facebook Like Button, Twitter Button and Google+ Button. So I ran a few tests:

Website without social media buttons, loading time 0.24s:

enter image description here

Website with social media buttons, loading time 1.38s:

enter image description here

Here is my code:

<div id="social">
    <!-- FB -->
    <div id="fb-root"></div>
    <script>(function(d, s, id) { var js, fjs = d.getElementsByTagName(s)[0]; if (d.getElementById(id)) return; js = d.createElement(s); js.id = id; js.src = "//connect.facebook.net/en_EN/all.js#xfbml=1&status=0"; fjs.parentNode.insertBefore(js, fjs); }(document, 'script', 'facebook-jssdk'));</script>
    <div class="fb-like" data-href="http://facebook.com/textsearcher" data-width="150" data-layout="button_count" data-show-faces="false" data-send="false"></div>
    <!-- TWITTER -->
    <a href="https://twitter.com/share" class="twitter-share-button" data-url="http://www.textsearcher.com/" data-hashtags="TextSearcher">Tweet</a>
    <script>!function(d,s,id){var js,fjs=d.getElementsByTagName(s)[0],p=/^http:/.test(d.location)?'http':'https';if(!d.getElementById(id)){js=d.createElement(s);js.id=id;js.src=p+'://platform.twitter.com/widgets.js';fjs.parentNode.insertBefore(js,fjs);}}(document, 'script', 'twitter-wjs');</script>
    <!-- G+ -->
    <div class="g-plusone" data-size="medium" data-href="http://www.textsearcher.com/"></div>
    <script type="text/javascript"> (function() { var po = document.createElement('script'); po.type = 'text/javascript'; po.async = true; po.src = 'https://apis.google.com/js/plusone.js'; var s = document.getElementsByTagName('script')[0]; s.parentNode.insertBefore(po, s); })(); </script>
</div>

So I tried few things to load these social buttons without them slowing website load time.

Loading buttons after one second delay via JavaScript:

setInterval(function(){
    $("#social").html("<!-- FB --><div id="fb-root"></div>.....");
},1000);

This did not help, buttons didn't load up properly and they were bugging.

Loading buttons after document is ready:

$(document).ready(function() {
    $("#social").html("<!-- FB --><div id="fb-root"></div>.....");
});

This did not help either. Buttons loaded just fine but website load time was still >1.00 seconds.

I'm running out of ideas. Any way to load them without slowing down website?

PS. Used Page load time plugin for chrome in those tests


SOLUTION:

Thanks to CodeMonkey for his answer, I eventually solved this problem by loading social buttons after entire page is loaded. I moved the necessary JavaScript code (for social media buttons) in a separate file to make my HTML/markup little bit cleaner.

JS (in a seperate file, social.js):

/* Facebook*/
(function(d, s, id) { var js, fjs = d.getElementsByTagName(s)[0]; if (d.getElementById(id)) return; js = d.createElement(s); js.id = id; js.src = "//connect.facebook.net/en_EN/all.js#xfbml=1&status=0"; fjs.parentNode.insertBefore(js, fjs); }(document, 'script', 'facebook-jssdk'));
/* Twitter */
!function(d,s,id){var js,fjs=d.getElementsByTagName(s)[0],p=/^http:/.test(d.location)?'http':'https';if(!d.getElementById(id)){js=d.createElement(s);js.id=id;js.src=p+'://platform.twitter.com/widgets.js';fjs.parentNode.insertBefore(js,fjs);}}(document, 'script', 'twitter-wjs');
/* G+ */
(function() { var po = document.createElement('script'); po.type = 'text/javascript'; po.async = true; po.src = 'https://apis.google.com/js/plusone.js'; var s = document.getElementsByTagName('script')[0]; s.parentNode.insertBefore(po, s); })(); 

HTML:

<script>
    $(window).bind("load", function() {
       $.getScript('js/social.js', function() {});
    });
</script>
<!-- FB -->
<div id="fb-root"></div>
<div class="fb-like" data-href="http://facebook.com/textsearcher" data-width="150" data-layout="button_count" data-show-faces="false" data-send="false"></div>
<!-- TWITTER -->
<a href="https://twitter.com/share" class="twitter-share-button" data-url="http://www.textsearcher.com/" data-hashtags="TextSearcher">Tweet</a>
<!-- G+ -->
<div class="g-plusone" data-size="medium" data-href="http://www.textsearcher.com/"></div>

So after this load timings were normal again, 0.24s:

Load timings

Lodicule answered 27/9, 2013 at 21:24 Comment(3)
You could simplify it with a simple HTTP GET, but it will require manual styling: hanselman.com/blog/…Avron
is there really any need to getElementsByTagName() ? I don't think so. Try using classes and/or id's instead.Nurture
You know all those 3 social media sites can use js.async=True tooScifi
D
41

You could try

$(window).load(function() {

instead of

$(document).ready(function() {

so it will wait until after your images and everything has loaded.

If that doesn't help, then I would suggest having them only appear on hover. Have a bunch of static images / CSS sprites, that get replaced when the user hovers over them.

If you don't want that extra step, and you have server access to install modules you can try google's mod pagespeed to defer the javascript for you https://developers.google.com/speed/pagespeed/module/filter-js-defer

If you don't have server access you can try the CDN route, Cloudflare's rocket loader is very interesting, I am testing it at the minute for similar reasons, and see ~ 33% speed increase http://www.cloudflare.com/features-optimizer

If that doesn't help you could try the old favourite of sticking the buttons at the bottom of the page and repositioning with CSS so they look higher up; that way you can have them where you want them but they don't seem to interfere with the page load time.

You could try simpler oldschool alternatives like here http://zurb.com/article/883/small-painful-buttons-why-social-media-bu

or see if service like http://www.addthis.com/ or http://www.sharethis.com/ work any faster for you

Of course the elephant in the room at this point is that to have the 3 main social media buttons on the page, and for it to only cost you a second - sadly seems quite good! They are deceptively complicated buttons that don't seem well optimised, google pagespeed insights finds something to complain about with all of them iirc.

Since you are taking a 100%+ speed hit, I would suggest some A/B testing to see if you really need them, i.e. for your site does being slower decrease traffic? Does having the share buttons bring in more traffic to warrant their presence?

Dint answered 31/10, 2013 at 13:30 Comment(3)
A lot of the time they add iframes which load a tone of additional content all of which hijacks and delays the loading of your images etc... So your advice to use window.load instead of document.ready is the best I've seen yet.Hematite
$(document).ready(function() { is the same as $(function(){Anta
@codemonkey google pagespeed is horrible. it will take weeks to optimize all images and one may think that afterwards all images will load super fast but nothing is like that. it will damage server and cant return to previous stage untill you clear all your caches and everythingElectrobiology
H
5

Here is an alternative solution for anyone with the same issue -- as long as you don't mind sacrificing showing the number of likes/shares/etc.

You can simply add links that send the visitor to the actual social network and open a sharing window with pre-filled URL and description.

The code is very simple and you can use any image or text you want, which will make it easier to fit the buttons in with your site's design.

<a href="https://www.facebook.com/sharer/sharer.php?u=URL" target="_blank">Share on Facebook</a>
<a href="https://twitter.com/intent/tweet?url=URL&text=TEXT&via=YOURTWITTERACCOUNTNAME" target="_blank">Tweet</a>
<a href="https://plus.google.com/share?url=URL" target="_blank">Share on Google+</a>

Simply replace URL with the URL of you website and TEXT with a short description.

This solution requires no JavaScript and is therefore extremely lightweight. You can use logos, icon font, simple text ("Share on Facebook").

I also wrote a blog post that covers many other social networks.

Hydrozoan answered 26/4, 2014 at 12:26 Comment(0)
G
4

The social widgets should not be slowing down your load time too much, unless they are blocking more important scripts that are waiting for the page to finish loading. The code you're using is asynchronous, which helps, but in most browsers this will still block the window.onload event. See Stoyan's post here for information about how you can load the JS SDK in a non-blocking way using iframes.

If that's too much, and you want to delay the SDK downloading or running (and speed it up once it does run), here is my recommendation:

First, either use a library like jQuery that provides a way to hook into the DOM being ready in a cross-platform fashion. Here is one implementation. Once you have your "DOM ready handler", you should do one of the following two things:

  1. Move the JS SDK loading code into your DOM ready handler.

  2. Take xfbml: true out of FB.init(...), if you have it (in this case, you don't), and take xfbml=1 out of the SDK URL. This prevents social widgets from being parsed and initialized immediately. Then, call FB.XFBML.parse() in your DOM ready handler. See the documentation here for that method. The best thing to do for performance would be to specifically call FB.XFBML.parse(document.getElementById('')) so that the SDK doesn't waste time going over the whole DOM.

Gilliland answered 27/10, 2013 at 23:57 Comment(0)
U
2

The plugin (social media button) load times will vary depending on a number of factors, including (but not limited to):

  • Your server's response time (Plugins don't load until your code tells them too.)
  • The user's internet speed (in this case, yours)
  • The distance to the social media website's server (for instance, Facebook's server could be located on the other side of the continent, creating latency)
  • The load time of the social media website altogether

This means that there is not much you can do besides make your code as optimized as possible.

Also, it is good practice to run your Javascript plugins after the document is ready, unless otherwise specified by the plugin documentation. The setInterval is not a good approach, as it doesn't know if all the page is ready to be modified or not. So please make sure to use the $(document).ready() approach for doing anything that modifies the page content.

Unsettle answered 28/9, 2013 at 12:42 Comment(1)
None of that answers in any way Ville's question. He/She already nows the limitations of HTTP and the internet connectivity etc. There is a solution and it is below by CodeMonkey - window.load... document ready will run before images etc, and since each of these widgets add a script which then writes an separate iframe they hijack the loading of assets and thus postpone the initial "all your stuff loaded"Hematite
G
1

Inside the scripts that load the social media, put "defer" in them.

<script defer src="http://api.facebook.com/....."></script>
Gasp answered 28/10, 2013 at 9:17 Comment(0)
C
1

Try to use async loading for Social init scripts:

<script async="async">...</script>
Cheap answered 28/10, 2013 at 18:51 Comment(0)
T
0

Most of the major social media buttons offer an asynchronous version of their JavaScript. You just have to scroll a little further down on the official documentation pages.

Tivoli answered 27/12, 2013 at 23:20 Comment(0)
V
0

Try putting your like button into reusable iframe and pass the url to like.

<iframe src="http://www.facebook.com/plugins/like.php?href=http%3A%2F%2Fphys.org" scrolling="no" frameborder="0" style="border:none; overflow:hidden; width:450px;" allowTransparency="true"></iframe> 
Validity answered 19/7, 2016 at 15:54 Comment(0)
A
0

If you came here to find solution how to load facebook social plugins faster - e.g. how to render them BEFORE window.onload() event occures (because of slow network on wifi / large image on page / ...) you may try my solution:

window.fbAsyncInit = function () {
    dispatchEvent(new Event('load'));
}

fbAsyncInit is called as soon as facebook sdk js file is loaded (e.g. fast) and you can fake social buttons to render earlier (before other resources like images are loaded) using custom load event dispatching. Be aware of consequences when you fire onload() event earlier depending on your other javascript code/libraries.

Another solution is to wrap your social plugin with sdk loading into iframe. FB API will not wait for window.onload of parent window and will render social plugins earlier.

Almondeyed answered 21/4, 2017 at 11:23 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.