{
  "$type": "site.standard.document",
  "content": {
    "$type": "site.standard.content.markdown",
    "text": "As a software engineer, it's rare to have an idea for a personal project and actually finish it. We have ideas all the\ntime, buy domains for them, and then never finish them. For me, I've had a brain block for coding that isn't work for\nlike 5 years. _Well, maybe_ that isn't completely true, but for the purposes of this post, let's just roll with it.\n\nAt work, I've been working a lot with Gatsby on a new site. One of our big metrics that we are tracking with this new\nsite we are building is [Google Page Speed Insights](https://developers.google.com/speed/pagespeed/insights/). For those that don't know, Page Speed\nInsights is a like a special version of [Google Lighthouse](https://developers.google.com/web/tools/lighthouse) that runs outside of Chrome's Dev Tools. It was\nduring one of these runs that I got an idea:\n\n> What if I made a GitHub badge so that I can check on this passively?\n\nI did some Googling and couldn't find any implementations of it and went to work.\n\n# Implementation\n\n[Page Speed Insights provides an API endpoint in the Go Google client][pagespeedonline] which is easy enough to use.\nI went ahead are wired it into a [Gin HTTP server][gin] (I probably could have done this using the stdlib, but I like\nGin's routing and middlewares). After I ran the Page Speed test, I reverse proxied to [shields.io][shields.io], which is\na service that can generate GitHub shield badges.\n\nThis took me an evening and I was able to fetch a Page Speed badge using the following Markdown.\n\n```markdown\n![eligundry.com Mobile Page Speed Insights](https://page-speed-shield.eligundry.com/mobile/https://eligundry.com)\n![eligundry.com Desktop Page Speed Insights](https://page-speed-shield.eligundry.com/desktop/https://eligundry.com)\n```\n\nLook at these badges!\n\nLooks pretty snazzy, though it takes around 30 seconds to run, time to add it to a README!\n\n# Results\n\n![Page Speed shield fails to load on GitHub](https://eligundry.com/../../assets/img/page-speed-shield/failure.png)\n\nAh man, it failed to load! I did some Googling and it turns out that [GitHub proxies all images through their camo\nservice which has a 4 second timeout][camo-timeout]. This is good for the end user (prevents tracking pixels on GitHub\nand images taking forever to load is bad UX), but terrible for my use case.\n\nšŸ¤” What if I cache it server side? The first Page Speed image load will take forever, but after that, we should be golden for\nthe cache lifetime. I added [Gin's caching middleware][gin-cache] and deployed. Sure enough, the first touch penalty was\naround 30 seconds but after that it loaded instantly! **Unfortunately**, GitHub's camo proxy does it's own caching (so\nthat it can be on a CDN close to your geographic location) and it's impossible for the second image load to work as\noutlined 😭.\n\n# Conclusion\n\nEven though this is an impossible project to get working as I envisioned, I'm really happy with how it turned out! The\n[code][repo] is pretty \"clean\" (though that is subjective and I cringed saying that).\n\n<GithubFile url=\"https://github.com/eligundry/page-speed-shield/blob/21b795baaaa3d02b24a7767456e1432dfeea9d5a/api/main.go\" />\n\nOne really cool thing I found while building this was this [server timing Gin middleware][gin-server-timing] for writing\n[`Server-Timing` headers][server-timing] to a response. This allowed me to see how long Page Speed Insights was taking\nin the Chrome Dev Tools!\n\n![Server-Timing headers in the Chrome Dev Tools](https://eligundry.com/../../assets/img/page-speed-shield/server-timing.png)\n\nIt's like having a mini-DataDog right in your browser!\n\n[page-speed-insights]: https://developers.google.com/speed/pagespeed/insights/\n[lighthouse]: https://developers.google.com/web/tools/lighthouse\n[pagespeedonline]: https://pkg.go.dev/google.golang.org/api/pagespeedonline/v5\n[gin]: https://github.com/gin-gonic/gin\n[shields.io]: https://shields.io/\n[camo-timeout]: https://github.com/badges/shields/issues/1568\n[gin-cache]: https://github.com/gin-contrib/cache\n[gin-server-timing]: https://github.com/p768lwy3/gin-server-timing\n[server-timing]: https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Server-Timing\n[repo]: https://github.com/eligundry/page-speed-shield/",
    "version": "1.0"
  },
  "description": "I wanted Google Page Speed Insights to work with GitHub badges, but latency stays undefeated.",
  "path": "/blog/google-page-speed-shield/",
  "publishedAt": "2021-06-21T05:00:00.000Z",
  "site": "https://eligundry.com",
  "tags": [
    "code"
  ],
  "textContent": "As a software engineer, it's rare to have an idea for a personal project and actually finish it. We have ideas all the\ntime, buy domains for them, and then never finish them. For me, I've had a brain block for coding that isn't work for\nlike 5 years. Well, maybe that isn't completely true, but for the purposes of this post, let's just roll with it.\n\nAt work, I've been working a lot with Gatsby on a new site. One of our big metrics that we are tracking with this new\nsite we are building is Google Page Speed Insights. For those that don't know, Page Speed\nInsights is a like a special version of Google Lighthouse that runs outside of Chrome's Dev Tools. It was\nduring one of these runs that I got an idea:\n\nWhat if I made a GitHub badge so that I can check on this passively?\n\nI did some Googling and couldn't find any implementations of it and went to work.\n\nImplementation\n\n[Page Speed Insights provides an API endpoint in the Go Google client][pagespeedonline] which is easy enough to use.\nI went ahead are wired it into a [Gin HTTP server][gin] (I probably could have done this using the stdlib, but I like\nGin's routing and middlewares). After I ran the Page Speed test, I reverse proxied to [shields.io][shields.io], which is\na service that can generate GitHub shield badges.\n\nThis took me an evening and I was able to fetch a Page Speed badge using the following Markdown.\n\nLook at these badges!\n\nLooks pretty snazzy, though it takes around 30 seconds to run, time to add it to a README!\n\nResults\n\nAh man, it failed to load! I did some Googling and it turns out that [GitHub proxies all images through their camo\nservice which has a 4 second timeout][camo-timeout]. This is good for the end user (prevents tracking pixels on GitHub\nand images taking forever to load is bad UX), but terrible for my use case.\n\nšŸ¤” What if I cache it server side? The first Page Speed image load will take forever, but after that, we should be golden for\nthe cache lifetime. I added [Gin's caching middleware][gin-cache] and deployed. Sure enough, the first touch penalty was\naround 30 seconds but after that it loaded instantly! Unfortunately, GitHub's camo proxy does it's own caching (so\nthat it can be on a CDN close to your geographic location) and it's impossible for the second image load to work as\noutlined 😭.\n\nConclusion\n\nEven though this is an impossible project to get working as I envisioned, I'm really happy with how it turned out! The\n[code][repo] is pretty \"clean\" (though that is subjective and I cringed saying that).\n\nOne really cool thing I found while building this was this [server timing Gin middleware][gin-server-timing] for writing\n[ headers][server-timing] to a response. This allowed me to see how long Page Speed Insights was taking\nin the Chrome Dev Tools!\n\nIt's like having a mini-DataDog right in your browser!\n\n[page-speed-insights]: https://developers.google.com/speed/pagespeed/insights/\n[lighthouse]: https://developers.google.com/web/tools/lighthouse\n[pagespeedonline]: https://pkg.go.dev/google.golang.org/api/pagespeedonline/v5\n[gin]: https://github.com/gin-gonic/gin\n[shields.io]: https://shields.io/\n[camo-timeout]: https://github.com/badges/shields/issues/1568\n[gin-cache]: https://github.com/gin-contrib/cache\n[gin-server-timing]: https://github.com/p768lwy3/gin-server-timing\n[server-timing]: https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Server-Timing\n[repo]: https://github.com/eligundry/page-speed-shield/",
  "title": "Blogging My Failures: Google Page Speed Insights Shield",
  "updatedAt": "2025-02-12T02:34:47.000Z"
}