diff --git a/.eleventy.js b/.eleventy.js
index b256662..ca5b6d2 100644
--- a/.eleventy.js
+++ b/.eleventy.js
@@ -189,6 +189,13 @@ module.exports = function (eleventyConfig) {
return array.slice(0, n);
});
+ eleventyConfig.addFilter("starRating", function (rating) {
+ const full = Math.floor(rating);
+ const half = Math.floor(rating * 2) % 2 === 1;
+ const empty = 5 - full - (half ? 1 : 0);
+ return "★".repeat(full) + (half ? "½" : "") + "☆".repeat(empty);
+ });
+
eleventyConfig.addCollection("posts", function (collectionApi) {
return collectionApi.getFilteredByTag("posts");
});
diff --git a/_includes/layouts/weeknote.njk b/_includes/layouts/weeknote.njk
new file mode 100644
index 0000000..53271a6
--- /dev/null
+++ b/_includes/layouts/weeknote.njk
@@ -0,0 +1,153 @@
+---
+templateClass: tmpl-post
+---
+{% extends "layouts/base.njk" %}
+
+{% block coverImage %}
+{% if coverImage %}
+ {% set datePath = page.date | datePath %}
+ {% set coverImagePath = "/img/assets/" + datePath + "/" + coverImage %}
+
+{% endif %}
+{% endblock %}
+
+{% block extraArticleHeader %}
+ {% set wc = content | striptags | wordcount %}
+ {% set wPerMinute = (wc / 240) + 1 %}
+
+{% endblock %}
+
+{% set shareUrl = metadata.url + page.url %}
+
+{% block article %}
+
+{% if fitness %}
+
+ Fitness
+
+ Weight
+ {{ fitness.weight_start }}kg → {{ fitness.weight_end }}kg
+
+ ({{ (fitness.weight_end - fitness.weight_start) | round(1) }}kg)
+
+
+
+
+{% endif %}
+
+{% if films %}
+
+ Films
+
+ {% for film in films %}
+
+
+

+
+
+
+ {% endfor %}
+
+
+{% endif %}
+
+{% if music %}
+
+ Music
+ {% for session in music %}
+
+ {% endfor %}
+
+{% endif %}
+
+{% if sides %}
+
+ Sides
+
+ {% for project in sides %}
+
+
+
+ {% for item in project.items %}
+ -
+ {% if item.url %}{{ item.label }}
+ {% else %}{{ item.label }}{% endif %}
+
+ {% endfor %}
+
+
+ {% endfor %}
+
+
+{% endif %}
+
+
+ Life
+ {{ content | safe }}
+
+
+
+
+
+
+
+
+{% endblock %}
diff --git a/css/main.css b/css/main.css
index 2e31e04..4081413 100644
--- a/css/main.css
+++ b/css/main.css
@@ -1240,3 +1240,281 @@ a {
.category-micro { background: #555555; color: #fff; }
.category-aside { background: #888888; color: #fff; }
.category-weeknotes { background: #b8b8b8; color: #111; }
+
+/* ── Weeknote layout ────────────────────────────────────────── */
+
+.wn-section {
+ margin-bottom: 2.5rem;
+}
+
+.wn-section > h2 {
+ display: block;
+ text-align: left;
+ font-size: 0.7rem;
+ font-family: var(--font-family-base);
+ font-style: normal;
+ font-weight: 700;
+ text-transform: uppercase;
+ letter-spacing: 0.12em;
+ color: var(--primary);
+ margin-bottom: 1rem;
+ padding-top: 0;
+ padding-bottom: 0;
+}
+
+.wn-section > h2::before,
+.wn-section > h2::after {
+ display: none;
+}
+
+/* Fitness */
+.wn-weight-row {
+ display: flex;
+ align-items: center;
+ gap: 0.5em;
+ font-size: 0.95rem;
+ margin-bottom: 0.75rem;
+}
+
+.wn-weight-label {
+ font-weight: 600;
+}
+
+.wn-delta-down { color: var(--primary); }
+.wn-delta-up { color: #c0392b; }
+
+.wn-activities {
+ display: flex;
+ flex-wrap: wrap;
+ gap: 0.5rem;
+}
+
+.wn-activity-pill {
+ display: inline-flex;
+ align-items: center;
+ gap: 0.3em;
+ padding: 0.35em 0.75em;
+ border-radius: 999px;
+ font-size: 0.8rem;
+ font-weight: 600;
+ text-decoration: none;
+ color: #fff;
+ transition: opacity 0.15s ease;
+}
+
+.wn-activity-pill:hover {
+ opacity: 0.8;
+ text-decoration: none;
+ color: #fff;
+}
+
+.wn-activity-walk { background: #5a9e6f; }
+.wn-activity-swim { background: #3a7abf; }
+.wn-activity-elliptical { background: #8b5cf6; }
+.wn-activity-run { background: #e67e22; }
+
+.wn-activity-duration {
+ opacity: 0.8;
+ font-weight: 400;
+}
+
+/* Films */
+.wn-film-grid {
+ display: grid;
+ grid-template-columns: 1fr 1fr;
+ gap: 1rem;
+}
+
+.wn-film-card {
+ display: flex;
+ flex-direction: column;
+ border-radius: 8px;
+ overflow: hidden;
+ background: rgba(0, 0, 0, 0.04);
+ text-decoration: none;
+ color: inherit;
+ transition: transform 0.15s ease, box-shadow 0.15s ease;
+}
+
+.wn-film-card:hover {
+ transform: translateY(-2px);
+ box-shadow: 0 4px 16px rgba(0, 0, 0, 0.12);
+ text-decoration: none;
+}
+
+.wn-film-poster img {
+ width: 100%;
+ height: auto;
+ display: block;
+ aspect-ratio: 2/3;
+ object-fit: cover;
+}
+
+.wn-film-meta {
+ padding: 0.75rem;
+}
+
+.wn-film-title {
+ font-size: 0.95rem;
+ font-family: var(--font-family-heading);
+ font-style: italic;
+ margin: 0 0 0.25rem;
+ line-height: 1.3;
+}
+
+.wn-film-year {
+ font-style: normal;
+ opacity: 0.5;
+ font-size: 0.85em;
+}
+
+.wn-film-rating {
+ color: #f9c412;
+ font-size: 1rem;
+ letter-spacing: 0.05em;
+ margin-bottom: 0.35rem;
+}
+
+.wn-film-review {
+ font-size: 0.82rem;
+ font-style: italic;
+ color: #777;
+ margin: 0;
+ line-height: 1.45;
+}
+
+/* Music */
+.wn-music-session {
+ margin-bottom: 1.25rem;
+}
+
+.wn-music-session-header {
+ display: flex;
+ align-items: baseline;
+ gap: 0.6em;
+ margin-bottom: 0.5rem;
+}
+
+.wn-music-label {
+ font-weight: 700;
+ font-size: 0.9rem;
+}
+
+.wn-music-date {
+ font-size: 0.78rem;
+ color: #777;
+}
+
+.wn-track-pills {
+ display: flex;
+ flex-wrap: wrap;
+ gap: 0.4rem;
+}
+
+.wn-track-pill {
+ display: inline-flex;
+ align-items: center;
+ gap: 0.3em;
+ padding: 0.3em 0.65em;
+ border-radius: 999px;
+ background: rgba(61, 138, 94, 0.1);
+ border: 1px solid rgba(61, 138, 94, 0.25);
+ font-size: 0.75rem;
+ text-decoration: none;
+ color: inherit;
+ transition: background 0.15s ease;
+}
+
+.wn-track-pill:hover {
+ background: rgba(61, 138, 94, 0.22);
+ text-decoration: none;
+}
+
+.wn-track-artist {
+ font-weight: 600;
+}
+
+.wn-track-title {
+ opacity: 0.7;
+}
+
+/* Sides */
+.wn-sides-grid {
+ display: grid;
+ grid-template-columns: 1fr 1fr;
+ gap: 0.75rem;
+}
+
+.wn-side-card {
+ border: 1px solid rgba(0, 0, 0, 0.1);
+ border-radius: 8px;
+ padding: 0.85rem;
+}
+
+.wn-side-card-header {
+ display: flex;
+ align-items: center;
+ gap: 0.4em;
+ margin-bottom: 0.5rem;
+}
+
+.wn-side-emoji {
+ font-size: 1.1em;
+ line-height: 1;
+}
+
+.wn-side-name {
+ font-weight: 700;
+ font-size: 0.9rem;
+ color: var(--primary);
+}
+
+.wn-side-name:hover {
+ text-decoration: underline;
+}
+
+.wn-side-items {
+ list-style: none;
+ padding: 0;
+ margin: 0;
+ font-size: 0.82rem;
+}
+
+.wn-side-items li {
+ padding: 0.2em 0;
+ border-bottom: 1px solid rgba(0, 0, 0, 0.05);
+ line-height: 1.4;
+}
+
+.wn-side-items li:last-child {
+ border-bottom: none;
+}
+
+@media (max-width: 37.5em) {
+ .wn-film-grid,
+ .wn-sides-grid {
+ grid-template-columns: 1fr;
+ }
+}
+
+@media (max-width: 37.5em) {
+ .wn-film-card {
+ flex-direction: row;
+ align-items: flex-start;
+ }
+
+ .wn-film-poster {
+ flex: 0 0 90px;
+ }
+
+ .wn-film-poster img {
+ width: 90px;
+ height: 135px;
+ border-radius: 4px 0 0 4px;
+ }
+
+ .wn-film-meta {
+ flex: 1;
+ padding: 0.65rem;
+ }
+}
diff --git a/posts/weeknotes/weekly-2026-23.md b/posts/weeknotes/weekly-2026-23.md
new file mode 100644
index 0000000..b2b7570
--- /dev/null
+++ b/posts/weeknotes/weekly-2026-23.md
@@ -0,0 +1,227 @@
+---
+title: "Weeknotes 2026.23"
+date: 2026-06-07
+categories:
+ - "weeknotes"
+tags:
+ - "ldx3"
+ - "petals"
+ - "house-finesse"
+slug: "weekly-2026-23"
+description: "Week 23: LDX3 at The O2, PETALS Google SSO, House Finesse DJ sets, films, and the usual swimming and walks."
+layout: layouts/weeknote.njk
+
+fitness:
+ weight_start: 80.6
+ weight_end: 80.0
+ activities:
+ - type: walk
+ icon: "🚶"
+ distance_m: 1361
+ url: "http://www.strava.com/activities/18676664330"
+ - type: walk
+ icon: "🚶"
+ distance_m: 3079
+ url: "http://www.strava.com/activities/18679013708"
+ - type: swim
+ icon: "🏊"
+ distance_m: 915
+ duration_min: 29
+ url: "http://www.strava.com/activities/18701382829"
+ - type: elliptical
+ icon: "🏃"
+ distance_m: 6920
+ duration_min: 35
+ url: "http://www.strava.com/activities/18701398959"
+ - type: walk
+ icon: "🚶"
+ distance_m: 2775
+ url: "http://www.strava.com/activities/18724526704"
+ - type: walk
+ icon: "🚶"
+ distance_m: 2801
+ url: "http://www.strava.com/activities/18737832206"
+ - type: swim
+ icon: "🏊"
+ distance_m: 750
+ duration_min: 20
+ url: "http://www.strava.com/activities/18741830295"
+ - type: walk
+ icon: "🚶"
+ distance_m: 2831
+ url: "http://www.strava.com/activities/18779696597"
+ - type: walk
+ icon: "🚶"
+ distance_m: 3513
+ url: "http://www.strava.com/activities/18792827006"
+ - type: swim
+ icon: "🏊"
+ distance_m: 300
+ duration_min: 10
+ url: "http://www.strava.com/activities/18800346254"
+ - type: elliptical
+ icon: "🏃"
+ distance_m: 7242
+ duration_min: 35
+ url: "http://www.strava.com/activities/18800357426"
+ - type: walk
+ icon: "🚶"
+ distance_m: 2931
+ url: "http://www.strava.com/activities/18806875288"
+
+films:
+ - title: "Sinners"
+ year: 2025
+ rating: 1.5
+ review: "I don't get the hype. Vampire things always put me off, quite the waste of time."
+ poster: "https://a.ltrbxd.com/resized/film-poster/1/1/1/6/6/0/0/1116600-sinners-2025-0-600-0-900-crop.jpg"
+ url: "https://letterboxd.com/si/film/sinners-2025/"
+ - title: "Good Fortune"
+ year: 2025
+ rating: 2.5
+ review: "Easy watching with a fun cast."
+ poster: "https://a.ltrbxd.com/resized/film-poster/1/0/0/5/0/1/8/1005018-good-fortune-2025-0-600-0-900-crop.jpg"
+ url: "https://letterboxd.com/si/film/good-fortune-2025/"
+
+music:
+ - label: "House Finesse DJ Session"
+ date: "May 28"
+ tracks:
+ - artist: "Whitney Houston"
+ title: "I'm Your Baby Tonight (Yvonne Turner Remix)"
+ url: "https://open.spotify.com/track/5xSxxDiyhxOS00KLJKt9NR"
+ - artist: "La Fuente"
+ title: "Time To Go"
+ url: "https://open.spotify.com/track/073gmCXuSbUqYPAIVyIVt4"
+ - artist: "Sonan"
+ title: "Taking Us Higher"
+ url: "https://open.spotify.com/track/1y5AErdUv289F9zs8bbcRQ"
+ - artist: "ANOTR"
+ title: "Talk To You (ft. 54 Ultra)"
+ url: "https://open.spotify.com/track/0kl6Ozan3fuUdCl6TlB15v"
+ - artist: "Moon Boots"
+ title: "Get On Up"
+ url: "https://open.spotify.com/track/1Ifs7oc0gjWPDqD2MEFdi7"
+ - artist: "Kamma & Masalo"
+ title: "Can't Fake The Feeling"
+ url: "https://open.spotify.com/track/6Um8WBoZODMJFTXeQwl2Mo"
+ - artist: "Leyo"
+ title: "Safe To Say"
+ url: "https://open.spotify.com/track/6zjP0YVZnncoPd4uUzACMv"
+ - artist: "Mark Knight"
+ title: "Shut It Down"
+ url: "https://open.spotify.com/track/3JLcmhiMEa0A9i2KBdglsE"
+ - artist: "Groove Armada"
+ title: "Love's Theme"
+ url: "https://open.spotify.com/track/6x98PZzecLKDucRBL324qT"
+ - artist: "Prospa"
+ title: "Free Your Mind"
+ url: "https://open.spotify.com/track/6TWbY1dq8eYtFiMiGdBlOa"
+ - artist: "Jayda G"
+ title: "The Shiver"
+ url: "https://open.spotify.com/track/0ouWOf4W8331O6dt2GCW7A"
+ - artist: "Luuk Van Dijk"
+ title: "Everything"
+ url: "https://open.spotify.com/track/1BJyVpblYEmeYberEVmOWM"
+ - artist: "ANOTR"
+ title: "Hold On, Let Go"
+ url: "https://open.spotify.com/track/68tOdKX9bNXD2MCFVsE5OF"
+ - artist: "Honey Dijon"
+ title: "Satisfied"
+ url: "https://open.spotify.com/track/4J40gFNhRlukzy1MgLjeNt"
+ - label: "Gym Set"
+ date: "May 29"
+ tracks:
+ - artist: "Basement Jaxx"
+ title: "Jump N' Shout (Gorgon City Remix)"
+ url: "https://open.spotify.com/track/2pbtSI3CJXfAE9ekE5qowg"
+ - artist: "Calvin Harris"
+ title: "Satisfy"
+ url: "https://open.spotify.com/track/3AsOa3cNh8bqF4q1temSHE"
+ - artist: "FISHER"
+ title: "Favour"
+ url: "https://open.spotify.com/track/7oNqFOek4W2px8jzrK4BxF"
+ - artist: "Madonna"
+ title: "I Feel So Free (Peggy Gou Energy Mix)"
+ url: "https://open.spotify.com/track/5zZQc0Dgvz81P4BRt2jGE8"
+ - artist: "Franky Wah"
+ title: "Down For You (feat. Jyll)"
+ url: "https://open.spotify.com/track/5N0hLKYNwYhTLQsGyLz8As"
+ - artist: "Becky Hill"
+ title: "More! More! More!"
+ url: "https://open.spotify.com/track/7Bk9xGSArXDiMe5Jj2zSMo"
+ - artist: "ANOTR"
+ title: "Like It"
+ url: "https://open.spotify.com/track/0nm3gH1gu9bN2GzCdWwyUQ"
+ - label: "DJ Session"
+ date: "June 2"
+ tracks:
+ - artist: "Barry Can't Swim"
+ title: "Return To Bhibo"
+ url: "https://open.spotify.com/track/0b04O4aNqXhiUtHJcb6bcm"
+ - artist: "Sonan"
+ title: "Taking Us Higher"
+ url: "https://open.spotify.com/track/1y5AErdUv289F9zs8bbcRQ"
+ - artist: "ANOTR"
+ title: "Talk To You (ft. 54 Ultra)"
+ url: "https://open.spotify.com/track/0kl6Ozan3fuUdCl6TlB15v"
+ - artist: "Alok"
+ title: "I Wonder If You Know"
+ url: "https://open.spotify.com/track/3xk4DtJZKWMqREHQd8xsew"
+ - artist: "Jayda G"
+ title: "The Shiver"
+ url: "https://open.spotify.com/track/0ouWOf4W8331O6dt2GCW7A"
+ - artist: "Luuk Van Dijk"
+ title: "Everything"
+ url: "https://open.spotify.com/track/1BJyVpblYEmeYberEVmOWM"
+ - artist: "Alan Braxe"
+ title: "Intro (Fred Falke Remix)"
+ url: "https://open.spotify.com/track/5nxJbZFIHf8iGndx8eOJMa"
+ - artist: "Jayda G"
+ title: "All Day"
+ url: "https://open.spotify.com/track/20uABzxxuEjNVbMYgHUPa6"
+
+sides:
+ - name: "PETALS"
+ emoji: "🪸"
+ url: "https://usepetals.com"
+ items:
+ - label: "Google SSO launched"
+ url: "https://github.com/PETALS-team/app/pull/524"
+ - label: "Magic links shipped for existing users"
+ - label: "May 2026 newsletter sent"
+ - label: "Snapshot reverse grid order"
+ url: "https://github.com/PETALS-team/app/pull/527"
+ - label: "Snapshot Scheduling epic"
+ url: "https://github.com/PETALS-team/app/issues/529"
+ - label: "LDX3 promo postcards"
+ - name: "House Finesse"
+ emoji: "🎧"
+ url: "https://github.com/si/hf"
+ items:
+ - label: "HF326 with Taylan published"
+ url: "https://github.com/si/hf"
+ - label: "Moved to Cloudflare Workers"
+ url: "https://github.com/si/hf"
+ - name: "si.jobling.dev"
+ emoji: "💻"
+ url: "https://github.com/si/11ty"
+ items:
+ - label: "Cloudflare Pages migration"
+ url: "https://github.com/si/11ty"
+ - label: "World Cup 2026 calendar post"
+ url: "https://github.com/si/11ty"
+ - label: "Podnality portfolio post"
+ url: "https://github.com/si/11ty"
+ - name: "footballcal"
+ emoji: "⚽️"
+ url: "https://github.com/sportstimes/footballcal"
+ items:
+ - label: "World Cup 2026 calendar promo"
+---
+
+Up to London for **[LDX3 2026](http://foursquare.com/v/55e08615498eb6646e66471a)** at The O2 on June 2 — a day trip via Euston for one of the better engineering leadership conferences around. Day 2 had some genuine standouts: Ian Coldwater on why leaders need to be the psychological "adult in the room" when others won't be, Danit Nativ (Meta) on how AI is reshaping coding interviews and what that means for hiring, and Dominika Rogala's breakdown of the four dimensions of engineering manager burnout — exhaustion, emotional distance, reduced efficacy, and identity gap. Spent plenty of time on the floor networking and handing out PETALS quarterly planners, with some really useful conversations about team health metrics. Also relaunched the marketing site at [usepetals.com](https://usepetals.com) while I was there.
+
+**[On The Side](https://ontheside.network)** is a community for people working on projects alongside their day jobs — and we wrapped the week with one of our Friday after-hours chats. Topics ranged from Chad's coast-to-coast US skating trip and Woz printing his own money, to Trovster taking selfies with farm animals on a rural walk. Always one of the highlights of the week. If you've got something on the side, [come along](https://ontheside.network) — we meet Mondays and Fridays.
+
+A full Saturday shop on May 31 — recycling centre, M&S Foodhall, Boots, Sainsbury's, Margarets, and Lidl all in one loop around North Oxford. The Domino's on the Thursday evening was much better. Weight's nudging down: 80.6kg on June 1 to 80.0kg by June 5, helped by keeping the pool sessions and morning walks consistent even around the London travel day.