A simple DIY GitHub page counter using Netlify Functions + Blobs. Each repo key maps to a count, rendered as a small SVG, with design inspired by retro websites like 'GeoCities' etc.
This is a project I created for my own use, and felt others might find it useful so have published it in case it's useful for others.
Once set up, simply add this in your project's README.md to embed a page view counter:

Changing the repo= key will create a new count automatically.
local-dev-test.html- Local-only test page fornetlify dev.netlify-counter/functions/pageviews.js- Netlify Function (counter + list endpoint + SVG renderer).netlify-counter/index.html- Minimal template for a public overview page.netlify-counter/edit-counts.html- Same-origin admin UI for editing blob counts.netlify-counter/netlify.toml- Functions config.
- Counts increment on each GET.
- Requests must originate from
github.com/<GITHUB_USER>/...,https://<GITHUB_USER>.github.io/, the same Netlify site host (same-origin), or GitHub Camo. Localhost is allowed for dev. - Admin upsert/delete requires same-origin requests (intended for
edit-counts.html). - Output is SVG by default (
DEFAULT_RESPONSE_MODE), with format toggle (DEFAULT_IMAGE_FORMAT) reserved for future non-SVG output.
Page counter embed (returns SVG):
/.netlify/functions/pageviews?repo=YOUR_REPO
NOTE: Pass optional param increment=0 if you want to render the SVG, but not increment the count.
List all repo counts (returns JSON):
/.netlify/functions/pageviews?action=list
Admin upsert/delete (same-origin only):
/.netlify/functions/pageviews?action=upsert
/.netlify/functions/pageviews?action=delete
- Node.js 18+ (or any recent LTS)
- Netlify CLI (
npm install -g netlify-cli) - A Netlify account + site
From the repo root:
cd netlify-counter
npm install
All commands below should be run from within the netlify-counter folder.
Edit netlify-counter/functions/pageviews.js, from there you'll need to set your GitHub username and can also configure some other settings on how the counter looks.
This project includes an example index.html you can use to create a 'repo counter' summary page.
If you don't want a summary page, deploy without index.html and you can still embed counters normally.
Run Netlify locally to test before deploying:
netlify dev
Open local-dev-test.html in a browser to load an example page counter. You can change the key to try different page counts.
With this, you can easily tweak/iterate how you want the counter to look as you edit pageviews.js.
Once setup is done, you can move to deployment. A draft/preview is recommended first:
netlify deploy
Netlify will provide a draft URL which you can then test embedding in one of your GitHub repos, or test viewing your summary page if you added one.
There's no credit cost for draft deployments, so you can do as many DRAFT deploys as you want until everything is working correctly.
Tip
If you create multiple drafts, each one will be left as a draft in your deployments. When finishing up, make sure to go to your Netlify control panel afterwards and you can delete each draft deploy from there.
When all is tested and working, deploy to production using the --prod flag:
netlify deploy --prod
Caution
Production deployments cost 15 credits each. Make sure you test before going to production deployment!
Following this, you should be able to 'set-and-forget' and things should "just work" if you've set everything up correctly.
A basic admin UI edit-counts.html is included. It's intended only for temporary or draft deployment, so you can set up or edit counts as needed. There is no security on it, so it's recommended to only use it on a draft deployment and then remove it.
To use, deploy and open /edit-counts.html from the same Netlify site. From here you can add/update/remove counts and repo keys.
Note
The blobs edited are the same for Production and Deploy sites.
If you want to customize how the counter looks, edit netlify-counter/functions/pageviews.js as follows.
Edit the DESIGN block in netlify-counter/functions/pageviews.js:
digitCount: total digits shown (left padded with zeros).digitWidth,digitHeight: size of each digit panel.digitGap,padding: spacing between digits and outer padding.background,panelColor,panelStroke: panel background + border colors.digitText: number color.fontFamily,fontSize: typeface + size for digits.
Tip: adjust digitWidth and fontSize together to avoid clipping.
At the top of pageviews.js:
DEFAULT_RESPONSE_MODEcan besvgorjson.DEFAULT_IMAGE_FORMATis currentlysvgonly (PNG/WEBP are placeholders; you'll need to add support for those if you need them).
The counter only responds when requests originate from:
github.com/<GITHUB_USER>/...https://<GITHUB_USER>.github.io/- same Netlify site host (same-origin)
- GitHub Camo (for README image proxies)
- localhost (for dev)
Update GITHUB_USER before deploying.
While intended for GitHub repos, project can be adapted to other websites by updating access rules accordingly.
The admin page (netlify-counter/edit-counts.html) uses:
action=upsert(POST{ repo, count })action=delete(POST{ repo })
These are same-origin only. Deploy the file only when you need to adjust counts, then remove it.
Caution
There is no security on the edit-counts.html page. It's not meant for permanent deployment!
The includednetlify-counter/index.html is a minimal example that uses /.netlify/functions/pageviews?action=list. You can customize its layout freely; keep the list request same-origin to avoid CORS issues.
If you find this project useful, I have a Ko-Fi page here if you'd like to show some support: https://ko-fi.com/Dteyn