1<!doctype html> 2<html lang="en"> 3 <head> 4 <meta charset="utf-8"> 5 <meta name="viewport" content="width=device-width, initial-scale=1.0"> 6 <title>James Leighton</title> 7 <meta name="description" content="James, a techie who likes taking photos, birdwatching, reading, contributing to OpenBenches, and playing video games (with varying success)."> 8 <link rel="canonical" href="https://www.jamesleighton.com/blog/"> 9 <link rel="alternate" href="/feed/index.xml" type="application/atom+xml" title="James Leighton"> 10 <link rel="icon" href="/favicon.png" type="image/png"> 11 <link rel="apple-touch-icon" href="/apple-touch-icon.png"> 12 <meta property="og:type" content="website"> 13 <meta property="og:site_name" content="James Leighton"> 14 <meta property="og:locale" content="en"> 15 <meta property="og:title" content="James Leighton"> 16 <meta property="og:description" content="James, a techie who likes taking photos, birdwatching, reading, contributing to OpenBenches, and playing video games (with varying success)."> 17 <meta property="og:url" content="https://www.jamesleighton.com/blog/"> 18 <meta property="og:image" content="https://www.jamesleighton.com/img/WhdzdOPic--512.jpeg"> 19 <meta name="twitter:card" content="summary_large_image"> 20 <meta name="twitter:title" content="James Leighton"> 21 <meta name="twitter:description" content="James, a techie who likes taking photos, birdwatching, reading, contributing to OpenBenches, and playing video games (with varying success)."> 22 <meta name="twitter:image" content="https://www.jamesleighton.com/img/WhdzdOPic--512.jpeg"> 23 24 <link rel="preconnect" href="https://semaj.pythonanywhere.com"> 25 <link href="mailto:[email protected]" rel="me"> 26 <link rel="me" href="https://social.lol/@semaj"> 27 <link rel="webmention" href="https://webmention.io/www.jamesleighton.com/webmention"> 28 <link rel="authorization_endpoint" href="https://indieauth.com/auth"> 29 <link rel="me" href="https://web.brid.gy/r/https://www.jamesleighton.com"> 30 31 32 33 <style>/* This is an arbitrary CSS string added to the bundle */ 34:root{--font-family:Verdana,Geneva,"DejaVu Sans",Arial,"Helvetica Neue",Helvetica,sans-serif;--font-family-monospace:ui-monospace,Consolas,Menlo,Monaco,"Andale Mono WT","Andale Mono","Lucida Console","Lucida Sans Typewriter","DejaVu Sans Mono","Bitstream Vera Sans Mono","Liberation Mono","Nimbus Mono L","Courier New",Courier,monospace}:root{--color-gray-20:#e2e2e2;--color-gray-50:#c0c0c0;--color-gray-90:#444444;--page-background:#e4dcca;--page-background-image:radial-gradient(circle, rgba(43, 33, 24, 0.10) 1px, transparent 1.6px);--background-color:#fffdf7;--heading-color:#2b2118;--text-color:#3a2f26;--text-color-link:#e8590c;--text-color-link-active:#ff6a00;--text-color-link-visited:#b34a10;--code-background-color:#f3ede1;--code-color:#2b2118;--blockquote-color:#55483c;--accent:#d9631e;--accent-contrast:#2b2118;--border-strong:#d9631e;--border-soft:#ddd2c0;--surface:#f6efe2;--sidebar-width:220px;--content-max-width:960px;--syntax-tab-size:2}@media (prefers-color-scheme:dark){:root{--color-gray-20:#3a3a3a;--color-gray-50:#7a7a7a;--color-gray-90:#d6d6d6;--page-background:#15130f;--page-background-image:radial-gradient(circle, rgba(241, 233, 218, 0.08) 1px, transparent 1.6px);--background-color:#24201a;--heading-color:#f1e9da;--text-color:#d8cdb9;--text-color-link:#ff8a3d;--text-color-link-active:#ffab6b;--text-color-link-visited:#d98a55;--code-background-color:#17140f;--code-color:#ece3d2;--blockquote-color:#c7bba5;--accent:#e2782f;--accent-contrast:#1b1712;--border-strong:#e2782f;--border-soft:#3a332a;--surface:#2c2620}}::selection{background:var(--accent);color:var(--accent-contrast)}:focus-visible{outline:2px solid var(--accent);outline-offset:2px}*{box-sizing:border-box}@view-transition{navigation:auto}body,html{padding:0;margin:0;font-family:var(--font-family);color:var(--text-color);background-color:var(--page-background);background-image:var(--page-background-image);background-size:18px 18px}html{overflow-y:scroll}body{line-height:1.6}.page-frame{max-width:var(--content-max-width);margin:0 auto;background:var(--background-color);border:1px solid var(--border-soft);border-width:0 1px}@media (min-width:600px) and (max-width:1400px){.page-frame{max-width:100%;border-width:0}}.layout-grid{display:grid;grid-template-columns:1fr;gap:2rem;padding:1.5rem 1rem 1rem}@media (min-width:600px){.layout-grid{grid-template-columns:1fr var(--sidebar-width);align-items:start}}h1,h2,h3,h4,h5,h6{color:var(--heading-color);font-weight:600}b,strong{color:var(--heading-color)}hr{border:0;border-top:1px solid var(--border-soft)}blockquote{border-left:3px solid var(--border-soft);color:var(--blockquote-color);padding-left:20px;font-style:italic;margin-left:0}
34.visually-hidden:not(:focus):not(:active){clip:rect(0 0 0 0);clip-path:inset(50%);height:1px;overflow:hidden;position:absolute;white-space:nowrap;width:1px}img{max-width:100%}img[width][height]{height:auto}img[src$=".svg"]{width:100%;height:auto;max-width:none}iframe:not(.letterbird-embed),video{width:100%;height:auto}iframe:not(.letterbird-embed){aspect-ratio:16/9}p:last-child{margin-bottom:0}p{line-height:1.5}.post-content p{hyphens:auto}li{line-height:1.5}a[href]{color:var(--text-color-link);text-decoration:underline;text-underline-offset:3px;text-decoration-thickness:1px}a[href]:visited{color:var(--text-color-link-visited)}a[href]:active,a[href]:hover{color:var(--text-color-link-active)}a[href]:has(img):hover{background:0 0;color:inherit}footer{padding:1rem;text-align:center}main{min-width:0}main :first-child,main :first-child.visually-hidden+*{margin-top:0}header{border-bottom:1px solid var(--border-soft)}#skip-link{text-decoration:none;background:var(--background-color);color:var(--text-color);padding:.5rem 1rem;border:1px solid var(--border-strong);border-radius:2px}#skip-link.visually-hidden:focus{position:absolute;top:1rem;left:1rem;z-index:999}.links-nextprev{display:flex;justify-content:space-between;gap:.5em 1em;list-style:"";border-top:1px solid var(--border-soft);padding:1em 0}.links-nextprev>*{flex-grow:1}.links-nextprev-next{text-align:right}.challenge-progress{margin-top:1.5em;padding-top:1em;border-top:1px solid var(--border-soft);font-size:.9em}.challenge-progress p{margin:0 0 .4em}.challenge-track{width:100%;height:10px;background:var(--surface);border:1px solid var(--border-soft);border-radius:999px;overflow:hidden}.challenge-bar{height:100%;background:var(--accent);border-radius:inherit;transition:width .4s ease}.webmentions{margin-top:1.5em;padding-top:1em;border-top:1px solid var(--border-soft);font-size:.9em}.webmention-howto{margin-bottom:1em}.webmention-howto summary{cursor:pointer;font-weight:600;color:var(--heading-color)}.webmention-howto p{margin:.6em 0}.webmention-summary{margin-bottom:1em}.webmention-summary p{margin:.4em 0 0;color:var(--text-color-secondary,var(--text-color))}.webmention-facepile{display:flex;flex-wrap:wrap;gap:.3em}.webmention-facepile img{width:2em;height:2em;border-radius:50%;object-fit:cover}.webmention-comments{list-style:none;margin:0;padding:0;display:flex;flex-direction:column;gap:1em}.webmention-comments li{display:flex;gap:.7em}.webmention-comments p{margin:.2em 0 0}.webmention-avatar{width:2.2em;height:2.2em;border-radius:50%;object-fit:cover;flex-shrink:0}.webmention-author{font-weight:600}.gallery-post li:has(img){list-style-type:none;text-align:center;margin-bottom:1em}.gallery-post li img{max-width:80%}.gallery{margin:2rem auto;padding:0;display:grid;grid-template-columns:1fr;gap:1.5rem;max-width:900px}@media (min-width:600px){.gallery{grid-template-columns:repeat(auto-fit,minmax(280px,1fr));justify-items:center}}.gallery figure{width:100%;margin:0;text-align:center}.gallery-item{all:unset;display:block;width:100%;cursor:zoom-in}.gallery img{display:block;width:100%;height:auto;margin:0 auto;border-radius:4px;border:1px solid var(--border-soft)}@media (min-width:600px){.gallery img{max-width:350px}}.gallery figcaption{margin-top:.5rem;font-size:.9rem;color:var(--text-color)}.cover-strip .gallery{display:flex;flex-wrap:wrap;gap:1rem;max-width:none;margin:1.5rem 0}.cover-strip .gallery figure{width:112px}@media (max-width:600px){.cover-strip .gallery figure{width:calc((100% - 2rem)/ 3)}}.cover-strip .gallery img{width:100%;aspect-ratio:1/1;object-fit:cover;object-position:top;border-radius:50%;max-width:none;cursor:zoom-in}.lightbox{position:fixed;inset:0;background:rgba(0,0,0,.85);display:flex;flex-direction:column;align-items:center;justify-content:center;opacity:0;pointer-events:none;transition:opacity .25s;z-index:9999}.lightbox.open{opacity:1;pointer-events:auto}.lightbox img{max-width:90vw!important;max-height:95vh!important;width:auto!important;height:auto!important}.lightbox .caption{margin-top:1rem;padding:.75rem 1rem;background:rgba(255,255,255,.55);backdrop-filter:blur(10px);border-radius:8px;color:#111;font-size:1rem;text-align:center;max-width:90vw}@media (prefers-color-scheme:dark){.lightbox .caption{background:rgba(0,0,0,.45);color:#f5f5f5}}.lightbox .close,.lightbox .nav{all:unset}.lightbox .nav{position:absolute;top:50%;transform:translateY(-50%);font-size:3rem;color:#fff;cursor:pointer;user-select:none;padding:0 1rem}.lightbox .prev{left:0}.lightbox .next{right:0}.lightbox .close{position:absolute;top:1rem;right:1rem;font-size:2rem;color:#fff;cursor:pointer;user-select:none}.table-scroll{overflow-x:auto;-webkit-overflow-scrolling:touch;margin:1em 0}.table-scroll table{margin:0;min-width:560px}table{margin:1em 0;width:100%;border-collapse:collapse}table td,table th{padding:4px 1em 4px 0;text-align:left;border-bottom:1px solid var(--border-soft)}table th{color:var(--heading-color);border-bottom:2px solid var(--border-strong)}code,pre{font-family:var(--font-family-monospace)}pre:not([class*=language-]){margin:.5em 0;line-height:1.375;-moz-tab-size:var(--syntax-tab-size);-o-tab-size:var(--syntax-tab-size);tab-size:var(--syntax-tab-size);-webkit-hyphens:none;-ms-hyphens:none;hyphens:none;direction:ltr;text-align:left;white-space:pre;word-spacing:normal;word-break:normal;overflow-x:auto;padding:1px 15px;background-color:var(--code-background-color);color:var(--code-color);border-radius:6px;border-left:3px solid var(--border-soft)}code{word-break:break-all;padding:2px 4px;background-color:var(--code-background-color);color:var(--code-color);border-radius:4px}pre code{padding:0;background:0 0;border-radius:0}header{display:flex;gap:1em;flex-wrap:wrap;justify-content:space-between;align-items:center;padding:1em}.home-link{display:flex;align-items:center;gap:.5em;flex-grow:1;font-size:1.4em;font-weight:700}.home-link:link:not(:hover){text-decoration:none}.header-avatar{flex:none;width:40px;height:40px;border-radius:50%;border:1px solid var(--border-soft)}.nav{display:flex;gap:.5em 1em;padding:0;margin:0;list-style:none}.nav-item{display:inline-block}.nav-item a[href]:not(:hover){text-decoration:none}.nav a[href][aria-current=page]{text-decoration:underline}.nav-wrap{position:relative}.nav-toggle-checkbox{position:absolute;clip:rect(0 0 0 0);clip-path:inset(50%);
34height:1px;width:1px;overflow:hidden;white-space:nowrap}.nav-menu-toggle{display:flex;align-items:center;gap:.4em;cursor:pointer;font-weight:500}.nav-toggle-checkbox:focus-visible~.nav-menu-toggle{outline:2px solid var(--border-strong);outline-offset:2px}.nav-menu-icon{display:inline-block;width:1.1em;height:.85em;background:linear-gradient(currentcolor,currentcolor) top/100% 2px no-repeat,linear-gradient(currentcolor,currentcolor) center/100% 2px no-repeat,linear-gradient(currentcolor,currentcolor) bottom/100% 2px no-repeat}@media (max-width:599px){.nav-toggle-checkbox~.nav{display:none}.nav-toggle-checkbox:checked~.nav{display:flex;position:absolute;right:0;top:100%;flex-direction:column;align-items:flex-start;gap:.25em;margin-top:.75em;padding:.75em 1em;background:var(--background-color);border:1px solid var(--border-soft);border-radius:4px;box-shadow:0 2px 8px rgba(0,0,0,.15);z-index:10}.nav-toggle-checkbox:checked~.nav .nav-item{display:block}}@media (min-width:600px){.nav-menu-toggle{display:none}.nav-toggle-checkbox~.nav{display:flex}}.postlist{list-style:none;padding:0;margin:0}.postlist-item{display:flex;flex-wrap:wrap;align-items:baseline;column-gap:.75em;padding:.7em 0;border-bottom:1px solid var(--border-soft)}.postlist-item:first-child{border-top:1px solid var(--border-soft)}.postlist-date{flex:0 0 auto;font-size:.8125em;font-variant-numeric:tabular-nums;color:var(--color-gray-90);word-spacing:-0.5px}.postlist-link{flex:1 1 auto;min-width:60%;font-size:1.1875em;font-weight:700;text-underline-position:from-font;text-underline-offset:0;text-decoration-thickness:1px}.postlist-item-active .postlist-link{font-weight:700}.postlist-excerpt{flex-basis:100%;margin:.3em 0 0;font-size:.9em;color:var(--text-color);opacity:.8}.postlist-tags{display:flex;flex-wrap:wrap;gap:.4em;list-style:none;padding:0;margin:0}.postlist-tags .post-tag{font-size:.75em;padding:0 .55em}.year-group{margin:1.5em 0}.year-group-summary{cursor:pointer;font-size:1em;font-weight:400;padding:.3em 0}.year-group-count{font-weight:400;color:var(--color-gray-90);font-size:.8em}.year-group[open] .year-group-summary{margin-bottom:.3em}.bookshelf-hero{display:flex;flex-wrap:wrap;gap:1.5em;margin:1.5em 0;padding-bottom:1.5em;border-bottom:1px solid var(--border-soft)}.bookshelf-hero-item{flex:1 1 260px;display:flex;align-items:center;gap:1em;text-decoration:none;color:inherit}.item-cover.bookshelf-hero-cover,.item-placeholder.bookshelf-hero-cover{width:140px;flex-shrink:0}.item-cover.bookshelf-hero-cover{box-shadow:0 6px 16px rgba(0,0,0,.18)}.bookshelf-hero-kicker{font-size:.75em;font-weight:700;letter-spacing:.05em;text-transform:uppercase;color:var(--accent)}.bookshelf-hero-title{display:block;font-size:1.3em;font-weight:700;color:var(--heading-color);margin:.2em 0 0}a.bookshelf-hero-title{text-decoration:none}a.bookshelf-hero-title:hover{color:var(--text-color-link-active);text-decoration:underline}.bookshelf-hero-meta{margin-top:.2em;opacity:.8}.shelf-grid{max-width:960px;margin:0 auto}.year-block{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:16px 10px}@media (min-width:600px){.year-block{grid-template-columns:repeat(3,minmax(0,1fr));gap:24px 18px}}.year-info{grid-column:1/-1;text-align:center;margin-bottom:10px}.progress-label{margin-top:4px;font-size:.9rem;opacity:.8}.item-card{display:block;position:relative;text-align:center;text-decoration:none;color:inherit;border-radius:10px}.item-title{font-weight:700;font-size:16px;margin:8px 0 0;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.item-author{font-size:14px;margin:0;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.bookshelf-hero-item picture,.item-card picture{display:contents}.item-cover{width:100%;aspect-ratio:2/3;object-fit:cover;border-radius:10px;box-shadow:0 4px 8px rgba(0,0,0,.1);transition:transform .15s ease,box-shadow .15s ease}.item-card:focus-visible .item-cover,.item-card:hover .item-cover{transform:translateY(-2px);box-shadow:0 6px 14px rgba(0,0,0,.18)}.item-placeholder{width:100%;aspect-ratio:2/3;display:flex;align-items:center;justify-content:center;text-align:center;padding:8px;box-sizing:border-box;font-size:2.5em;border-radius:10px;background:var(--surface);border:1px solid var(--border-soft)}.item-rating{color:var(--accent);font-size:20px;margin-top:4px}.pager{display:flex;align-items:center;justify-content:space-between;flex-wrap:wrap;gap:.75em;margin:1.5em 0;padding-top:1em;border-top:1px solid var(--border-soft)}.pager-disabled{color:var(--color-gray-90);opacity:.5}.pager-pages{display:flex;flex-wrap:wrap;gap:.4em;order:3;flex-basis:100%;justify-content:center}.pager-pages a{display:inline-flex;align-items:center;justify-content:center;min-width:1.75em;height:1.75em;padding:0 .4em;border:1px solid var(--border-soft);border-radius:999px;text-decoration:none}.pager-pages a.pager-current{background:var(--accent);color:var(--accent-contrast);border-color:var(--accent)}.webmention-like-pill{display:inline-flex;align-items:center;gap:.3em;color:var(--text-color);background:var(--surface);border:1px solid var(--border-soft);border-radius:999px;padding:0 .6em}.post-hits-pill{display:inline-flex;align-items:center;gap:.3em;color:var(--text-color);background:var(--surface);border:1px solid var(--border-soft);border-radius:999px;padding:0 .6em}.post-tag{display:inline-flex;align-items:center;justify-content:center;text-transform:capitalize;color:var(--text-color);background:var(--surface);border:1px solid var(--border-soft);border-radius:999px;padding:0 .6em}a[href].post-tag{color:var(--text-color);text-decoration:none}.post-tag:hover{border-color:var(--border-strong)}.tag-cloud{display:flex;flex-wrap:wrap;align-items:baseline;justify-content:center;gap:.2em .8em;list-style:none;padding:0;margin:0;text-align:center}.tag-cloud li{display:inline-flex}.tag-cloud-word{display:inline-flex;align-items:center;justify-content:center;min-width:24px;min-height:24px;color:var(--text-color);text-decoration:none;text-transform:capitalize;line-height:1.2;padding:.35em 0;margin:-.35em 0;transition:opacity .15s ease,color .15s ease}.tag-cloud-word:hover{opacity:1!important;color:var(--text-color-link-active);text-decoration:underline}.postlist-item>.post-tag{align-self:center}.post-metadata{display:inline-flex;flex-wrap:wrap;align-items:center;gap:.5em;list-style:none;padding:0;margin:0 0 1.5em}.post-metadata time{margin-right:1em}.post-metadata .bubbles-vote{margin-top:0}.post-metadata a.bubbles-vote-btn{--bt-fg:var(--text-color);
34--bt-accent:var(--text-color-link-active);align-items:center;gap:.3em;padding:.15em .65em;border:1px solid var(--border-soft);border-radius:999px;background:var(--surface);transition:border-color .15s ease,background-color .15s ease}.post-metadata a.bubbles-vote-btn::before{content:"\1FAE7";margin-right:.1em}.post-metadata a.bubbles-vote-btn:hover{border-color:var(--text-color-link-active);background:color-mix(in srgb,var(--text-color-link-active) 10%,var(--surface));text-decoration:none}.post-metadata .bubbles-vote-tri{font-size:.75em}.feed-card{display:block;max-width:100%;margin:1.5rem auto;border:1px solid var(--border-soft);border-radius:6px;overflow:hidden;background:var(--surface)}.feed-card-header{display:flex;align-items:center;gap:8px;padding:12px 14px}.feed-card-avatar{display:flex;align-items:center;justify-content:center;width:30px;height:30px;border-radius:50%;flex:none;font-size:15px;background:color-mix(in srgb,currentColor 15%,transparent)}.feed-card-label{font-weight:600;color:var(--heading-color)}.feed-card-date{margin-left:auto;font-size:.85em;opacity:.6}.feed-card-split{display:flex;flex-direction:column;align-items:center;text-align:center;gap:.75em;padding:14px;padding-top:10px}.feed-card-media{display:block;flex:none;width:35%;max-width:130px;height:auto;margin:0}.feed-card-body{min-width:0;padding:14px;padding-top:10px}.feed-card-split .feed-card-body{padding:0}@media (min-width:600px){.feed-card-split{flex-direction:row;text-align:left;gap:1em}.feed-card-media{flex:0 0 35%;width:100%}.feed-card-body{flex:1 1 auto}}.feed-card-body p{margin:0 0 .6em}.feed-card-body p:last-child{margin-bottom:0}.feed-card-body ul{margin:0;padding:0}.latest-posts-card .blog-posts{list-style:none;margin:0;padding:0}.latest-posts-card .blog-posts li+li{margin-top:1.5rem;padding-top:1.5rem;border-top:1px solid var(--border-soft)}.latest-posts-card .blog-posts li>span{display:block;font-size:.8125em;color:var(--color-gray-90);opacity:.7}.latest-posts-card .blog-posts li>a{display:block;font-size:1.1875em;font-weight:700;margin-top:.15rem}.latest-posts-card .blog-posts li>p{margin:.5rem 0 0;font-size:.95rem;line-height:1.5;opacity:.82}a.latest-photo-post{display:block;max-width:100%;margin:1.5rem auto;border:1px solid var(--border-soft);border-radius:6px;overflow:hidden;text-decoration:none;color:inherit;font:inherit;background:var(--surface)}a[href].latest-photo-post:hover{background:var(--surface);color:inherit;text-decoration:none}.latest-photo-post-header{display:flex;align-items:center;gap:8px;padding:12px 14px}.latest-photo-post-avatar{display:flex;align-items:center;justify-content:center;width:30px;height:30px;border-radius:50%;flex:none;font-size:15px;background:color-mix(in srgb,currentColor 15%,transparent)}.latest-photo-post-label{font-weight:600;color:var(--heading-color)}.latest-photo-post-date{margin-left:auto;font-size:.85em;opacity:.6}a.latest-photo-post img{display:block;width:100%;max-width:100%;height:auto;aspect-ratio:3/2;object-fit:cover;border:0}.latest-photo-post-body{padding:14px;padding-top:10px}.latest-photo-post-title{margin:0 0 4px;font-weight:600;color:var(--text-color-link);text-decoration:underline;text-underline-offset:3px;text-decoration-thickness:1px}a.latest-photo-post:hover .latest-photo-post-title{color:var(--text-color-link-active)}.latest-photo-post-caption{margin:0;font-size:.95em;color:var(--text-color);opacity:.75}a.nebula-embed{position:relative;display:block;max-width:100%;margin:1.5rem auto;border:1px solid var(--border-soft);border-radius:6px;overflow:hidden;text-decoration:none;color:inherit;font:inherit;background:var(--surface)}a[href].nebula-embed:hover{background:var(--surface);color:inherit;text-decoration:none}.nebula-embed-thumb{display:block;width:100%;max-width:100%;height:auto;aspect-ratio:16/9;object-fit:cover;border:0}.nebula-embed-play{position:absolute;top:14px;left:14px;display:flex;align-items:center;justify-content:center;width:44px;height:44px;border-radius:50%;background:color-mix(in srgb,var(--heading-color) 55%,transparent);color:#fff;font-size:16px}
34.nebula-embed-body{display:block;padding:14px}.nebula-embed-title{display:block;margin:0 0 4px;font-weight:600;color:var(--text-color-link);text-decoration:underline;text-underline-offset:3px;text-decoration-thickness:1px}a.nebula-embed:hover .nebula-embed-title{color:var(--text-color-link-active)}.nebula-embed-meta{display:block;font-size:.85em;color:var(--text-color);opacity:.7}.currently{margin:0;padding:0;list-style:none}.currently-row+.currently-row{margin-top:.6em}.currently-icon{margin-right:.3em}.currently-label{font-weight:600;color:var(--heading-color)}.currently-label::after{content:":"}.currently-value{display:block;opacity:.85}.page-jump{display:flex;flex-wrap:wrap;gap:.5em 1em;margin:1.5em 0 0;font-size:.9em}.now-grid{display:grid;grid-template-columns:repeat(auto-fill,minmax(260px,1fr));gap:1.5em;margin:1.5em 0}.now-card{overflow:hidden;border:1px solid var(--border-soft);border-radius:10px;background:var(--surface)}.now-card picture{display:contents}.now-card-art,.now-card-placeholder{display:block;width:100%;aspect-ratio:1/1;object-fit:cover;object-position:top}.now-card-placeholder{display:flex;align-items:center;justify-content:center;font-size:3em;background:var(--page-background)}.now-card-body{padding:.5em .8em .8em}.now-card-kicker{font-size:.7em;font-weight:600;letter-spacing:.05em;text-transform:uppercase;opacity:.7}.now-card-title{font-size:.95em;font-weight:400;color:var(--text-color);margin-top:.1em}.now-card-meta{margin-top:.1em;font-size:.85em;opacity:.7}.now-refreshed{margin-top:2em;font-size:.85em;opacity:.7}.year-nav{display:flex;gap:1em;margin:2.5em 0 1em}.year-nav-next{margin-left:auto}.history-bubbles{display:flex;flex-wrap:wrap;justify-content:center;align-items:center;gap:.5em;margin:1.5em 0}.history-bubble{display:block;padding:0;border:none;background:0 0;cursor:pointer;line-height:0;border-radius:50%;transition:transform .15s ease}.history-bubble:focus-visible,.history-bubble:hover{transform:scale(1.06)}.history-bubble:focus-visible{outline:2px solid var(--link-color,currentColor);outline-offset:3px}.history-bubble-art-wrap{position:relative}.history-bubble-art-wrap picture{display:contents}.history-bubble .item-placeholder,.history-bubble-art{display:block;border-radius:50%;object-fit:cover;border:1px solid var(--border-soft)}.history-bubble .item-placeholder{display:flex;align-items:center;justify-content:center;background:var(--surface)}.history-bubble-sm .history-bubble-art-wrap{width:80px;height:80px}.history-bubble-md .history-bubble-art-wrap{width:120px;height:120px}.history-bubble-lg .history-bubble-art-wrap{width:160px;height:160px}.history-bubble .item-placeholder,.history-bubble-art{width:100%;height:auto;aspect-ratio:1/1}.history-bubble-sm .item-placeholder{font-size:1.6em}.history-bubble-md .item-placeholder{font-size:2.2em}.history-bubble-lg .item-placeholder{font-size:2.8em}.history-bubble-badge{position:absolute;bottom:-.2em;right:-.2em;background:var(--surface);border:1px solid var(--border-soft);border-radius:50%;width:1.8em;height:1.8em;display:flex;align-items:center;justify-content:center;font-size:.9em}.history-modal{position:fixed;inset:0;background:rgba(0,0,0,.85);display:flex;align-items:center;justify-content:center;padding:1.5rem;opacity:0;pointer-events:none;transition:opacity .2s;z-index:9999}.history-modal.open{opacity:1;pointer-events:auto}.history-modal-inner{display:flex;flex-direction:column;align-items:center;gap:1rem;max-width:90vw;max-height:90vh}.history-modal-img{display:block;max-width:min(560px,90vw);max-height:70vh;width:auto;height:auto;border-radius:8px;object-fit:contain}.history-modal-img[hidden]{display:none}.history-modal-text{text-align:center;color:#f5f5f5;max-width:32ch}.history-modal-kicker{font-size:.85rem;text-transform:uppercase;letter-spacing:.05em;opacity:.75}.history-modal-title{font-size:1.3rem;font-weight:600;margin:.2em 0;line-height:1.2}.history-modal-detail{font-size:.95rem;opacity:.85}.history-modal-meta{font-size:.9rem;opacity:.7;margin-top:.2em}.history-modal-close{position:absolute;top:1rem;right:1rem;background:0 0;border:none;font-size:2rem;line-height:1;color:#fff;cursor:pointer;padding:.25rem .5rem}.sidebar{display:flex;flex-direction:column;gap:1.5rem;min-width:0}.sidebar-widget{min-width:0;border:1px solid var(--border-soft);border-radius:4px;background:var(--surface);padding:.75em 1em}.sidebar-widget-label{display:block;margin:0 0 .6em;font-size:.8em;font-weight:700;text-transform:uppercase;letter-spacing:.04em;color:var(--heading-color)}.sidebar-about{display:flex;flex-direction:column;align-items:center;text-align:center;gap:.5em}.sidebar-about img{width:64px;
34height:64px;border-radius:50%;border:1px solid var(--border-soft)}.sidebar-about p{margin:0;font-size:.9em}.badge-row{display:flex;flex-wrap:wrap;gap:.5em}.badge{display:inline-flex;align-items:center;gap:.3em;border:1px solid var(--border-soft);background:var(--background-color);color:var(--text-color);padding:.25em .6em;border-radius:3px;font-size:.8em}a.badge{text-decoration:none}.badge:hover{border-color:var(--border-strong);color:var(--text-color);background:var(--background-color)}button.badge{appearance:none;-webkit-appearance:none;font-family:inherit;margin:0;cursor:pointer;color:var(--text-color-link);text-decoration:none}button.badge:hover{color:var(--text-color-link-active)}.copy-dialog{max-width:32em;border:1px solid var(--border-soft);border-radius:4px;background:var(--surface);color:var(--text-color);padding:1.25em}.copy-dialog::backdrop{background:rgba(0,0,0,.5)}.copy-dialog p{margin:0 0 1em}.copy-field{display:flex;gap:.5em;margin:0 0 1em}.copy-field input{flex:1;min-width:0;border:1px solid var(--border-soft);border-radius:3px;background:var(--background-color);color:var(--text-color);padding:.25em .6em;font:inherit;font-size:.9em}.badge-group{gap:.5em;white-space:nowrap}.badge-group a{color:inherit;text-decoration:none}.badge-group a:hover{color:var(--text-color-link-active)}.sidebar .tag-cloud{font-size:.8em;justify-content:flex-start;text-align:left}.sidebar .tag-cloud li{min-width:0;max-width:100%}.sidebar .tag-cloud-word{display:inline-block;max-width:100%;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;vertical-align:bottom}.tag-cloud-more{margin-top:.7em}.sidebar-recent-posts .postlist-item{padding:.4em 0}.sidebar-recent-posts .postlist-link{font-size:1em}.sidebar-recent-posts .postlist-excerpt,.sidebar-recent-posts .postlist-tags{display:none}</style> 35 36 </head> 37 <body><a href="https://www.jamesleighton.com/cdn-cgi/content?id=i3UJAiRr_HpITjUFcslkCu45pGIRg7rEmOySTJ5iAiw-1791412598.4756835-1.2.1.1-uFCJkiEO6LfGYZ1StXOOEw3BRW3KoE.pHQ3Td8c6cDoJ5bomJDiCl3NaFK7BItv1" aria-hidden="true" rel="nofollow noopener" style="display: none !important; visibility: hidden !important"></a> 38 <a href="#main" id="skip-link" class="visually-hidden">Skip to main content</a> 39 40 <div class="page-frame"> 41 42 <header> 43 <a href="/" class="home-link"> 44 <img src="/img/N0GPRLZROg-40.webp" alt="" class="header-avatar" width="40" height="40" loading="lazy" decoding="async"> 45 <span>James Leighton</span> 46 </a> 47 <nav class="nav-wrap" aria-label="Primary"> 48 <h2 class="visually-hidden" id="top-level-navigation-menu">Top level navigation menu</h2> 49 <input type="checkbox" id="nav-toggle" class="nav-toggle-checkbox"> 50 <label for="nav-toggle" class="nav-menu-toggle" role="button" aria-expanded="false" aria-controls="primary-nav"> 51 <span aria-hidden="true" class="nav-menu-icon"></span> 52 Menu 53 </label> 54 <ul class="nav" id="primary-nav"> 55 <li class="nav-item"><a href="/">Home</a></li> 56 <li class="nav-item"><a href="/about/">About</a></li> 57 <li class="nav-item"><a href="/blog/" aria-current="page">Blog</a></li> 58 <li class="nav-item"><a href="/week-notes/">Week Notes</a></li> 59 <li class="nav-item"><a href="/random/">Random</a></li> 60 <li class="nav-item"><a href="/now/">Now</a></li> 61 <li class="nav-item"><a href="/guestbook/">Guestbook</a></li> 62 </ul> 63 </nav> 64 </header> 65 66 <div class="layout-grid"> 67 <main id="main" data-pagefind-body=""> 68 <heading-anchors> 69 <h1 id="blog">Blog</h1> 70 71<div id="blog-default"> 72 73 74 75<ol class="postlist" aria-label="Blog posts"> 76 <li class="postlist-item"> 77 <h2 class="postlist-title" id="week-notes-2026-40"><a href="/week-notes/2026/40/" class="postlist-link">Week Notes - 2026-40</a></h2> 78 <p class="postlist-excerpt">My week notes for week 40 of 2026</p> 79 <time class="postlist-date" datetime="2026-10-05"><span class="visually-hidden">Published </span>5 Oct 2026</time> 80 <ul class="postlist-tags" aria-label="Tags"> 81 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 82 <li><a href="/tags/week-note/" class="post-tag">week note</a></li> 83 </ul> 84 </li> 85 <li class="postlist-item"> 86 <h2 class="postlist-title" id="september-in-numbers"><a href="/2026/10/september-in-numbers/" class="postlist-link">September in Numbers</a></h2> 87 <p class="postlist-excerpt">I had Claude crunch the numbers from my time tracking system for this one - here is September 2026 in numbers. September at a glance Metric September August Change Reading 17h 18m 16h 50m +28m Gamingâ¦</p> 88 <time class="postlist-date" datetime="2026-10-02"><span class="visually-hidden">Published </span>2 Oct 2026</time> 89 <ul class="postlist-tags" aria-label="Tags"> 90 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 91 <li><a href="/tags/life/" class="post-tag">life</a></li> 92 </ul> 93 </li> 94 <li class="postlist-item"> 95 <h2 class="postlist-title" id="week-notes-2026-39"><a href="/week-notes/2026/39/" class="postlist-link">Week Notes - 2026-39</a></h2> 96 <p class="postlist-excerpt">My week notes for week 39 of 2026</p> 97 <time class="postlist-date" datetime="2026-09-28"><span class="visually-hidden">Published </span>28 Sep 2026</time> 98 <ul class="postlist-tags" aria-label="Tags"> 99 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 100 <li><a href="/tags/week-note/" class="post-tag">week note</a></li> 101 </ul> 102 </li> 103 <li class="postlist-item"> 104 <h2 class="postlist-title" id="week-notes-2026-38"><a href="/week-notes/2026/38/" class="postlist-link">Week Notes - 2026-38</a></h2> 105 <p class="postlist-excerpt">My week notes for week 38 of 2026</p> 106 <time class="postlist-date" datetime="2026-09-21"><span class="visually-hidden">Published </span>21 Sep 2026</time> 107 <ul class="postlist-tags" aria-label="Tags"> 108 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 109 <li><a href="/tags/week-note/" class="post-tag">week note</a></li> 110 </ul> 111 </li> 112 <li class="postlist-item"> 113 <h2 class="postlist-title" id="how-to-embed-youtube-videos-into-11ty"><a href="/2026/09/easily-embed-youtube-videos-into-11ty/" class="postlist-link">How to Embed Youtube Videos Into 11ty</a></h2> 114 <p class="postlist-excerpt">I was getting annoyed at having to manually copy Youtube's privacy preserving embed code each time I wanted to include a video in a post, so here is a simple shortcode for 11ty that does the heavyâ¦</p> 115 <time class="postlist-date" datetime="2026-09-17"><span class="visually-hidden">Published </span>17 Sep 2026</time> 116 <ul class="postlist-tags" aria-label="Tags"> 117 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 118 <li><a href="/tags/how-to/" class="post-tag">how to</a></li> 119 <li><a href="/tags/11ty/" class="post-tag">11ty</a></li> 120 </ul> 121 </li> 122 <li class="postlist-item"> 123 <h2 class="postlist-title" id="week-notes-2026-37"><a href="/week-notes/2026/37/" class="postlist-link">Week Notes - 2026-37</a></h2> 124 <p class="postlist-excerpt">My week notes for week 37 of 2026</p> 125 <time class="postlist-date" datetime="2026-09-14"><span class="visually-hidden">Published </span>14 Sep 2026</time> 126 <ul class="postlist-tags" aria-label="Tags"> 127 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 128 <li><a href="/tags/week-note/" class="post-tag">week note</a></li> 129 </ul> 130 </li> 131 <li class="postlist-item"> 132 <h2 class="postlist-title" id="a-new-day-for-my-blog"><a href="/2026/09/new-blog/" class="postlist-link">A New Day for My Blog</a></h2> 133 <p class="postlist-excerpt">I have switched my blog to a new platform. If you subscribe by RSS you probably didn't even notice! I've moved away from Bearblog despite it being an amazing platform because I found it constricting.â¦</p> 134 <time class="postlist-date" datetime="2026-09-09"><span class="visually-hidden">Published </span>9 Sep 2026</time> 135 <ul class="postlist-tags" aria-label="Tags"> 136 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 137 </ul> 138 </li> 139 <li class="postlist-item"> 140 <h2 class="postlist-title" id="week-notes-2026-36"><a href="/week-notes/2026/36/" class="postlist-link">Week Notes - 2026-36</a></h2> 141 <p class="postlist-excerpt">My week notes for week 36 of 2026</p> 142 <time class="postlist-date" datetime="2026-09-06"><span class="visually-hidden">Published </span>6 Sep 2026</time> 143 <ul class="postlist-tags" aria-label="Tags"> 144 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 145 <li><a href="/tags/week-note/" class="post-tag">week note</a></li> 146 </ul> 147 </li> 148 <li class="postlist-item"> 149 <h2 class="postlist-title" id="a-journey-through-nine-years-of-health-and-activity-data"><a href="/2026/09/a-journey-through-nine-years-of-data/" class="postlist-link">A Journey Through Nine Years of Health and Activity Data</a></h2> 150 <p class="postlist-excerpt">18 million steps, 23,000 hours of sleep, and zero missed days logged, the numbers show 2026 is officially my happiest year yet... How I analyse my life</p> 151 <time class="postlist-date" datetime="2026-09-01"><span class="visually-hidden">Published </span>1 Sep 2026</time> 152 <ul class="postlist-tags" aria-label="Tags"> 153 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 154 <li><a href="/tags/exist-io/" class="post-tag">exist.io</a></li> 155 <li><a href="/tags/life/" class="post-tag">life</a></li> 156 <li><a href="/tags/quantified-self/" class="post-tag">quantified self</a></li> 157 </ul> 158 </li> 159 <li class="postlist-item"> 160 <h2 class="postlist-title" id="week-notes-2026-35"><a href="/week-notes/2026/35/" class="postlist-link">Week Notes - 2026-35</a></h2> 161 <p class="postlist-excerpt">My week notes for week 35 of 2026</p> 162 <time class="postlist-date" datetime="2026-08-31"><span class="visually-hidden">Published </span>31 Aug 2026</time> 163 <ul class="postlist-tags" aria-label="Tags"> 164 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 165 <li><a href="/tags/week-note/" class="post-tag">week note</a></li> 166 </ul> 167 </li> 168 <li class="postlist-item"> 169 <h2 class="postlist-title" id="goals-for-september"><a href="/2026/08/goals-for-september/" class="postlist-link">Goals for September</a></h2> 170 <p class="postlist-excerpt">It's nearly a new month and here are the things I want to hold myself to through September Blogging Blogging first. I want to keep the week notes streak alive. I've managed 34 weeks in a row and itâ¦</p> 171 <time class="postlist-date" datetime="2026-08-30"><span class="visually-hidden">Published </span>30 Aug 2026</time> 172 <ul class="postlist-tags" aria-label="Tags"> 173 <li><a href="/tags/life/" class="post-tag">life</a></li> 174 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 175 </ul> 176 </li> 177 <li class="postlist-item"> 178 <h2 class="postlist-title" id="the-games-i-play"><a href="/2026/08/the-games-i-play/" class="postlist-link">The Games I Play</a></h2> 179 <p class="postlist-excerpt">A look back at fifteen years of my gaming, pulled from my self-hosted t
179ime tracker. Roughly 4,600 hours across 535 games on 3DS, Switch and PC, backfilled with lifetime Steam totals</p> 180 <time class="postlist-date" datetime="2026-08-29"><span class="visually-hidden">Published </span>29 Aug 2026</time> 181 <ul class="postlist-tags" aria-label="Tags"> 182 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 183 <li><a href="/tags/gaming/" class="post-tag">gaming</a></li> 184 <li><a href="/tags/quantified-self/" class="post-tag">quantified self</a></li> 185 </ul> 186 </li> 187 <li class="postlist-item"> 188 <h2 class="postlist-title" id="colby-woodland-garden"><a href="/2026/08/colby-woodland-garden/" class="postlist-link">Colby Woodland Garden</a></h2> 189 <p class="postlist-excerpt">A short trip report on our visit to Colby Woodland Garden</p> 190 <time class="postlist-date" datetime="2026-08-26"><span class="visually-hidden">Published </span>26 Aug 2026</time> 191 <ul class="postlist-tags" aria-label="Tags"> 192 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 193 <li><a href="/tags/adventures/" class="post-tag">adventures</a></li> 194 <li><a href="/tags/national-trust/" class="post-tag">national trust</a></li> 195 <li><a href="/tags/wales/" class="post-tag">wales</a></li> 196 </ul> 197 </li> 198 <li class="postlist-item"> 199 <h2 class="postlist-title" id="week-notes-2026-34"><a href="/week-notes/2026/34/" class="postlist-link">Week Notes - 2026-34</a></h2> 200 <p class="postlist-excerpt">My week notes for week 34 of 2026</p> 201 <time class="postlist-date" datetime="2026-08-24"><span class="visually-hidden">Published </span>24 Aug 2026</time> 202 <ul class="postlist-tags" aria-label="Tags"> 203 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 204 <li><a href="/tags/week-note/" class="post-tag">week note</a></li> 205 </ul> 206 </li> 207 <li class="postlist-item"> 208 <h2 class="postlist-title" id="week-notes-2026-33"><a href="/week-notes/2026/33/" class="postlist-link">Week Notes - 2026-33</a></h2> 209 <p class="postlist-excerpt">My week notes for week 33 of 2026</p> 210 <time class="postlist-date" datetime="2026-08-18"><span class="visually-hidden">Published </span>18 Aug 2026</time> 211 <ul class="postlist-tags" aria-label="Tags"> 212 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 213 <li><a href="/tags/week-note/" class="post-tag">week note</a></li> 214 </ul> 215 </li> 216 <li class="postlist-item"> 217 <h2 class="postlist-title" id="leaving-agile-behind-our-move-to-edf-freephase-dynamic"><a href="/2026/08/leaving-agile-behind-our-move-to-edf-freephase-dynamic/" class="postlist-link">Leaving Agile Behind: Our Move to EDF FreePhase Dynamic</a></h2> 218 <p class="postlist-excerpt">We'd been long term Octopus Agile customers even though it wasn't tailored to us as we don't have solar or battery storage. I'd started to think about looking at alternatives but never got very farâ¦</p> 219 <time class="postlist-date" datetime="2026-08-13"><span class="visually-hidden">Published </span>13 Aug 2026</time> 220 <ul class="postlist-tags" aria-label="Tags"> 221 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 222 <li><a href="/tags/smart-home/" class="post-tag">smart home</a></li> 223 <li><a href="/tags/how-to/" class="post-tag">how to</a></li> 224 </ul> 225 </li> 226 <li class="postlist-item"> 227 <h2 class="postlist-title" id="week-notes-2026-32"><a href="/week-notes/2026/32/" class="postlist-link">Week Notes - 2026-32</a></h2> 228 <p class="postlist-excerpt">My week notes for week 32 of 2026</p> 229 <time class="postlist-date" datetime="2026-08-10"><span class="visually-hidden">Published </span>10 Aug 2026</time> 230 <ul class="postlist-tags" aria-label="Tags"> 231 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 232 <li><a href="/tags/week-note/" class="post-tag">week note</a></li> 233 </ul> 234 </li> 235 <li class="postlist-item"> 236 <h2 class="postlist-title" id="week-notes-2026-31"><a href="/week-notes/2026/31/" class="postlist-link">Week Notes - 2026-31</a></h2> 237 <p class="postlist-excerpt">My week notes for week 31 of 2026</p> 238 <time class="postlist-date" datetime="2026-08-03"><span class="visually-hidden">Published </span>3 Aug 2026</time> 239 <ul class="postlist-tags" aria-label="Tags"> 240 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 241 <li><a href="/tags/week-note/" class="post-tag">week note</a></li> 242 </ul> 243 </li> 244 <li class="postlist-item"> 245 <h2 class="postlist-title" id="monitoring-mv-and-other-quiet-commands-with-watch-and-progress"><a href="/2026/08/monitoring-mv-and-other-quiet-commands-with-watch-and-progress/" class="postlist-link">Monitoring Mv and Other Quiet Commands With Watch and Progress</a></h2> 246 <p class="postlist-excerpt">How to keep an eye on long running file moves. Pair watch with progress to get a live view of commands like mv that show no output of their own.</p> 247 <time class="postlist-date" datetime="2026-08-01"><span class="visually-hidden">Published </span>1 Aug 2026</time> 248 <ul class="postlist-tags" aria-label="Tags"> 249 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 250 <li><a href="/tags/how-to/" class="post-tag">how to</a></li> 251 <li><a href="/tags/linux/" class="post-tag">linux</a></li> 252 </ul> 253 </li> 254 <li class="postlist-item"> 255 <h2 class="postlist-title" id="week-notes-2026-30"><a href="/week-notes/2026/30/" class="postlist-link">Week Notes - 2026-30</a></h2> 256 <p class="postlist-excerpt">My week notes for week 30 of 2026</p> 257 <time class="postlist-date" datetime="2026-07-27"><span class="visually-hidden">Published </span>27 Jul 2026</time> 258 <ul class="postlist-tags" aria-label="Tags"> 259 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 260 <li><a href="/tags/week-note/" class="post-tag">week note</a></li> 261 </ul> 262 </li> 263</ol> 264 265 266<nav class="pager" aria-label="Pagination"> 267 <span class="pager-prev pager-disabled">â Newer</span> 268 269 <span class="pager-pages"> 270 <a href="/blog/" aria-label="Page 1" class="pager-current" aria-current="page">1</a> 271 <a href="/blog/2/" aria-label="Page 2">2</a> 272 <a href="/blog/3/" aria-label="Page 3">3</a> 273 <a href="/blog/4/" aria-label="Page 4">4</a> 274 <a href="/blog/5/" aria-label="Page 5">5</a> 275 <a href="/blog/6/" aria-label="Page 6">6</a> 276 <a href="/blog/7/" aria-label="Page 7">7</a> 277 <a href="/blog/8/" aria-label="Page 8">8</a> 278 <a href="/blog/9/" aria-label="Page 9">9</a> 279 <a href="/blog/10/" aria-label="Page 10">10</a> 280 <a href="/blog/11/" aria-label="Page 11">11</a> 281 <a href="/blog/12/" aria-label="Page 12">12</a> 282 <a href="/blog/13/" aria-label="Page 13">13</a> 283 <a href="/blog/14/" aria-label="Page 14">14</a> 284 <a href="/blog/15/" aria-label="Page 15">15</a> 285 <a href="/blog/16/" aria-label="Page 16">16</a> 286 </span> 287 <a href="/blog/2/" class="pager-next">Older â</a> 288</nav> 289 290</div> 291 292<div id="blog-filtered" hidden=""> 293 <p id="blog-filtered-summary"></p> 294 <ol class="postlist" id="blog-filtered-list" aria-label="Filtered blog posts"></ol> 295 <p><a href="/blog/">Clear filter</a></p> 296</div> 297 298 299 300 301 </heading-anchors> 302 </main> 303 304 <aside class="sidebar"> 305 306 <div class="sidebar-widget"> 307 <h2 class="sidebar-widget-label" id="subscribe">Subscribe</h2> 308 <div class="badge-row"> 309 <a class="badge" href="/how-to-subscribe-to-my-blog/">RSS</a> 310 <a class="badge" href="https://bsky.app/profile/jamesleighton.com">Bluesky</a> 311 <button type="button" class="badge" id="blog-mastodon-badge" aria-haspopup="dialog" aria-controls="blog-mastodon-dialog">Mastodon</button> 312 </div> 313 </div> 314 315 <dialog id="blog-mastodon-dialog" class="copy-dialog"> 316 <form method="dialog"> 317 <p>This blog's Mastodon account isn't hosted on an instance you can click straight to — instead, copy the handle below and paste it into the search box of your own ActivityPub/Mastodon client to follow from there.</p> 318 <div class="copy-field"> 319 <label for="blog-mastodon-handle" class="visually-hidden">Mastodon handle</label> 320 <input type="text" id="blog-mastodon-handle" value="@[email protected]" readonly=""> 321 <button type="button" class="badge copy-field-btn" data-copy-target="blog-mastodon-handle">Copy</button> 322 </div> 323 <button type="submit" class="badge">Close</button> 324 </form> 325 </dialog> 326 327 <div class="sidebar-widget"> 328 <h2 class="sidebar-widget-label" id="follow-me">Follow Me</h2> 329 <div class="badge-row"> 330 <a class="badge" href="https://social.lol/@semaj" rel="me">Mastodon</a> 331 <a class="badge" href="https://bsky.app/profile/semaj.social.lol.ap.brid.gy" rel="me">Bluesky</a> 332 </div> 333 </div> 334 335 336 <div class="sidebar-widget"> 337 <h2 class="sidebar-widget-label" id="tags">Tags</h2> 338 <ul class="tag-cloud"> 339 340 341 <li><a href="/tags/100daystooffload/" class="tag-cloud-word" style="font-size: 2.22em; font-weight: 779; opacity: 0.98;" aria-label="100daystooffload (74 posts)">100daystooffload</a></li> 342 343 344 <li><a href="/tags/adventures/" class="tag-cloud-word" style="font-size: 1.16em; font-weight: 507; opacity: 0.71;" aria-label="adventures (23 posts)">adventures</a></li> 345 346 347 <li><a href="/tags/android/" class="tag-cloud-word" style="font-size: 0.94em; font-weight: 448; opacity: 0.65;" aria-label="android (12 posts)">android</a></li> 348 349 350 <li><a href="/tags/apple/" class="tag-cloud-word" style="font-size: 0.75em; font-weight: 400; opacity: 0.6;" aria-label="apple (3 posts)">apple</a></li> 351 352 353 <li><a href="/tags/backlog/" class="tag-cloud-word" style="font-size: 1em; font-weight: 464; opacity: 0.66;" aria-label="backlog (15 posts)">backlog</a></li> 354 355 356 <li><a href="/tags/blog/" class="tag-cloud-word" style="font-size: 0.77em; font-weight: 405; opacity: 0.61;" aria-label="blog (4 posts)">blog</a></li> 357 358 359 <li><a href="/tags/camping/" class="tag-cloud-word" style="font-size: 0.75em; font-weight: 400; opacity: 0.6;" aria-label="camping (3 posts)">camping</a></li> 360 361 362 <li><a href="/tags/cross-stitching/" class="tag-cloud-word" style="font-size: 0.75em; font-weight: 400; opacity: 0.6;" aria-label="cross stitching (3 posts)">cross stitching</a></li> 363 364 365 <li><a href="/tags/exist-io/" class="tag-cloud-word" style="font-size: 0.94em; font-weight: 448; opacity: 0.65;" aria-label="exist.io (12 posts)">exist.io</a></li> 366 367 368 <li><a href="/tags/four-in-february/" class="tag-cloud-word" style="font-size: 0.79em; font-weight: 411; opacity: 0.61;" aria-label="four in february (5 posts)">four in february</a></li> 369 370 371 <li><a href="/tags/gadgets/" class="tag-cloud-word" style="font-size: 1.18em; font-weight: 512; opacity: 0.71;" aria-label="gadgets (24 posts)">gadgets</a></li> 372 373 374 <li><a href="/tags/gaming/" class="tag-cloud-word" style="font-size: 2.22em; font-weight: 779; opacity: 0.98;" aria-label="gaming (74 posts)">gaming</a></li> 375 376 377 <li><a href="/tags/health/" class="tag-cloud-word" style="font-size: 1.23em; font-weight: 523; opacity: 0.72;" aria-label="health (26 posts)">health</a></li> 378 379 380 <li><a href="/tags/how-to/" class="tag-cloud-word" style="font-size: 1.87em; font-weight: 688; opacity: 0.89;" aria-label="how to (57 posts)">how to</a></li> 381 382 383 <li><a href="/tags/life/" class="tag-cloud-word" style="font-size: 2.3em; font-weight: 800;
383 opacity: 1;" aria-label="life (78 posts)">life</a></li> 384 385 386 <li><a href="/tags/linux/" class="tag-cloud-word" style="font-size: 1.06em; font-weight: 480; opacity: 0.68;" aria-label="linux (18 posts)">linux</a></li> 387 388 389 <li><a href="/tags/national-trust/" class="tag-cloud-word" style="font-size: 0.94em; font-weight: 448; opacity: 0.65;" aria-label="national trust (12 posts)">national trust</a></li> 390 391 392 <li><a href="/tags/networking/" class="tag-cloud-word" style="font-size: 0.83em; font-weight: 421; opacity: 0.62;" aria-label="networking (7 posts)">networking</a></li> 393 394 395 <li><a href="/tags/outdoors/" class="tag-cloud-word" style="font-size: 0.77em; font-weight: 405; opacity: 0.61;" aria-label="outdoors (4 posts)">outdoors</a></li> 396 397 398 <li><a href="/tags/podcasts/" class="tag-cloud-word" style="font-size: 0.77em; font-weight: 405; opacity: 0.61;" aria-label="podcasts (4 posts)">podcasts</a></li> 399 400 401 <li><a href="/tags/projects/" class="tag-cloud-word" style="font-size: 0.85em; font-weight: 427; opacity: 0.63;" aria-label="projects (8 posts)">projects</a></li> 402 403 404 <li><a href="/tags/python/" class="tag-cloud-word" style="font-size: 0.77em; font-weight: 405; opacity: 0.61;" aria-label="python (4 posts)">python</a></li> 405 406 407 <li><a href="/tags/quantified-self/" class="tag-cloud-word" style="font-size: 1.18em; font-weight: 512; opacity: 0.71;" aria-label="quantified self (24 posts)">quantified self</a></li> 408 409 410 <li><a href="/tags/reading/" class="tag-cloud-word" style="font-size: 0.98em; font-weight: 459; opacity: 0.66;" aria-label="reading (14 posts)">reading</a></li> 411 412 413 <li><a href="/tags/reviews/" class="tag-cloud-word" style="font-size: 0.89em; font-weight: 437; opacity: 0.64;" aria-label="reviews (10 posts)">reviews</a></li> 414 415 416 <li><a href="/tags/smart-home/" class="tag-cloud-word" style="font-size: 0.89em; font-weight: 437; opacity: 0.64;" aria-label="smart home (10 posts)">smart home</a></li> 417 418 419 <li><a href="/tags/summer-2012/" class="tag-cloud-word" style="font-size: 0.85em; font-weight: 427; opacity: 0.63;" aria-label="summer 2012 (8 posts)">summer 2012</a></li> 420 421 422 <li><a href="/tags/tech-thoughts/" class="tag-cloud-word" style="font-size: 0.81em; font-weight: 416; opacity: 0.62;" aria-label="tech thoughts (6 posts)">tech thoughts</a></li> 423 424 425 <li><a href="/tags/technology/" class="tag-cloud-word" style="font-size: 0.81em; font-weight: 416; opacity: 0.62;" aria-label="technology (6 posts)">technology</a></li> 426 427 428 <li><a href="/tags/uni/" class="tag-cloud-word" style="font-size: 0.94em; font-weight: 448; opacity: 0.65;" aria-label="uni (12 posts)">uni</a></li> 429 430 431 <li><a href="/tags/wales/" class="tag-cloud-word" style="font-size: 0.92em; font-weight: 443; opacity: 0.64;" aria-label="wales (11 posts)">wales</a></li> 432 433 434 <li><a href="/tags/week-note/" class="tag-cloud-word" style="font-size: 1.74em; font-weight: 656; opacity: 0.86;" aria-label="week note (51 posts)">week note</a></li> 435 436 437 <li><a href="/tags/yearly-theme/" class="tag-cloud-word" style="font-size: 0.81em; font-weight: 416; opacity: 0.62;" aria-label="yearly theme (6 posts)">yearly theme</a></li> 438 439 </ul> 440 <a href="/tags" class="badge tag-cloud-more" title="More Tags">More tags →</a> 441 </div> 442 443 <div class="sidebar-widget sidebar-recent-posts"> 444 <h2 class="sidebar-widget-label" id="recent-posts">Recent posts</h2> 445 446 447 448 449<ol class="postlist" aria-label="Recent posts"> 450 <li class="postlist-item"> 451 <h3 class="postlist-title" id="week-notes-2026-40-2"><a href="/week-notes/2026/40/" class="postlist-link">Week Notes - 2026-40</a></h3> 452 <p class="postlist-excerpt">My week notes for week 40 of 2026</p> 453 <time class="postlist-date" datetime="2026-10-05"><span class="visually-hidden">Published </span>5 Oct 2026</time> 454 <ul class="postlist-tags" aria-label="Tags"> 455 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 456 <li><a href="/tags/week-note/" class="post-tag">week note</a></li> 457 </ul> 458 </li> 459 <li class="postlist-item"> 460 <h3 class="postlist-title" id="september-in-numbers-2"><a href="/2026/10/september-in-numbers/" class="postlist-link">September in Numbers</a></h3> 461 <p class="postlist-excerpt">I had Claude crunch the numbers from my time tracking system for this one - here is September 2026 in numbers. September at a glance Metric September August Change Reading 17h 18m 16h 50m +28m Gamingâ¦</p> 462 <time class="postlist-date" datetime="2026-10-02"><span class="visually-hidden">Published </span>2 Oct 2026</time> 463 <ul class="postlist-tags" aria-label="Tags"> 464 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 465 <li><a href="/tags/life/" class="post-tag">life</a></li> 466 </ul> 467 </li> 468 <li class="postlist-item"> 469 <h3 class="postlist-title" id="week-notes-2026-39-2"><a href="/week-notes/2026/39/" class="postlist-link">Week Notes - 2026-39</a></h3> 470 <p class="postlist-excerpt">My week notes for week 39 of 2026</p> 471 <time class="postlist-date" datetime="2026-09-28"><span class="visually-hidden">Published </span>28 Sep 2026</time> 472 <ul class="postlist-tags" aria-label="Tags"> 473 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 474 <li><a href="/tags/week-note/" class="post-tag">week note</a></li> 475 </ul> 476 </li> 477 <li class="postlist-item"> 478 <h3 class="postlist-title" id="week-notes-2026-38-2"><a href="/week-notes/2026/38/" class="postlist-link">Week Notes - 2026-38</a></h3> 479 <p class="postlist-excerpt">My week notes for week 38 of 2026</p> 480 <time class="postlist-date" datetime="2026-09-21"><span class="visually-hidden">Published </span>21 Sep 2026</time> 481 <ul class="postlist-tags" aria-label="Tags"> 482 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 483 <li><a href="/tags/week-note/" class="post-tag">week note</a></li> 484 </ul> 485 </li> 486 <li class="postlist-item"> 487 <h3 class="postlist-title" id="how-to-embed-youtube-videos-into-11ty-2"><a href="/2026/09/easily-embed-youtube-videos-into-11ty/" class="postlist-link">How to Embed Youtube Videos Into 11ty</a></h3> 488 <p class="postlist-excerpt">I was getting annoyed at having to manually copy Youtube's privacy preserving embed code each time I wanted to include a video in a post, so here is a simple shortcode for 11ty that does the heavyâ¦</p> 489 <time class="postlist-date" datetime="2026-09-17"><span class="visually-hidden">Published </span>17 Sep 2026</time> 490 <ul class="postlist-tags" aria-label="Tags"> 491 <li><a href="/tags/100daystooffload/" class="post-tag">100daystooffload</a></li> 492 <li><a href="/tags/how-to/" class="post-tag">how to</a></li> 493 <li><a href="/tags/11ty/" class="post-tag">11ty</a></li> 494 </ul> 495 </li> 496</ol> 497 498 </div> 499 <div class="sidebar-widget" id="currently-card"> 500 <h2 class="sidebar-widget-label" id="now">Now</h2> 501 <ul class="currently"> 502 <li class="currently-row"> 503 <span class="currently-icon" aria-hidden="true">ð®</span> 504 <span class="currently-label">Playing</span> 505 <span class="currently-value">The Witcher 3: Wild Hunt â Remastered (Switch 2)</span> 506 </li> 507 <li class="currently-row"> 508 <span class="currently-icon" aria-hidden="true">ð²</span> 509 <span class="currently-label">Board gaming</span> 510 <span class="currently-value">My City: Roll & Build</span> 511 </li> 512 <li class="currently-row"> 513 <span class="currently-icon" aria-hidden="true">ð</span> 514 <span class="currently-label">Reading</span> 515 <span class="currently-value">Carpe Jugulum by Terry Pratchett</span> 516 </li> 517 </ul> 518 </div> 519 520 <div class="sidebar-widget"> 521 <h2 class="sidebar-widget-label" id="webrings">Webrings</h2> 522 <div class="badge-row"> 523 <span class="badge badge-group"> 524 <a href="https://xn--sr8hvo.ws/previous" aria-label="Previous site in the IndieWeb webring">←</a> 525 <a href="https://xn--sr8hvo.ws" aria-label="IndieWeb Webring">🕸️💍</a> 526 <a href="https://xn--sr8hvo.ws/next" aria-label="Next site in the IndieWeb webring">→</a> 527 </span> 528 <span class="badge badge-group"> 529 <a href="https://static.quest/previous/www.jamesleighton.com" aria-label="Previous site in the Static.quest webring">←</a> 530 <a href="https://static.quest/members" aria-label="Static.quest Webring">Static.quest</a> 531 <a href="https://static.quest/next/www.jamesleighton.com" aria-label="Next site in the Static.quest webring">→</a> 532 </span> 533 <span class="badge badge-group"> 534 <a href="https://polyring.club/previous?host=https://www.jamesleighton.com" aria-label="Previous site in the Polyring webring">←</a> 535 <a href="https://polyring.club/" aria-label="Polyring Webring">Polyring</a> 536 <a href="https://polyring.club/next?host=https://www.jamesleighton.com" aria-label="Next site in the Polyring webring">→</a> 537 </span> 538 <a class="badge" href="https://iheartrss.com/">I ♥ RSS</a> 539 </div> 540 </div> 541 542</aside> 543 544 545 546 547 </div> 548 549 <footer> 550 551 552 <p><span class="mastoshare"><a href="https://share.joinmastodon.org/#text=James Leighton https://www.jamesleighton.com/blog/" target="_blank" rel="noopener">Share on Mastodon<span class="visually-hidden"> (opens in a new tab)</span></a></span></p> 553 554 <p><a href="/feed/index.xml">Feed</a> · <a href="/search/">Search</a> · <a href="/stats/">Stats</a> · <a href="/privacy-policy">Privacy Policy</a></p> 555 </footer> 556 557 </div> 558 559 560 561 <!-- This page `/blog/` was built on 2026-10-07T21:30:05.075Z --> 562
562<script type="f81c2a924710e7b2910cef01-module" src="/dist/0XZIemyCua.js"></script>
562 563 564
564<script data-goatcounter="https://jamesleighton_com.goatcounter.com/count" async="" src="//gc.zgo.at/count.js" type="f81c2a924710e7b2910cef01-text/javascript"></script>
vendor: 144 bytes, lines 564-565
564 565 <script src="/cdn-cgi/scripts/7d0fa10a/cloudflare-static/rocket-loader.min.js" data-cf-settings="f81c2a924710e7b2910cef01-|49" defer></script>
565<script>(function(){function c(){var b=a.contentDocument||(a.contentWindow&&a.contentWindow.document);if(b){var d=b.createElement('script');d.innerHTML="window.__CF$cv$params={r:'a47062c479f3163a',t:'MTc5MTQxMjU5OA=='};var a=document.createElement('script');a.src='/cdn-cgi/challenge-platform/scripts/jsd/main.js';document.getElementsByTagName('head')[0].appendChild(a);";b.getElementsByTagName('head')[0].appendChild(d)}}if(document.body){var a=document.createElement('iframe');a.height=1;a.width=1;a.style.position='absolute';a.style.top=0;a.style.left=0;a.style.border='none';a.style.visibility='hidden';document.body.appendChild(a);if('loading'!==document.readyState)c();else if(window.addEventListener)document.addEventListener('DOMContentLoaded',c);else{var e=document.onreadystatechange||function(){};document.onreadystatechange=function(b){e(b);'loading'!==document.readyState&&(document.onreadystatechange=e,c())}}}})();</script>
565<script type="module" src="https://static.cloudflareinsights.com/beacon.min.js/v4bc70e2c01a94c73b74392e4234840661791215815920" integrity="sha512-L0ha0OXavK/8okipN9F8BtP84dg9DUhPERbBXzwI6dgTA55d2+yweo3pn5CSFYs45/r8md2+xvUPtTdvTNRfjA==" data-cf-beacon='{"version":"2024.11.0","token":"c3d161b35c7f4800af228479bc060e0f","r":1,"spa":2}' crossorigin="anonymous"></script>
565 566</body> 567</html>
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.