Hello. I am Paul Kinlan.

I lead the Chrome and the Open Web Developer Relations team at Google. Exploring the intersection of modern web design and future-facing technologies.

1 min read

Support during layoffs

I'm offering support to those affected by recent layoffs, including those at Google and across the tech industry. I can help with networking, introductions, LinkedIn recommendations, resume reviews, interview preparation, and just being a listening ear. I've been running support calls for over a year and want to continue helping as much as possible. My calendar is open for bookings if you think I can be of assistance.

Stay in the loop.

I'm trialing a newsletter. Join for monthly insights into web dev, Chrome, and the open web.

alternate_email

Get in touch

Open to chat about Chrome or Web development.

Book a consultation
4 min read

Using ML to Create a Simple Lighthouse Audit to Detect a Button

I created a Lighthouse audit that uses machine learning to detect if an anchor tag looks like a button. This involved training a TensorflowJS model, building a custom Lighthouse gatherer to capture high-resolution screenshots, and processing those screenshots to identify anchors styled as buttons. The audit highlights these anchors in the Lighthouse report. The code for the scraper, web app, and Lighthouse audit are available on GitHub. While there are edge cases, this project demonstrates the potential of using ML for visual inspection tasks in web development.
2 min read

Creating a Lighthouse Gatherer to generate high-res screenshots for your Audit

I needed higher resolution screenshots for an ML model to classify elements on a webpage, but the default Lighthouse screenshot was too compressed. So, I created a custom Lighthouse Gatherer using Puppeteer. This gatherer captures a full-page, high-resolution screenshot encoded as base64 and returns it along with the device pixel ratio. This was a fun little project, and the code is surprisingly concise. However, future Lighthouse versions may include higher-resolution screenshots, making this gatherer redundant.
3 min read

Creating a web app with Deno, Fresh and TensorflowJS

I built a web app using Deno, Fresh, and TensorFlowJS to classify images as links or buttons. The app uses a pre-trained ML model and allows users to drag and drop multiple images for classification. I encountered challenges with server-side rendering and islands, specifically with integrating a file-drop web component. I also documented the process of integrating the TensorFlowJS model, including model loading and prediction handling. The code is available on GitHub.
5 min read

Training the Button detector ML model

I trained a machine learning model to differentiate between buttons and links on web pages. Using a dataset of ~3000 button images and ~4000 link images, I trained a convolutional neural network (CNN) with added noise for better generalization. Preprocessing included grayscale conversion, dataset diversification with multilingual sites, and image compression. The model performed well in initial tests, correctly classifying button-like and link-like elements. Next, I'll build a web app for easier testing and a Lighthouse audit for website analysis.
5 min read

Button and Link Scraping for ML training

In this project, I'm working on an accessibility tool to detect links styled as buttons, a common issue that can confuse users. My approach involves scraping websites to gather images of buttons and links, and then training a machine learning model to distinguish between them. This post focuses on the scraping process using Puppeteer. I encountered challenges like occluded elements and smooth scrolling, which I addressed by checking for occlusion and disabling smooth scrolling. The next step is training the ML image classifier.
11 min read

Adding ActivityPub to your static site

I added ActivityPub support to my static Hugo blog hosted on Vercel. It now automatically announces new posts to followers on the Fediverse. Key challenges included implementing the ActivityPub protocol for a static site, handling WebFinger discovery, managing Follow/Unfollow requests, and sending signed HTTP requests. I used Vercel Serverless Functions for dynamic request handling and Firebase Firestore for storing follower data. Check out the code and follow me @paul@paul.kinlan.me to see it in action!
2 min read

Post Deploy Webhook for Vercel

I needed to find a way to send webhooks after a successful deployment on Vercel, which wasn't a built-in feature. Since Vercel integrations can listen for deployment events, I created one to solve this. It's a simple tool hosted on GitHub that lets you set up custom webhooks for your Vercel projects. It's not on the Vercel Marketplace, and it's more of a workaround until Vercel natively supports deployment webhooks. Check out the GitHub repo for instructions on setting it up with Firebase Firestore.
4 min read

Thoughts on a "Web Follow" protocol

Mastodon's cross-instance following is clunky. I propose a solution using the web+follow URL scheme, like mailto, to streamline following users on ActivityPub platforms. A user's home instance registers as a handler for web+follow. Clicking a web+follow link opens the home instance, redirecting to a /follow request on the target instance. This page uses a meta refresh tag to redirect to /resolve-app, which redirects back to web+follow: with the user's ID. This triggers the registered handler (if available), creating a seamless follow experience within the user's preferred app. If no handler is installed, the user remains on the target instance's follow page, preserving existing functionality.
3 min read

Using ML to improve developer experience.

This blog post explores how machine learning (ML) can enhance the developer experience. Inspired by Corridor Crew's use of ML in VFX, I initially brainstormed ways ML could automate tedious developer tasks, like accessibility improvements and performance optimization. I also considered ML's potential for generating layouts and images. The emergence of tools like GitHub Copilot and DALL-E-2 significantly impacted my thinking, especially regarding the future of software development and my role as a DevRel lead. Ultimately, the transformative power of GPT-Chat, demonstrated through its ability to generate webpage layouts and populate them with images based on simple prompts, left me questioning the future of my profession and considering the role I might play in training the next generation of AI tools.