<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Raphaël Pinson</title>
    <description>The latest articles on DEV Community by Raphaël Pinson (@raphink).</description>
    <link>https://dev.to/raphink</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F59811%2F4dc2cd0d-9fed-44ef-a1e8-b249f32c7a0e.png</url>
      <title>DEV Community: Raphaël Pinson</title>
      <link>https://dev.to/raphink</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/raphink"/>
    <language>en</language>
    <item>
      <title>Four years chasing a consistent eBee — and what I built when I finally caught one</title>
      <dc:creator>Raphaël Pinson</dc:creator>
      <pubDate>Tue, 23 Jun 2026 08:10:00 +0000</pubDate>
      <link>https://dev.to/raphink/four-years-chasing-a-consistent-ebee-and-what-i-built-when-i-finally-caught-one-35je</link>
      <guid>https://dev.to/raphink/four-years-chasing-a-consistent-ebee-and-what-i-built-when-i-finally-caught-one-35je</guid>
      <description>&lt;p&gt;I've been trying to generate a consistent cartoon bee with AI for four years.&lt;/p&gt;

&lt;p&gt;Not just any bee. A specific one: eBee, the Isovalent mascot. Black rounded head, large teal oval eyes, semi-transparent wings, yellow and black body. Simple enough in concept. Surprisingly hard in practice.&lt;/p&gt;

&lt;p&gt;This is the story of that chase — and what I ended up building because of it.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Midjourney years (2021–2024)
&lt;/h2&gt;

&lt;p&gt;I started with Midjourney v3 shortly after it launched. The results were immediately interesting, but not useful — blurry bee-adjacent blobs that had no relationship to the character I was after.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fqy042qxh5obgl6nvubj0.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fqy042qxh5obgl6nvubj0.png" alt="Midjourney v3 — bees around a stone castle" width="512" height="512"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;V4 and v5 brought a quality leap. I started getting images I could actually use: atmospheric backgrounds for slide decks, dramatic scenes, a Cilium network map background I still use today. But for character work — a specific, recognizable, repeatable eBee — the models kept missing. Too photorealistic. Too generic. Too &lt;em&gt;bee&lt;/em&gt; and not enough &lt;em&gt;eBee&lt;/em&gt;.&lt;/p&gt;


&lt;div class="ltag-slides ltag-slides--carousel"&gt;
  &lt;div class="ltag-slides__track"&gt;
    &lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fzf2e5olzkgmstlpgweqd.png" alt="Midjourney v5 — steampunk mechanical bee" width="800" height="800"&gt;
&lt;/div&gt;


&lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fv3pskgikj18c7ynlx9go.png" alt="Midjourney v5 — realistic bee on server hardware" width="800" height="1200"&gt;
&lt;/div&gt;


&lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fd6j7z2loxma9uxbd0oz1.png" alt="Midjourney v5 — floating island map" width="800" height="299"&gt;
&lt;/div&gt;



  &lt;/div&gt;
    ‹
    ›
    &lt;div class="ltag-slides__dots"&gt;&lt;/div&gt;
    
      (function() {
        var container = document.currentScript.closest('.ltag-slides--carousel');
        var track = container.querySelector('.ltag-slides__track');
        var slides = track.querySelectorAll('.ltag-slide');
        var prevBtn = container.querySelector('.ltag-slides__nav--prev');
        var nextBtn = container.querySelector('.ltag-slides__nav--next');
        var dotsContainer = container.querySelector('.ltag-slides__dots');
        var current = 0;
        var total = slides.length;

        for (var i = 0; i &amp;lt; total; i++) {
          var dot = document.createElement('button');
          dot.className = 'ltag-slides__dot' + (i === 0 ? ' ltag-slides__dot--active' : '');
          dot.setAttribute('aria-label', 'Go to slide ' + (i + 1));
          dot.dataset.index = i;
          dot.addEventListener('click', function() { goTo(parseInt(this.dataset.index)); });
          dotsContainer.appendChild(dot);
        }

        function goTo(index) {
          current = ((index % total) + total) % total;
          track.style.transform = 'translateX(-' + (current * 100) + '%)';
          var dots = dotsContainer.querySelectorAll('.ltag-slides__dot');
          for (var i = 0; i &amp;lt; dots.length; i++) {
            dots[i].classList.toggle('ltag-slides__dot--active', i === current);
          }
        }

        prevBtn.addEventListener('click', function() { goTo(current - 1); });
        nextBtn.addEventListener('click', function() { goTo(current + 1); });
      })();
    
&lt;/div&gt;


&lt;p&gt;V6 got closer in style, and v6.1 closer still. A watercolor bee scientist. A cartoon bee astronaut. A bee in front of a cottage. Each one charming. None of them quite right.&lt;/p&gt;

&lt;p&gt;I tried style references, style boards, and character references — Midjourney's own tools for exactly this problem. None of them gave me the consistency I needed across scenes.&lt;/p&gt;


&lt;div class="ltag-slides ltag-slides--carousel"&gt;
  &lt;div class="ltag-slides__track"&gt;
    &lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fx1svqqy2s1qwjxcse3xq.png" alt="Midjourney v6.1 — watercolor scientist bee" width="800" height="1259"&gt;
&lt;/div&gt;


&lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fkazvqjdvok15xuj5p0ak.png" alt="Midjourney v6.1 — astronaut bee orbiting Earth" width="800" height="533"&gt;
&lt;/div&gt;


&lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F8qpibnkpivum3q96ux9w.png" alt="Midjourney v6.1 — cartoon bee at cottage door" width="800" height="556"&gt;
&lt;/div&gt;



  &lt;/div&gt;
    ‹
    ›
    &lt;div class="ltag-slides__dots"&gt;&lt;/div&gt;
    
      (function() {
        var container = document.currentScript.closest('.ltag-slides--carousel');
        var track = container.querySelector('.ltag-slides__track');
        var slides = track.querySelectorAll('.ltag-slide');
        var prevBtn = container.querySelector('.ltag-slides__nav--prev');
        var nextBtn = container.querySelector('.ltag-slides__nav--next');
        var dotsContainer = container.querySelector('.ltag-slides__dots');
        var current = 0;
        var total = slides.length;

        for (var i = 0; i &amp;lt; total; i++) {
          var dot = document.createElement('button');
          dot.className = 'ltag-slides__dot' + (i === 0 ? ' ltag-slides__dot--active' : '');
          dot.setAttribute('aria-label', 'Go to slide ' + (i + 1));
          dot.dataset.index = i;
          dot.addEventListener('click', function() { goTo(parseInt(this.dataset.index)); });
          dotsContainer.appendChild(dot);
        }

        function goTo(index) {
          current = ((index % total) + total) % total;
          track.style.transform = 'translateX(-' + (current * 100) + '%)';
          var dots = dotsContainer.querySelectorAll('.ltag-slides__dot');
          for (var i = 0; i &amp;lt; dots.length; i++) {
            dots[i].classList.toggle('ltag-slides__dot--active', i === current);
          }
        }

        prevBtn.addEventListener('click', function() { goTo(current - 1); });
        nextBtn.addEventListener('click', function() { goTo(current + 1); });
      })();
    
&lt;/div&gt;


&lt;p&gt;By late 2024, the best I could produce was a mountain climber eBee, an aviator eBee, a Christmas eBee. Recognizable as the same character across scenes. Close enough to use. But still requiring manual fixes, and always with that slight wrongness I couldn't prompt away.&lt;/p&gt;


&lt;div class="ltag-slides ltag-slides--carousel"&gt;
  &lt;div class="ltag-slides__track"&gt;
    &lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fd88nqa7nxdyai88l1r9v.png" alt="Late 2024 Midjourney — mountain climber eBee" width="800" height="800"&gt;
&lt;/div&gt;


&lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fkp59dgdcha7dy5sfh7js.png" alt="Late 2024 Midjourney — aviator eBee in biplane" width="800" height="450"&gt;
&lt;/div&gt;


&lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fxl4ncwttjm1wpk0szsfe.png" alt="Late 2024 Midjourney — Christmas eBee on sled" width="800" height="450"&gt;
&lt;/div&gt;



  &lt;/div&gt;
    ‹
    ›
    &lt;div class="ltag-slides__dots"&gt;&lt;/div&gt;
    
      (function() {
        var container = document.currentScript.closest('.ltag-slides--carousel');
        var track = container.querySelector('.ltag-slides__track');
        var slides = track.querySelectorAll('.ltag-slide');
        var prevBtn = container.querySelector('.ltag-slides__nav--prev');
        var nextBtn = container.querySelector('.ltag-slides__nav--next');
        var dotsContainer = container.querySelector('.ltag-slides__dots');
        var current = 0;
        var total = slides.length;

        for (var i = 0; i &amp;lt; total; i++) {
          var dot = document.createElement('button');
          dot.className = 'ltag-slides__dot' + (i === 0 ? ' ltag-slides__dot--active' : '');
          dot.setAttribute('aria-label', 'Go to slide ' + (i + 1));
          dot.dataset.index = i;
          dot.addEventListener('click', function() { goTo(parseInt(this.dataset.index)); });
          dotsContainer.appendChild(dot);
        }

        function goTo(index) {
          current = ((index % total) + total) % total;
          track.style.transform = 'translateX(-' + (current * 100) + '%)';
          var dots = dotsContainer.querySelectorAll('.ltag-slides__dot');
          for (var i = 0; i &amp;lt; dots.length; i++) {
            dots[i].classList.toggle('ltag-slides__dot--active', i === current);
          }
        }

        prevBtn.addEventListener('click', function() { goTo(current - 1); });
        nextBtn.addEventListener('click', function() { goTo(current + 1); });
      })();
    
&lt;/div&gt;


&lt;h2&gt;
  
  
  The breakthrough (early 2025)
&lt;/h2&gt;

&lt;p&gt;Then OpenAI released gpt-image-1, and from one day to the next, everything changed.&lt;/p&gt;

&lt;p&gt;I handed it a few reference images and got back this:&lt;/p&gt;


&lt;div class="ltag-slides ltag-slides--carousel"&gt;
  &lt;div class="ltag-slides__track"&gt;
    &lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fpmtc0lr4gdgi4x5dx4wd.png" alt="gpt-image-1 — baseball eBee" width="577" height="577"&gt;
&lt;/div&gt;


&lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fg4xp3imr0w5l5auz130m.png" alt="gpt-image-1 — Starfleet eBee" width="577" height="577"&gt;
&lt;/div&gt;


&lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fn9ggia93wuv1zc05zlic.png" alt="gpt-image-1 — basketball eBee" width="577" height="577"&gt;
&lt;/div&gt;


&lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fj1h3pyk84g6aw00e67vg.png" alt="gpt-image-1 — aviator eBee with toy plane" width="577" height="577"&gt;
&lt;/div&gt;


&lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fawvd142kk1pnc0cozuhu.png" alt="gpt-image-1 — samurai eBee" width="577" height="577"&gt;
&lt;/div&gt;



  &lt;/div&gt;
    ‹
    ›
    &lt;div class="ltag-slides__dots"&gt;&lt;/div&gt;
    
      (function() {
        var container = document.currentScript.closest('.ltag-slides--carousel');
        var track = container.querySelector('.ltag-slides__track');
        var slides = track.querySelectorAll('.ltag-slide');
        var prevBtn = container.querySelector('.ltag-slides__nav--prev');
        var nextBtn = container.querySelector('.ltag-slides__nav--next');
        var dotsContainer = container.querySelector('.ltag-slides__dots');
        var current = 0;
        var total = slides.length;

        for (var i = 0; i &amp;lt; total; i++) {
          var dot = document.createElement('button');
          dot.className = 'ltag-slides__dot' + (i === 0 ? ' ltag-slides__dot--active' : '');
          dot.setAttribute('aria-label', 'Go to slide ' + (i + 1));
          dot.dataset.index = i;
          dot.addEventListener('click', function() { goTo(parseInt(this.dataset.index)); });
          dotsContainer.appendChild(dot);
        }

        function goTo(index) {
          current = ((index % total) + total) % total;
          track.style.transform = 'translateX(-' + (current * 100) + '%)';
          var dots = dotsContainer.querySelectorAll('.ltag-slides__dot');
          for (var i = 0; i &amp;lt; dots.length; i++) {
            dots[i].classList.toggle('ltag-slides__dot--active', i === current);
          }
        }

        prevBtn.addEventListener('click', function() { goTo(current - 1); });
        nextBtn.addEventListener('click', function() { goTo(current + 1); });
      })();
    
&lt;/div&gt;


&lt;p&gt;Same character. Five completely different costumes and scenarios. Unmistakably the same eBee.&lt;/p&gt;

&lt;p&gt;The remaining gap was concrete and finite: eBees occasionally sprouted mouths, abdomens appeared when they shouldn't, the odd anatomical quirk crept in. Fixable in GIMP in minutes. My rule is simple: I won't publish something made with generative AI that I wouldn't publish if I'd made it without. No six-fingered hands. No eBees with mouths. If it would make a reader do a double-take for the wrong reason, it doesn't ship. With gpt-image-1, the fixes needed to meet that bar finally felt like a reasonable ask rather than a full redraw.&lt;/p&gt;

&lt;p&gt;I wrote a detailed character prompt my colleagues could copy-paste into ChatGPT. I even built a custom GPT called eBee Creator. But there was still a manual step nobody could get around: the reference images had to be attached by hand, every time. The platform had no way to bundle prompt and images together. You had to know where to find the refs and attach them to the chat thread, every time.&lt;/p&gt;

&lt;h2&gt;
  
  
  The comic problem
&lt;/h2&gt;

&lt;p&gt;Then I decided to make comic strips to explain Kubernetes networking concepts. Sixty-four panels, three character types, multiple recurring scenes.&lt;/p&gt;

&lt;p&gt;The drift started immediately.&lt;/p&gt;

&lt;p&gt;ChatGPT threads are both your context and your liability. The longer a thread runs, the more it drifts — more stars appearing in the sky across pages, characters subtly changing, scene backgrounds shifting. There's no surgical fix. You can't undo drift without losing all the good context that preceded it.&lt;/p&gt;


&lt;div class="ltag-slides ltag-slides--carousel"&gt;
  &lt;div class="ltag-slides__track"&gt;
    &lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fe8et5n7x4r5no33mrbfc.png" alt="more and more stars" width="800" height="800"&gt;
&lt;/div&gt;


&lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fgup3bjocub77zw68dpnb.png" alt="more and more stars" width="800" height="800"&gt;
&lt;/div&gt;


&lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fiayv25rn3cplb2zedlc4.png" alt="more and more stars" width="800" height="800"&gt;
&lt;/div&gt;


&lt;div class="ltag-slide"&gt;
      &lt;img class="ltag-slide__image" src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F0m9kffl8sl3csw9i6obq.png" alt="more and more stars" width="800" height="800"&gt;
&lt;/div&gt;



  &lt;/div&gt;
    ‹
    ›
    &lt;div class="ltag-slides__dots"&gt;&lt;/div&gt;
    
      (function() {
        var container = document.currentScript.closest('.ltag-slides--carousel');
        var track = container.querySelector('.ltag-slides__track');
        var slides = track.querySelectorAll('.ltag-slide');
        var prevBtn = container.querySelector('.ltag-slides__nav--prev');
        var nextBtn = container.querySelector('.ltag-slides__nav--next');
        var dotsContainer = container.querySelector('.ltag-slides__dots');
        var current = 0;
        var total = slides.length;

        for (var i = 0; i &amp;lt; total; i++) {
          var dot = document.createElement('button');
          dot.className = 'ltag-slides__dot' + (i === 0 ? ' ltag-slides__dot--active' : '');
          dot.setAttribute('aria-label', 'Go to slide ' + (i + 1));
          dot.dataset.index = i;
          dot.addEventListener('click', function() { goTo(parseInt(this.dataset.index)); });
          dotsContainer.appendChild(dot);
        }

        function goTo(index) {
          current = ((index % total) + total) % total;
          track.style.transform = 'translateX(-' + (current * 100) + '%)';
          var dots = dotsContainer.querySelectorAll('.ltag-slides__dot');
          for (var i = 0; i &amp;lt; dots.length; i++) {
            dots[i].classList.toggle('ltag-slides__dot--active', i === current);
          }
        }

        prevBtn.addEventListener('click', function() { goTo(current - 1); });
        nextBtn.addEventListener('click', function() { goTo(current + 1); });
      })();
    
&lt;/div&gt;


&lt;p&gt;I ended up with a multi-thread architecture: one thread for the storyline, separate threads for each scene type, with manual copy-pasting between them to prevent cross-contamination. It worked, but it was fragile. Any drift in any thread propagated forward. The only reset was starting from scratch and losing everything.&lt;/p&gt;

&lt;p&gt;When I cancelled ChatGPT for unrelated reasons, I moved the same workflow to Microsoft Copilot. Similar results, with the added frustration of edit features that kept losing images into a void.&lt;/p&gt;

&lt;h2&gt;
  
  
  Building the tool I needed
&lt;/h2&gt;

&lt;p&gt;When gpt-image-2 was released, I wanted to test it. Copilot didn't have it yet. So I deployed it on Azure AI Foundry myself and wrote the first version of panelgen in Python.&lt;/p&gt;

&lt;p&gt;I knew immediately what it needed to be: declarative and idempotent. Every pain point I'd accumulated across four years pointed at the same root cause — there was no persistent ground truth. The thread was doing the job that a spec file should be doing.&lt;/p&gt;

&lt;p&gt;And importantly: panelgen is not AI. It's deterministic glue — it reads a spec, builds a prompt, calls the API, and saves a versioned output. No model makes decisions inside it. The intelligence is in the spec you write; the creativity is in the prompts you craft. panelgen just makes sure both travel reliably to the API every single time, without drift.&lt;/p&gt;

&lt;p&gt;That said, nothing stops you from using an LLM to generate the YAML itself — I have. The spec is just text. Write it by hand, generate it, or have an agent produce it panel by panel. panelgen doesn't care.&lt;/p&gt;

&lt;p&gt;The insight was simple: replace the thread's implicit memory with an explicit config.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;characters&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;astronaut&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;description&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;Astronaut&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;eBee&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;—&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;white&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;space&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;suit,&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;glass&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;helmet,&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;orange&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;'eBPF'&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;badge"&lt;/span&gt;
    &lt;span class="na"&gt;refs&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s"&gt;characters/astronaut-bee.png&lt;/span&gt;
  &lt;span class="na"&gt;engineer&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;description&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;Engineer&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;eBee&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;—&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;hard&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;yellow&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;hat,&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;safety&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;jacket"&lt;/span&gt;

&lt;span class="na"&gt;scenes&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;space-conversation&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;prompt_prefix&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="s"&gt;Comic panel in outer space with deep purple/blue starry background.&lt;/span&gt;
      &lt;span class="s"&gt;Two eBee characters facing each other. Square panel with rounded corners.&lt;/span&gt;
    &lt;span class="na"&gt;characters&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;[&lt;/span&gt;&lt;span class="nv"&gt;astronaut&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="nv"&gt;engineer&lt;/span&gt;&lt;span class="pi"&gt;]&lt;/span&gt;

&lt;span class="na"&gt;panels&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;page&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;10&lt;/span&gt;
    &lt;span class="na"&gt;scene&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;space-conversation&lt;/span&gt;
    &lt;span class="na"&gt;prompt&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="s"&gt;Engineer eBee pointing upward while explaining to astronaut eBee.&lt;/span&gt;
      &lt;span class="s"&gt;Speech bubble: "You need to go through a Kubernetes Service!"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;Characters are defined once. Reference images travel with the config. Scenes don't pollute each other. The style guide is prepended to every prompt automatically. And crucially: re-running is safe. Each output is versioned (&lt;code&gt;page_10_low-1.png&lt;/code&gt;), existing versions are skipped unless you explicitly ask for a new increment.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fq1mrgv581gt4268fdqd0.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fq1mrgv581gt4268fdqd0.png" alt="Generated Scene" width="800" height="800"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The drift problem disappears because there is no thread. Every generation starts from the same spec, and the config can even be versioned.&lt;/p&gt;
&lt;h2&gt;
  
  
  Beyond the comic
&lt;/h2&gt;

&lt;p&gt;Once the workflow was solid, other use cases fell out naturally.&lt;/p&gt;

&lt;p&gt;An eBee shop demo app: product images generated as panels, then lifestyle shots of eBees using each product — with every lifestyle panel referencing the corresponding product image as a ref, so the product stays consistent across shots.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F6vng7uyr6p9has74v97y.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F6vng7uyr6p9has74v97y.png" alt="eBee Shop: lamp" width="800" height="787"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Consistent diagrams for labs: the same scene/panel abstraction works for technical illustrations. Define the diagram style as a scene, generate variants as panels. Consistent visual language across an entire lab series without copy-pasting style descriptions between prompts.&lt;/p&gt;

&lt;p&gt;The spec-first approach turns out to be useful anywhere you need a series of images that share visual DNA — not just comics.&lt;/p&gt;
&lt;h2&gt;
  
  
  The agentic angle
&lt;/h2&gt;

&lt;p&gt;Once image generation is driven by a YAML file and a prompt field, any upstream step can write to that prompt field — including an LLM. The &lt;code&gt;-prompt-file&lt;/code&gt; flag exists precisely for this: an agent generates or refines the panel prompt, writes it to a file, and panelgen consumes it.&lt;br&gt;
&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Agent writes the prompt&lt;/span&gt;
&lt;span class="nb"&gt;echo&lt;/span&gt; &lt;span class="s2"&gt;"Astronaut eBee looking shocked. Pod is exploding."&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; prompt.txt

&lt;span class="c"&gt;# panelgen consumes it&lt;/span&gt;
panelgen generate &lt;span class="nt"&gt;-prompt-file&lt;/span&gt; prompt.txt &lt;span class="nt"&gt;-scene&lt;/span&gt; space-solo output.png
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;Better yet, it can now generate a full YAML config with multiple scenes and panels, commit it to Git, and generate all the images from it.&lt;/p&gt;

&lt;p&gt;The agent doesn't need to know anything about the Azure API, the style guide, or the reference images. It just writes a prompt. The tool handles the rest. This is Unix composability with an LLM upstream — and that's why I rewrote the tool in Go: a simple static binary with no runtime dependencies drops into any pipeline without dependency management.&lt;/p&gt;

&lt;p&gt;I'll dive more into the agentic approach for labs design and illustration in a future post.&lt;/p&gt;
&lt;h2&gt;
  
  
  panelgen
&lt;/h2&gt;

&lt;p&gt;Panelgen is open-source and can be found (and contributed to) on GitHub:&lt;/p&gt;


&lt;div class="ltag-github-readme-tag"&gt;
  &lt;div class="readme-overview"&gt;
    &lt;h2&gt;
      &lt;img src="https://assets.dev.to/assets/github-logo-5a155e1f9a670af7944dd5e12375bc76ed542ea80224905ecaf878b9157cdefc.svg" alt="GitHub logo"&gt;
      &lt;a href="https://github.com/raphink" rel="noopener noreferrer"&gt;
        raphink
      &lt;/a&gt; / &lt;a href="https://github.com/raphink/panelgen" rel="noopener noreferrer"&gt;
        panelgen
      &lt;/a&gt;
    &lt;/h2&gt;
    &lt;h3&gt;
      Generate image panels from YAML + genAI
    &lt;/h3&gt;
  &lt;/div&gt;
  &lt;div class="ltag-github-body"&gt;
    
&lt;div id="readme" class="md"&gt;&lt;div class="markdown-heading"&gt;
&lt;h1 class="heading-element"&gt;panelgen&lt;/h1&gt;
&lt;/div&gt;

&lt;p&gt;&lt;a href="https://github.com/raphink/panelgen/actions/workflows/checks.yml" rel="noopener noreferrer"&gt;&lt;img src="https://github.com/raphink/panelgen/actions/workflows/checks.yml/badge.svg?branch=main" alt="checks"&gt;&lt;/a&gt;
&lt;a href="https://github.com/raphink/panelgen/actions/workflows/release.yml" rel="noopener noreferrer"&gt;&lt;img src="https://github.com/raphink/panelgen/actions/workflows/release.yml/badge.svg" alt="release"&gt;&lt;/a&gt;
&lt;a href="https://github.com/raphink/panelgen/blob/main/go.mod" rel="noopener noreferrer"&gt;&lt;img src="https://camo.githubusercontent.com/9933fdbe335b6c92e82268d81cbad1365d8ef3e7671ab10b75bf5d6933b5671b/68747470733a2f2f696d672e736869656c64732e696f2f6769746875622f676f2d6d6f642f676f2d76657273696f6e2f72617068696e6b2f70616e656c67656e" alt="Go Version"&gt;&lt;/a&gt;
&lt;a href="https://goreportcard.com/report/github.com/raphink/panelgen" rel="nofollow noopener noreferrer"&gt;&lt;img src="https://camo.githubusercontent.com/2f202cca3d1aa27cf255a74bf52d366f9d183043473c75ad6bf93c31bb10320b/68747470733a2f2f676f7265706f7274636172642e636f6d2f62616467652f6769746875622e636f6d2f72617068696e6b2f70616e656c67656e" alt="Go Report Card"&gt;&lt;/a&gt;
&lt;a href="https://pkg.go.dev/github.com/raphink/panelgen" rel="nofollow noopener noreferrer"&gt;&lt;img src="https://camo.githubusercontent.com/e67ab92274d746b376e17bc896c7b139685d0ed4e48fecb2617758652d2f3b7d/68747470733a2f2f706b672e676f2e6465762f62616467652f6769746875622e636f6d2f72617068696e6b2f70616e656c67656e2e737667" alt="Go Reference"&gt;&lt;/a&gt;
&lt;a href="https://opensource.org/licenses/Apache-2.0" rel="nofollow noopener noreferrer"&gt;&lt;img src="https://camo.githubusercontent.com/a549a7a30bacba7bfceebdc207a8e86c3f2c02995a2527640dca30048fd2b64e/68747470733a2f2f696d672e736869656c64732e696f2f62616467652f4c6963656e73652d417061636865253230322e302d626c75652e737667" alt="License: Apache 2.0"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;AI image series generator. Define scenes and panels in YAML, generate consistent image series with gpt-image-2 via Azure AI Foundry.&lt;/p&gt;
&lt;p&gt;Single static binary. No runtime dependencies. Designed to drop cleanly into agentic pipelines.&lt;/p&gt;
&lt;div class="markdown-heading"&gt;
&lt;h2 class="heading-element"&gt;Install&lt;/h2&gt;
&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;Homebrew (recommended):&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight highlight-source-shell notranslate position-relative overflow-auto js-code-highlight"&gt;
&lt;pre&gt;brew tap raphink/tap
brew install panelgen&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;From source:&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight highlight-source-shell notranslate position-relative overflow-auto js-code-highlight"&gt;
&lt;pre&gt;go install github.com/raphink/panelgen@latest&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;Binary:&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight highlight-source-shell notranslate position-relative overflow-auto js-code-highlight"&gt;
&lt;pre&gt;&lt;span class="pl-c"&gt;&lt;span class="pl-c"&gt;#&lt;/span&gt; Download from GitHub releases&lt;/span&gt;
curl -L https://github.com/raphink/panelgen/releases/latest/download/panelgen-linux-amd64 \
  -o panelgen &lt;span class="pl-k"&gt;&amp;amp;&amp;amp;&lt;/span&gt; chmod +x panelgen&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;Container:&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight highlight-source-shell notranslate position-relative overflow-auto js-code-highlight"&gt;
&lt;pre&gt;&lt;span class="pl-c"&gt;&lt;span class="pl-c"&gt;#&lt;/span&gt; Azure&lt;/span&gt;
docker run --rm \
  -v &lt;span class="pl-s"&gt;&lt;span class="pl-pds"&gt;"&lt;/span&gt;&lt;span class="pl-smi"&gt;$PWD&lt;/span&gt;:/work&lt;span class="pl-pds"&gt;"&lt;/span&gt;&lt;/span&gt; \
  -e AZURE_OPENAI_ENDPOINT \
  -e AZURE_OPENAI_API_KEY \
  panelgen batch --config panelgen.yml

&lt;span class="pl-c"&gt;&lt;span class="pl-c"&gt;#&lt;/span&gt; OpenAI&lt;/span&gt;
docker run --rm \
  -v &lt;span class="pl-s"&gt;&lt;span class="pl-pds"&gt;"&lt;/span&gt;&lt;span class="pl-smi"&gt;$PWD&lt;/span&gt;:/work&lt;span class="pl-pds"&gt;"&lt;/span&gt;&lt;/span&gt; \
  -e OPENAI_API_KEY \
  panelgen batch --config panelgen.yml&lt;/pre&gt;

&lt;/div&gt;
&lt;div class="markdown-heading"&gt;
&lt;h2 class="heading-element"&gt;Requirements&lt;/h2&gt;

&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;Azure OpenAI:&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight highlight-source-shell notranslate position-relative overflow-auto js-code-highlight"&gt;
&lt;pre&gt;&lt;span class="pl-k"&gt;export&lt;/span&gt; AZURE_OPENAI_ENDPOINT=&lt;span class="pl-s"&gt;&lt;span class="pl-pds"&gt;"&lt;/span&gt;https://your-resource.openai.azure.com&lt;span class="pl-pds"&gt;"&lt;/span&gt;&lt;/span&gt;
&lt;span class="pl-k"&gt;export&lt;/span&gt; AZURE_OPENAI_API_KEY=&lt;span class="pl-s"&gt;&lt;span class="pl-pds"&gt;"&lt;/span&gt;your-key&lt;span class="pl-pds"&gt;"&lt;/span&gt;&lt;/span&gt;
&lt;span class="pl-k"&gt;export&lt;/span&gt; AZURE_OPENAI_DEPLOYMENT=&lt;span class="pl-s"&gt;&lt;span class="pl-pds"&gt;"&lt;/span&gt;gpt-image-2&lt;span class="pl-pds"&gt;"&lt;/span&gt;&lt;/span&gt;   &lt;span class="pl-c"&gt;&lt;span class="pl-c"&gt;#&lt;/span&gt; optional, default: gpt-image-2&lt;/span&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;Standard OpenAI:&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight highlight-source-shell notranslate position-relative overflow-auto js-code-highlight"&gt;
&lt;pre&gt;&lt;span class="pl-k"&gt;export&lt;/span&gt; OPENAI_API_KEY=&lt;span class="pl-s"&gt;&lt;span class="pl-pds"&gt;"&lt;/span&gt;your-key&lt;span class="pl-pds"&gt;"&lt;/span&gt;&lt;/span&gt;
&lt;span class="pl-k"&gt;export&lt;/span&gt; OPENAI_MODEL=&lt;span class="pl-s"&gt;&lt;span class="pl-pds"&gt;"&lt;/span&gt;gpt-image-2&lt;span class="pl-pds"&gt;"&lt;/span&gt;&lt;/span&gt;    &lt;span class="pl-c"&gt;&lt;span class="pl-c"&gt;#&lt;/span&gt; optional, default: gpt-image-2&lt;/span&gt;
&lt;span class="pl-k"&gt;export&lt;/span&gt; OPENAI_BASE_URL=&lt;span class="pl-s"&gt;&lt;span class="pl-pds"&gt;"&lt;/span&gt;https://api.openai.com&lt;span class="pl-pds"&gt;"&lt;/span&gt;&lt;/span&gt;  &lt;span class="pl-c"&gt;&lt;span class="pl-c"&gt;#&lt;/span&gt;&lt;/span&gt;&lt;/pre&gt;…
&lt;/div&gt;&lt;/div&gt;
  &lt;/div&gt;
  &lt;div class="gh-btn-container"&gt;&lt;a class="gh-btn" href="https://github.com/raphink/panelgen" rel="noopener noreferrer"&gt;View on GitHub&lt;/a&gt;&lt;/div&gt;
&lt;/div&gt;


&lt;p&gt;You can install it via brew:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;brew tap raphink/tap
brew &lt;span class="nb"&gt;install &lt;/span&gt;panelgen
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The full config format, batch generation options, parallel generation, and agentic usage patterns are documented in the &lt;a href="https://github.com/raphink/panelgen" rel="noopener noreferrer"&gt;GitHub repository&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  What four years taught me
&lt;/h2&gt;

&lt;p&gt;The models got better — dramatically better. But the workflow bottleneck wasn't the model. It was the absence of a spec.&lt;/p&gt;

&lt;p&gt;Every time I was working around drift, copying prompts between threads, manually attaching reference images, I was compensating by hand for what a declarative config should do automatically. The tool I built isn't clever. It's just the missing infrastructure that should have existed from the start.&lt;/p&gt;

&lt;p&gt;If you're generating more than a handful of images with a consistent character or style, you probably need a spec too.&lt;/p&gt;

&lt;p&gt;For AI image generation, the chat thread is not your friend.&lt;/p&gt;

</description>
      <category>ai</category>
      <category>showdev</category>
      <category>opensource</category>
      <category>devtools</category>
    </item>
    <item>
      <title>We're at Risk of Losing Human Dignity to Machine Productivity</title>
      <dc:creator>Raphaël Pinson</dc:creator>
      <pubDate>Wed, 17 Jun 2026 17:13:51 +0000</pubDate>
      <link>https://dev.to/raphink/were-at-risk-of-losing-human-dignity-to-machine-productivity-lip</link>
      <guid>https://dev.to/raphink/were-at-risk-of-losing-human-dignity-to-machine-productivity-lip</guid>
      <description>&lt;p&gt;This is not an argument against AI. I use it daily, I build with it, and by most measures I'm on the winning side of the system it's creating, which is exactly why this argument needs to be made now, and why I'm in a position to make it.&lt;/p&gt;

&lt;p&gt;The debate about artificial intelligence keeps returning to the same question: is it intelligent? I'm not going to spend much time there. LLMs are not intelligent, not because of what they can or can't do, but because of what they are: statistical pattern matching at scale over human-generated data. They're mimicry, not cognition, and that's not a controversial claim if you understand the architecture.&lt;/p&gt;

&lt;p&gt;But a lot of people are making a different argument. They're pointing at capability failures: LLMs can't reliably count the letter "r" in "strawberry", therefore they're not intelligent. The problem with that argument is that many humans can't either, because they're illiterate, or because they process language differently. If that's your criterion, you've excluded a significant portion of humanity from intelligence before you've even reached AI, and if you then adjust the criterion to accommodate those humans, you need to explain why the adjusted criterion still excludes LLMs.&lt;/p&gt;

&lt;p&gt;That adjustment — finding a definition of intelligence that cleanly separates humans from machines — is where the danger lives, not because it might accidentally vindicate LLMs, but because every definition proposed, when applied consistently, ends up drawing a line through humanity itself.&lt;/p&gt;

&lt;p&gt;This is not a new problem. It has a history, and the history is not abstract. Defining humanity by capability has been used before to sort people into those who matter and those who don't, and the vocabulary changes, but the structure doesn't.&lt;/p&gt;

&lt;p&gt;What's new is the comparison class. As long as humans were the most productive agents in the economy, tying dignity to output was cruel to those at the bottom but didn't threaten the category as a whole. AI changes that arithmetic, and on an expanding set of measurable tasks, AI outproduces humans, cheaper, faster, without complaint. If your framework measures human worth by productive contribution, that framework now has a benchmark humans will increasingly fail to meet.&lt;/p&gt;

&lt;p&gt;The people most invested in that framework are aware of this. Some of them are building the AI, some of them are funding the political movements that will decide what to do with the humans who don't compete well, and they are not hiding their contempt for what they call low-productivity people, they are writing it in public and funding it into policy.&lt;/p&gt;

&lt;p&gt;The requirement — not the solution, the requirement — is to decorrelate human dignity from productive output, not because work has no value, not because contribution doesn't matter, but because human dignity has to be prior to and independent of what a person produces, or it isn't dignity at all, it's a performance review.&lt;/p&gt;

&lt;p&gt;This principle isn't new. It predates capitalism, predates the nation-state, predates the industrial revolution. The biblical tradition knew it well: the Jubilee year cancelled debts and returned land regardless of what people had produced, gleaning rights fed those who couldn't work without requiring them to justify their hunger, and Sabbath rest was mandatory, even for the productive. In each case, the logic is the same: human dignity primes over efficiency, subsistence is not means-tested, and neither is worth.&lt;/p&gt;

&lt;p&gt;In a world where a small number of people and systems can automate the productive output that once required millions, that principle stops being ancient wisdom and starts being urgent policy, and survival cannot remain a reward for contribution, it has to be a starting point.&lt;/p&gt;

&lt;p&gt;Most serious human rights frameworks rest on the same premise. What's new is that we can no longer afford to pay lip service to it while quietly grounding it in utility, because AI is removing the ambiguity, and the logical conclusion of measuring human worth by output, in a world where AI outproduces humans, is not prosperity, it's a sorting mechanism.&lt;/p&gt;

&lt;p&gt;The AI debate is not asking us whether machines are intelligent, it's asking us whether we meant what we said about humans.&lt;/p&gt;

</description>
      <category>ai</category>
      <category>ethics</category>
      <category>humanity</category>
      <category>discuss</category>
    </item>
    <item>
      <title>AI Doesn't Hallucinate. Your Architecture Does.</title>
      <dc:creator>Raphaël Pinson</dc:creator>
      <pubDate>Mon, 15 Jun 2026 08:30:00 +0000</pubDate>
      <link>https://dev.to/raphink/ai-doesnt-hallucinate-your-architecture-does-32pe</link>
      <guid>https://dev.to/raphink/ai-doesnt-hallucinate-your-architecture-does-32pe</guid>
      <description>&lt;p&gt;Everyone is talking about hallucination. That's the wrong diagnosis.&lt;/p&gt;

&lt;p&gt;Hallucination isn't a bug. It's the mechanism. Turn the temperature down far enough and the model stops confabulating, but it also stops being useful. What people call hallucination is what LLMs do when their creativity fails in a context that needed correctness. But all LLM output is hallucination in some form: generated token by token, probabilistically, without ground truth — just with enough structure and guardrails that most of it lands close enough to be acceptable.&lt;/p&gt;

&lt;p&gt;The creativity and the confabulation are the same thing. Different temperature, different context, different guardrails.&lt;/p&gt;

&lt;p&gt;Which means "reducing hallucination" is the wrong goal. You can't reduce it without reducing the model. The right goal is routing: giving LLMs only the problems where that generative, probabilistic process is actually what you need.&lt;/p&gt;

&lt;p&gt;Using a non-deterministic tool where a deterministic one would do the job perfectly is what breaks agentic systems.&lt;/p&gt;

&lt;p&gt;A deterministic API call costs microseconds and fractions of a cent. It is correct 100% of the time, by definition. An LLM doing the same task is slower, more expensive, and introduces a failure rate you now have to reason about — not because the model is broken, but because you've asked a creativity engine to act like a lookup table. Chain three of those steps together and you don't have a 10% failure rate, you have 27%. Five steps and you're past 40%. The errors are hard to reproduce and harder to attribute.&lt;/p&gt;

&lt;p&gt;I've been building an agentic genealogy research system. Two tasks, completely different natures.&lt;/p&gt;

&lt;p&gt;Fetching newspaper archive records for a given name and date range: deterministic. The API either returns results or it doesn't. There's no judgment to exercise, no ambiguity to resolve. An LLM here is just an expensive way to call curl — and one that will occasionally invent records that don't exist, because that's what it does.&lt;/p&gt;

&lt;p&gt;Deciding whether the person in that archive record is the same as the one in the birth register — given a different spelling of the surname, a two-year age discrepancy, and a naming convention that shifted at the border: LLM. This is exactly the kind of ill-defined correlation across uncertain evidence where you &lt;em&gt;want&lt;/em&gt; the probabilistic reasoning. The hallucination, properly constrained, is the feature.&lt;/p&gt;

&lt;p&gt;This is also why the current wave of "we don't need MCP anymore — SKILLS.md is enough" is exactly backwards.&lt;/p&gt;

&lt;p&gt;SKILLS.md is a routing layer. It tells the LLM which tool to use for which class of problem, directing judgment toward genuinely hard problems rather than eliminating it. That's valuable. But SKILLS.md is still natural language processed by a probabilistic model. MCP gives the model actual deterministic tools: APIs with guaranteed behavior, typed inputs, reliable outputs. Replacing MCP with SKILLS.md doesn't simplify your architecture, it replaces a deterministic function call with a probabilistic description of one. You've kept the complexity and removed the reliability.&lt;/p&gt;

&lt;p&gt;The routing layer is where most agentic architectures fail silently. Engineers reach for the LLM because it's faster to prototype, because it removes the need to maintain separate services, because describing a tool in natural language feels easier than building it. What they get instead is unnecessary entropy at every step, and failure modes that look like model problems but are actually architecture problems.&lt;/p&gt;

&lt;p&gt;The question to ask at every step of your pipeline isn't "can the LLM do this." It can, after enough tries. The question is: is this problem actually non-deterministic? Is there genuine ambiguity here that requires judgment? If not — if there's a correct answer a function could return reliably — you've given a creativity engine a job that doesn't need creativity. And you'll pay for it in every run.&lt;/p&gt;

&lt;p&gt;The good news: MCP servers are rather easy to build. Using LLMs.&lt;/p&gt;

</description>
      <category>ai</category>
      <category>architecture</category>
      <category>llm</category>
      <category>discuss</category>
    </item>
    <item>
      <title>Defining Autism: The Shadow and the Object</title>
      <dc:creator>Raphaël Pinson</dc:creator>
      <pubDate>Fri, 12 Jun 2026 14:28:09 +0000</pubDate>
      <link>https://dev.to/raphink/defining-autism-the-shadow-and-the-object-3ca7</link>
      <guid>https://dev.to/raphink/defining-autism-the-shadow-and-the-object-3ca7</guid>
      <description>&lt;p&gt;When I attend tech conferences, people usually know me — if they do — for my work on Cilium and my labs.&lt;/p&gt;

&lt;p&gt;That started changing recently. At the last two tech conferences I attended, visitors came up to me and thanked me for my series on autism. That has been extremely encouraging, especially hearing them say they relate to most of what I shared.&lt;/p&gt;

&lt;p&gt;But their next question is often: "so how would you define autism, actually?"&lt;/p&gt;

&lt;p&gt;It's a fair question. And the honest answer is that the official definition — the one in the DSM-5, the handbook clinicians use worldwide — doesn't really answer it.&lt;/p&gt;

&lt;p&gt;The DSM defines autism by its observable symptoms: persistent deficits in social communication, restricted and repetitive behaviors. It's a checklist of what a clinician can see in a room, or what a patient can report about themselves. It describes the shadow, not the object.&lt;/p&gt;

&lt;p&gt;This made sense historically. Autism was identified and named from behavioral observation before its neurological mechanisms were understood. The definition was built on what was available — the same way plague was once defined by buboes and fever, before Yersin identified Yersinia pestis in 1894 and medicine stopped defining the disease by its symptoms and started defining it by its cause.&lt;/p&gt;

&lt;p&gt;We are still, for autism, in the pre-Yersin era. Not because the underlying neurological differences are unknown — neuroimaging studies have consistently identified atypical subcortical connectivity, different sensory processing thresholds, distinct patterns in amygdala and thalamic function. The neurobiological reality is known well enough to begin building definitions grounded in cause rather than presentation. Clinical practice just hasn't caught up to the science yet.&lt;/p&gt;

&lt;p&gt;The goal here is not to settle which neurological mechanism is primary — researchers are still actively debating that. The point is simpler: the definition belongs in that category at all, rather than in the category of observable social behavior.&lt;/p&gt;

&lt;p&gt;So the DSM keeps the symptom-based definition. Not out of dishonesty — out of a category error that was reasonable when it was made and hasn't been corrected since. Mistaking the presentation for the condition. The shadow for the object.&lt;/p&gt;

&lt;p&gt;We may not yet have a complete mechanistic definition. But an incomplete map of the cause is still closer to the object than a detailed map of the shadow.&lt;/p&gt;

&lt;p&gt;The distinction matters because a definition and a diagnostic test are not the same thing. A definition requires knowing what something is. A test requires detecting it consistently. We already know autism is neurological. We know it has a substantial genetic basis. We know many of the brain structures and processes involved. What we do not yet have is enough precision to build a repeatable diagnostic test from that knowledge.&lt;/p&gt;

&lt;p&gt;The first bar has largely been cleared. The second has not. Defining autism by its behavioral presentation conflates the two — building the definition from the available test rather than from the available knowledge. That is the category error.&lt;/p&gt;

&lt;p&gt;The behavioral criteria remain useful as diagnostic proxies — when used as such. The problem is when they become the definition. One of my children was seen by clinicians for years who dismissed the possibility of autism because he presented well in their office. He was a good boy. Not rolling on the floor. What they didn't see was what happened at home. The proxy was working as designed. The clinicians mistook it for reality.&lt;/p&gt;

&lt;p&gt;There's a compounding error here: early support and intervention can improve behavioral presentation. Which means the better the support, the less visible the condition — and the more likely a clinician using a behavioral checklist will miss it. Adjusted behavior gets mistaken for low need. A social outcome gets mistaken for a sufficient one.&lt;/p&gt;

&lt;p&gt;Some would argue that if a child presents well, diagnosis is unnecessary. But diagnosis changed everything — not for the clinicians, but for the people around him. Siblings understood. Teachers adjusted. The bullying stopped, not because he changed, but because the people around him finally had a frame for why he was the way he was. That is what diagnosis is actually for. Not a label. A lens.&lt;/p&gt;

&lt;p&gt;The consequences extend further. A definition built on observable behavior misses anyone whose behavior has been masked, compensated, or trained away. Which is precisely the late-diagnosed adult population — the people most likely to have spent decades performing neurotypicality convincingly enough to fool everyone, including themselves. My own GP discouraged me from seeking a diagnosis twice. I was diagnosed at 43.&lt;/p&gt;

&lt;p&gt;As a suggested definition, for what it's worth: autism is a neurological condition — not a psychological disorder — in which the preconscious processing of sensory input and social information operates with a different filtering baseline, through different mechanisms and different thresholds than the neurotypical baseline. The behavioral symptoms follow from that. They are consequences, not causes.&lt;/p&gt;

&lt;p&gt;That definition is stable. It doesn't shift with age, context, or the quality of someone's masking on a given Tuesday.&lt;/p&gt;

&lt;p&gt;The checklist shifts. The underlying neurology doesn't.&lt;/p&gt;

&lt;p&gt;I'd be curious to hear from researchers, clinicians, or fellow autistics: is there a better definition? One that names the cause rather than the shadow?&lt;/p&gt;

</description>
      <category>mentalhealth</category>
      <category>inclusion</category>
      <category>community</category>
      <category>career</category>
    </item>
    <item>
      <title>Vanity of vanities — on AI slop and the problem of content for content's sake</title>
      <dc:creator>Raphaël Pinson</dc:creator>
      <pubDate>Fri, 12 Jun 2026 08:30:00 +0000</pubDate>
      <link>https://dev.to/raphink/vanity-of-vanities-on-ai-slop-and-the-problem-of-content-for-contents-sake-4e6l</link>
      <guid>https://dev.to/raphink/vanity-of-vanities-on-ai-slop-and-the-problem-of-content-for-contents-sake-4e6l</guid>
      <description>&lt;p&gt;3,000 years ago, Qoheleth surveyed everything done under the sun and called it vanity. Not pride — emptiness. The striving after wind. Labor that produces nothing that lasts, accumulates nothing that matters, leaves nothing behind worth finding.&lt;/p&gt;

&lt;p&gt;He would have recognized LinkedIn immediately.&lt;/p&gt;

&lt;p&gt;The flood of AI-generated content that fills every feed right now is not primarily a quality problem. It is a vanity problem. Content produced not because there was something to say, but because the algorithm rewards posting. Because silence looks like absence. Because everyone else is publishing, so you must too.&lt;/p&gt;

&lt;p&gt;The tool didn't create this. The tool made it cheaper.&lt;/p&gt;

&lt;p&gt;The barrier to publishing was never the writing. It was having something worth saying. Remove the writing barrier without removing the emptiness barrier, and you get an avalanche of nothing — dressed in confident prose, structured in three points, ending with a call to action that leads nowhere.&lt;/p&gt;

&lt;p&gt;Qoheleth's diagnosis was precise: vanity is not about what you produce, it's about why. Work done for its own sake, for appearance, for the striving — that is the problem. The medium is irrelevant. A hand-written empty thought is still empty. An AI-generated profound insight is still profound, if it came from somewhere real.&lt;/p&gt;

&lt;p&gt;The question AI forces us to ask — and that most people are avoiding — is not "did a human write this." It is "was there anything here worth saying." That question predates the tool by at least three thousand years.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;A chasing after wind.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>ai</category>
      <category>writing</category>
      <category>discuss</category>
      <category>career</category>
    </item>
    <item>
      <title>Gen AI is an Amplification Machine</title>
      <dc:creator>Raphaël Pinson</dc:creator>
      <pubDate>Thu, 11 Jun 2026 08:41:34 +0000</pubDate>
      <link>https://dev.to/raphink/gen-ai-is-an-amplification-machine-d54</link>
      <guid>https://dev.to/raphink/gen-ai-is-an-amplification-machine-d54</guid>
      <description>&lt;p&gt;I've been using generative AI pretty much daily for months now. And I've come to think most people fundamentally misunderstand what it does.&lt;/p&gt;

&lt;p&gt;Gen AI is an amplification machine.&lt;/p&gt;

&lt;p&gt;Give it good ideas, and it will help you express them better than you could alone. Give it bad ideas, and it will make them worse, more confidently, with better grammar. Give it nothing — no ideas, no voice, no judgment — and you'll get slop. Averaged mediocrity, the statistical center of human expression, smoothed of anything surprising or true.&lt;/p&gt;

&lt;p&gt;The tool doesn't add quality. It multiplies what's already there, as a catalyst.&lt;/p&gt;

&lt;p&gt;Which is why the people I see getting the most genuine value from it are almost always people who were already creating and thinking seriously before it existed. Not because the tool is gatekept, but because the gate was never the tool. It was always the ideas. The voice. The judgment that knows when something is good and when it only looks good.&lt;/p&gt;

&lt;p&gt;I use it as a mind extension. I drop half-formed thoughts into a conversation, and something comes back that helps me see what I was actually trying to say. It holds more threads simultaneously than I can. It pushes back from angles I hadn't considered. It drafts the sentence I was circling around for twenty minutes.&lt;/p&gt;

&lt;p&gt;But it has never once given me a novel idea I didn't already have in some latent form. It has never surprised me with an insight I couldn't recognize as mine once it appeared. The correlation happens in my head. The tool just removes the friction between having the thought and getting it out of my head in a form others can use.&lt;/p&gt;

&lt;p&gt;I don't judge the tool by how much content it helps me produce. I judge it by whether I think better because of it. Whether a conversation sharpened an argument I'd been carrying half-formed for months. Whether pushing back on a draft helped me find what I actually believed. Whether I understand something today that I didn't yesterday.&lt;/p&gt;

&lt;p&gt;There's a word for what it produces when there's nothing to amplify: mediocre. Not bad — bad can be interesting, even funny; it takes a soul to genuinely produce failure. Mediocre is the absence of soul. Competent enough to look like it tried, empty enough to leave nothing behind.&lt;/p&gt;

&lt;p&gt;If you wouldn't publish that post in your own voice, AI is no excuse to do it. You — and the world — deserve better than statistical word soup.&lt;/p&gt;

&lt;p&gt;Disclaimer: This post was sublimated through a two-hour conversation with Claude.&lt;/p&gt;

</description>
      <category>ai</category>
      <category>productivity</category>
      <category>career</category>
      <category>discuss</category>
    </item>
    <item>
      <title>Return to the Planet of the Autistics</title>
      <dc:creator>Raphaël Pinson</dc:creator>
      <pubDate>Mon, 08 Jun 2026 15:33:39 +0000</pubDate>
      <link>https://dev.to/raphink/return-to-the-planet-of-the-autistics-447g</link>
      <guid>https://dev.to/raphink/return-to-the-planet-of-the-autistics-447g</guid>
      <description>&lt;p&gt;&lt;em&gt;Field journal of Dr. E. Rempel, Department of Minority Neurological Studies, University of New Carthage (A work of fiction. "Allism" is a real term used by some autistic people to describe the neurological profile of the non-autistic majority.)&lt;/em&gt;&lt;/p&gt;




&lt;p&gt;&lt;em&gt;March 3, 2089&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;I have now spent three months embedded with an allistic community in the outer provinces. Allism, for those unfamiliar, is a rare neurological variant affecting approximately 1% of our population. My colleagues at the University have long debated its origins and persistence. After direct observation, I am no more certain of the answers, but I have accumulated a remarkable set of field notes.&lt;/p&gt;

&lt;p&gt;The allistic subjects I have observed appear, on the surface, entirely functional. They hold jobs, maintain relationships, raise children. And yet their neurological profile diverges from the norm in ways that are at once fascinating and bewildering.&lt;/p&gt;




&lt;p&gt;&lt;em&gt;March 11, 2089&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;The most immediately striking feature of the allistic profile is their relationship with information. Where a typical individual experiences the sharing of useful knowledge as a basic social reflex, the allistic subject appears to require an elaborate ritual before any information exchange can occur.&lt;/p&gt;

&lt;p&gt;Approach an allistic subject directly with a piece of useful data and observe what happens. Rather than receiving it, they freeze. A threat-assessment process appears to engage, entirely pre-consciously, before the content of the communication can be evaluated at all. One subject described it to me as feeling "strange" when a stranger approached with unsolicited information, though she could not articulate why.&lt;/p&gt;

&lt;p&gt;I have learned to preface all information exchanges with what my translator calls "the preamble ritual" — a sequence of social signals that appears to deactivate the threat response and allow communication to proceed. The exact form varies, but typically involves eye contact, a softening of posture, and verbal acknowledgment that one is about to speak. Only then can the information be received.&lt;/p&gt;

&lt;p&gt;The evolutionary origins of this ritual remain unclear to me. My working hypothesis is that it functions as a trust-establishment protocol, though why the allistic nervous system requires trust to precede factual information rather than follow its evaluation is a question I have not yet been able to answer satisfactorily.&lt;/p&gt;




&lt;p&gt;&lt;em&gt;March 16, 2089&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;A minor observation, but one I keep returning to. The clothing worn by my allistic subjects would be, for most members of my own population, a source of considerable distress. Rough seams left unfinished. Labels intact at the collar. Fabrics that I would describe as abrasive worn directly against the skin, apparently without a second thought.&lt;/p&gt;

&lt;p&gt;I raised this carefully with one subject, asking whether she found certain textures uncomfortable. She looked at me with what I have come to recognize as polite confusion. "Not really," she said. "Should I?"&lt;/p&gt;

&lt;p&gt;I did not pursue the matter further. But I noted that the specialized garment industry my own population has developed over generations — seamless constructions, carefully selected weaves, the near-universal preference for soft natural fibers — would likely strike her as an inexplicable luxury.&lt;/p&gt;

&lt;p&gt;I am not certain she is wrong.&lt;/p&gt;




&lt;p&gt;&lt;em&gt;March 19, 2089&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;The allistic empathy system is, I will admit, remarkable in its own way. Where the typical mind responds to another's distress by immediately searching for relevant information or resources, the allistic subject responds with something altogether different: they synchronize.&lt;/p&gt;

&lt;p&gt;I observed this phenomenon repeatedly. One subject was visibly distressed about a professional difficulty. A colleague sat close, placed a hand on her arm, and said: "That sounds really hard." No information was exchanged. No solution was offered. And yet the distressed subject visibly relaxed.&lt;/p&gt;

&lt;p&gt;I spent some time puzzling over this before my translator explained that the allistic subject was not attempting to solve the problem. They were signaling membership in a shared emotional space. The distress itself was the point of contact.&lt;/p&gt;

&lt;p&gt;I have since come to understand that allistic empathy is cohesion-based rather than information-based. They experience something of another's distress, synchronize with it, and express care by making that synchronization visible. It operates on entirely different principles than the system I grew up with, but I have stopped assuming it is therefore less sophisticated.&lt;/p&gt;




&lt;p&gt;&lt;em&gt;March 24, 2089&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;I attended a social gathering this evening in a venue I would describe as aggressively stimulating. Overhead lighting of the flickering variety my population abandoned some decades ago. Music at a volume that made conversation technically possible but practically taxing. Several simultaneous sound sources competing without apparent hierarchy.&lt;/p&gt;

&lt;p&gt;My allistic companions were energized. One of them leaned toward me at one point — shouting, by any reasonable measure — and asked if I was enjoying myself.&lt;/p&gt;

&lt;p&gt;I said that I was finding it interesting.&lt;/p&gt;

&lt;p&gt;I have since learned that this is an acceptable answer.&lt;/p&gt;

&lt;p&gt;What I could not explain to her is that I spent most of the evening mapping the exits and trying to identify which sound source to filter out first. She, I am fairly certain, was simply having a good time. The difference in our baseline calibration is something I am still trying to understand. I note, however, that not all of my allistic subjects respond to such environments identically — one excused himself early, citing a headache — which suggests the variation within the allistic profile is wider than our diagnostic literature implies.&lt;/p&gt;




&lt;p&gt;&lt;em&gt;March 31, 2089&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;A note on small talk, which I have been attempting to master with limited success.&lt;/p&gt;

&lt;p&gt;The allistic subjects I have observed engage in it fluently and apparently with pleasure. Exchanges about the weather, weekend plans, minor shared observations about the immediate environment — these seem to function as a kind of social maintenance, a low-stakes signal that the relationship is still intact and the parties are still on good terms. My translator describes it as "keeping the connection warm."&lt;/p&gt;

&lt;p&gt;I understand the function intellectually. The practice itself I find effortful in a way I struggle to convey. The content of most small talk exchanges carries very little information, which means I am spending social energy on a transaction that does not obviously repay it. My allistic subjects, conversely, seem genuinely refreshed by it. One described a brief exchange with a neighbor about her garden as "nice." I believe her.&lt;/p&gt;




&lt;p&gt;&lt;em&gt;April 2, 2089&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;The allistic tendency toward group cohesion produces some extraordinary social structures. They maintain large, complex networks of relationships with apparent ease, reading emotional states across a room, navigating implicit hierarchies without explicit rules. At a dinner party I attended as an observer, subjects managed at least four simultaneous conversations, tracking each other's engagement levels and adjusting fluidly. I found it overwhelming. They found it enjoyable.&lt;/p&gt;

&lt;p&gt;I have also observed, however, a recurring pattern in group decision-making contexts. Once a course of action has been agreed upon by the group, information that might complicate or reverse that decision becomes remarkably difficult to introduce. The social fabric of the agreement seems to take on a weight of its own. Subjects who possess relevant corrective information will often hesitate, gauge the room, and on more than one occasion I observed them remain silent altogether.&lt;/p&gt;

&lt;p&gt;I noted this carefully in my records but said nothing. It was not my place.&lt;/p&gt;




&lt;p&gt;&lt;em&gt;April 8, 2089&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Something I should have noted earlier: the allistic subjects I have observed do not appear to experience the ambient anxiety that most members of my population would describe as a background feature of daily life. The low-level monitoring of potential information gaps, the discomfort of unresolved uncertainty, the particular unease of an incomplete picture — these do not seem to register for them in the same way.&lt;/p&gt;

&lt;p&gt;One subject, when I described this to her, said: "I think I just assume things will probably work out."&lt;/p&gt;

&lt;p&gt;I wrote this down verbatim. I am not sure I have ever assumed things will probably work out.&lt;/p&gt;

&lt;p&gt;I want to be careful not to overstate this. Several of my subjects do describe anxiety — about social situations, about relationships, about the future in general. The allistic nervous system is not without its own forms of worry. But the specific texture of uncertainty-as-threat, the experience of an information gap as something requiring urgent resolution, does not appear to be a central feature of their profile. They seem, on the whole, more comfortable not knowing.&lt;/p&gt;




&lt;p&gt;&lt;em&gt;April 14, 2089&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;I raised the decision-making observation with my translator over dinner. He was quiet for a moment, then said: "We don't like to make people feel wrong in front of others."&lt;/p&gt;

&lt;p&gt;I asked whether they would prefer to proceed with an incorrect plan rather than endure that discomfort.&lt;/p&gt;

&lt;p&gt;He thought about it. "Sometimes," he said. "If the stakes are low enough."&lt;/p&gt;

&lt;p&gt;I found myself wondering how the group determines in advance whether the stakes are low enough.&lt;/p&gt;




&lt;p&gt;&lt;em&gt;April 29, 2089&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Before I left for the field, a colleague asked me why I had chosen to study allism rather than one of the more prevalent conditions. I told him it was precisely the rarity that interested me. A profile affecting 1% of a population tells you something about the other 99% — about what we consider default, expected, unremarkable.&lt;/p&gt;

&lt;p&gt;I have been sitting with a more unsettling question during these months, though. Our diagnostic manual defines allism as a neurological condition on the basis of its statistical rarity and its divergence from typical functioning. Typical functioning, the manual notes, reflects the profile of the majority.&lt;/p&gt;

&lt;p&gt;I keep returning to that definition. Not to dispute it, exactly. But I find I cannot read it now without wondering what it would say if the numbers were different — with inverted proportions, for example.&lt;/p&gt;

&lt;p&gt;Our society would probably be quite different then, and I wonder what they would think of us, autistics.&lt;/p&gt;




</description>
      <category>mentalhealth</category>
      <category>inclusion</category>
      <category>community</category>
      <category>career</category>
    </item>
    <item>
      <title>Why autism hasn't disappeared — a hypothesis</title>
      <dc:creator>Raphaël Pinson</dc:creator>
      <pubDate>Sat, 30 May 2026 14:38:16 +0000</pubDate>
      <link>https://dev.to/raphink/why-autism-hasnt-disappeared-a-hypothesis-1b6g</link>
      <guid>https://dev.to/raphink/why-autism-hasnt-disappeared-a-hypothesis-1b6g</guid>
      <description>&lt;p&gt;In the &lt;a href="https://dev.to/raphink/two-survival-systems-two-empathy-modes-5nl"&gt;previous post&lt;/a&gt;, I described two survival systems: one oriented toward information, one toward social cohesion. The autistic information drive produces friction: the café stranger, the colleague with links when you needed a hug. But it also produces something else.&lt;/p&gt;

&lt;p&gt;Picture a tribal council. The leader has spoken. The plan is agreed. Everyone around the fire has nodded. One person says: "But the herd tracks go the other way."&lt;/p&gt;

&lt;p&gt;Silence. Eyes. The weight of having contradicted the chief in front of everyone.&lt;/p&gt;

&lt;p&gt;The tracks went the other way.&lt;/p&gt;

&lt;h1&gt;
  
  
  The puzzle
&lt;/h1&gt;

&lt;p&gt;Autism has strong genetic components — spread on many genes, with expression influenced by environmental factors. It runs in families, it clusters, it transmits. It tends to isolate affected individuals, and yet it persists at consistent rates across all human populations, across cultures, and most likely across centuries. This is the kind of pattern that usually means something.&lt;/p&gt;

&lt;p&gt;The conventional explanations for its persistence focus on the individual level: genetic linkage to advantageous traits, cognitive advantages in pattern recognition and systemizing, the so-called "geek gene" hypothesis. These are real and worth taking seriously. But they explain individual fitness. What if the answer isn't at the individual level at all, what if the whole group benefited enough from the presence of autistic members that it played in favor of the group's survival?&lt;/p&gt;

&lt;h1&gt;
  
  
  The group-level argument
&lt;/h1&gt;

&lt;p&gt;A group where everyone runs the social-harmony calculation before speaking has a specific, predictable blind spot. Information gets suppressed to preserve group comfort. Errors go uncorrected because correcting them would embarrass someone senior. The plan with the structural flaw gets executed because no one wanted to be the one who said so in front of the chief.&lt;/p&gt;

&lt;p&gt;This is not a theoretical failure mode. It has a name —groupthink— with documented consequences. And it operates precisely through the mechanism that makes neurotypical social cohesion work so well in stable conditions: the instinct to read the room, preserve relationships, avoid disruption.&lt;/p&gt;

&lt;p&gt;The autistic information drive doesn't have that brake. Not because of courage or contrarianism, but because the system that would weigh social cost against information value simply doesn't run first. The information is there, it needs to be shared, and the authority of the person in front of you is not a relevant variable.&lt;/p&gt;

&lt;p&gt;The person around the fire says the tracks go the other way. Not to challenge the chief. Not to make a point. Because the tracks go the other way and that is the only thing that matters: to speak the facts.&lt;/p&gt;

&lt;h1&gt;
  
  
  The genetic angle
&lt;/h1&gt;

&lt;p&gt;You don't need to resolve the group selection debate in evolutionary biology to find this argument useful. There's a simpler version.&lt;/p&gt;

&lt;p&gt;Autism is heritable. Which means some groups, by genetic chance, would have had more of this profile and some would have had less — either by the higher presence of some autism-related genes, or by the presence of more such biological markers in the population. A group that happened to lack it entirely would have been exposed to the groupthink failure mode with no one to interrupt it. Information suppressed. Errors uncorrected. The tracks followed in the wrong direction.&lt;/p&gt;

&lt;p&gt;Over generations, over crises, over the moments when accuracy mattered more than social harmony, that asymmetry would have had consequences.&lt;/p&gt;

&lt;p&gt;This isn't a claim that autistic individuals were selected for. It's an observation that groups containing the profile were more robust against a specific and recurring failure mode that the majority profile generates in itself.&lt;/p&gt;

&lt;h1&gt;
  
  
  What this changes
&lt;/h1&gt;

&lt;p&gt;The usual framing of autism and society runs in one direction: here is a profile that generates difficulties, how do we accommodate it. That framing isn't wrong, but it's incomplete.&lt;/p&gt;

&lt;p&gt;The profile that makes someone say the tracks go the other way, correct the stranger's restaurant recommendation, flag the error in the meeting when everyone has moved on — that profile is costly in stable, low-stakes social conditions. It produces exactly the friction described in the previous post. But a group running only the social cohesion system is vulnerable in a specific direction, and has been throughout human history.&lt;/p&gt;

&lt;p&gt;The autistic people who drove everyone slightly mad in ordinary times may have been the ones who said the thing that needed saying when it mattered most.&lt;/p&gt;

&lt;h1&gt;
  
  
  A note on epistemic honesty
&lt;/h1&gt;

&lt;p&gt;This is a hypothesis. The genetic heritability of autism is established. The groupthink failure mode is documented. The observation that cross-neurotype groups might be more robust is plausible and consistent with broader neurodiversity research. But the specific claim — that autism persists in part because groups containing it outperformed groups that didn't — is an original assembly of solid components, not a finding from the literature.&lt;/p&gt;

&lt;p&gt;I'm offering it as a frame worth considering, not a conclusion worth defending. If you work in evolutionary biology or behavioral genetics and think I'm wrong, I'd genuinely like to know why.&lt;/p&gt;

</description>
      <category>mentalhealth</category>
      <category>inclusion</category>
      <category>community</category>
      <category>career</category>
    </item>
    <item>
      <title>Two survival systems, two empathy modes</title>
      <dc:creator>Raphaël Pinson</dc:creator>
      <pubDate>Fri, 29 May 2026 06:56:49 +0000</pubDate>
      <link>https://dev.to/raphink/two-survival-systems-two-empathy-modes-5nl</link>
      <guid>https://dev.to/raphink/two-survival-systems-two-empathy-modes-5nl</guid>
      <description>&lt;p&gt;Here are two scenes. They look unrelated. They're not.&lt;/p&gt;

&lt;h1&gt;
  
  
  Scene 1
&lt;/h1&gt;

&lt;p&gt;Two people at a café, talking about a restaurant they want to try. A stranger walking past stops: "That place closed six months ago. The one on the corner is better." A brief nod, and they walk on.&lt;/p&gt;

&lt;p&gt;The two people exchange a glance, taken aback. Why did that person stop? What did they want?&lt;/p&gt;

&lt;p&gt;A few steps away, the stranger is also confused. They had useful information. They shared it. Why did these people react so strangely?&lt;/p&gt;

&lt;h1&gt;
  
  
  Scene 2
&lt;/h1&gt;

&lt;p&gt;A colleague is visibly stressed, describing a difficult situation at work. One friend pulls their chair closer, puts a hand on their arm: "That sounds really hard." Another opens their laptop: "I found something that might help — HR has a process for exactly this, I'll send you the link."&lt;/p&gt;

&lt;p&gt;The colleague leans into the first. Glances uncertainly at the second.&lt;/p&gt;

&lt;p&gt;The second person doesn't understand why sitting close and saying "that sounds hard" counts as helping. You haven't solved anything. The first doesn't understand why anyone would respond to distress with links.&lt;/p&gt;




&lt;p&gt;Both scenes end the same way: people on both sides convinced they did the right thing, confused by the other's reaction. The mismatch is mutual and invisible from the inside.&lt;/p&gt;

&lt;h1&gt;
  
  
  Two survival instincts, two empathy systems
&lt;/h1&gt;

&lt;p&gt;For many &lt;em&gt;autistic&lt;/em&gt; people, information is a &lt;strong&gt;survival&lt;/strong&gt; mechanism. Uncertainty is threat, missing information is a vulnerability, and the drive to correct and share runs below conscious awareness. &lt;strong&gt;Empathy, expressed through that system&lt;/strong&gt;, looks like giving someone what keeps you safe: accurate information, solutions, resources. The social preamble before sharing — announcing yourself, softening the approach — doesn't arise as a concept. Why would useful information require an introduction?&lt;/p&gt;

&lt;p&gt;For many &lt;em&gt;neurotypical&lt;/em&gt; people, social safety is a &lt;strong&gt;survival&lt;/strong&gt; mechanism. Group cohesion and reading others accurately are what keep people safe. &lt;strong&gt;Empathy, expressed through that system&lt;/strong&gt;, looks like presence: mirroring distress, making someone feel held, maintaining the social fabric. An uninvited approach from a stranger bypasses the protocol that signals safe intent — and that protocol isn't a nicety, it's the unlock code. Without it, the content can't land regardless of how useful it is.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fll3p3bkxfe9auwyvxzoq.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fll3p3bkxfe9auwyvxzoq.png" alt=" " width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The social preamble is as foreign a concept to the autistic person as the direct approach is unsettling to the neurotypical person. The information response is as opaque to the neurotypical person as emotional attunement is to the autistic person. Neither protocol is natural to the other system. The incomprehension runs in both directions, with equal depth.&lt;/p&gt;

&lt;h1&gt;
  
  
  Milton's double empathy problem
&lt;/h1&gt;

&lt;p&gt;In 2012, autistic researcher Damian Milton described what he called the double empathy problem: cross-neurotype communication difficulties aren't a deficit on one side, they're a mismatch between two coherent systems that are mutually opaque to each other. Historically, the autistic side has been asked to compensate, the neurotypical system treated as the default rather than as one particular survival logic among two.&lt;/p&gt;

&lt;p&gt;What these two scenes show is that both sides are trying to care for the other, each in the only language their system knows, and neither is being received as care.&lt;/p&gt;

&lt;p&gt;That's not a deficit. That's two survival systems, built for different threats, each expressing empathy in the only currency it has.&lt;/p&gt;

</description>
      <category>mentalhealth</category>
      <category>inclusion</category>
      <category>community</category>
      <category>career</category>
    </item>
    <item>
      <title>Rest is not what you think</title>
      <dc:creator>Raphaël Pinson</dc:creator>
      <pubDate>Wed, 27 May 2026 08:25:00 +0000</pubDate>
      <link>https://dev.to/raphink/rest-is-not-what-you-think-1mbc</link>
      <guid>https://dev.to/raphink/rest-is-not-what-you-think-1mbc</guid>
      <description>&lt;p&gt;My wife says she's never seen me rest.&lt;/p&gt;

&lt;p&gt;She's not wrong, exactly. But I think we've been working with different definitions.&lt;/p&gt;

&lt;p&gt;When someone tells me to rest, they usually mean: do something calm. Low stimulation. A walk in nature, a beach, quiet time.&lt;/p&gt;

&lt;p&gt;For a long time I couldn't explain why that didn't work for me. It wasn't that I didn't want to rest. It was that what counted as rest seemed to be defined by other people's nervous systems, not mine.&lt;/p&gt;

&lt;p&gt;Here's what I eventually figured out.&lt;/p&gt;

&lt;p&gt;Rest, for me, is not about low stimulation. It's about low novelty load on the threat and navigation system.&lt;/p&gt;

&lt;p&gt;I can blast metal music at full volume through headphones and come out of it genuinely restored. Not despite the intensity, because of something specific about it: my brain knows every note, every transition, every moment of that record. It keeps registering "I know this. I know this. I know this." No decisions required. No scanning. The system can stop.&lt;/p&gt;

&lt;p&gt;A beach is the opposite. It looks calm. But for my nervous system it's a continuous stream of unclassified inputs: people passing at unpredictable intervals, sounds I don't recognize, movements in peripheral vision, social situations I might need to navigate. My brain doesn't get to stop. It has to keep evaluating, filing, preparing. That's not rest. That's work with good lighting.&lt;/p&gt;

&lt;p&gt;The axis isn't intensity versus calm. It's known versus unknown. More precisely: does this input require a response decision, or not?&lt;/p&gt;

&lt;p&gt;This connects to something I've written about before — the background scan, the nervous system running in a kind of permanent low-level threat detection mode. What that system needs to rest isn't silence. It needs to be released from decision load. Familiar music does that. An unfamiliar environment doesn't, regardless of how peaceful it looks from the outside.&lt;/p&gt;

&lt;p&gt;I think this is why a lot of autistic people have very specific, sometimes surprising rest rituals that look nothing like relaxation to others. It's not quirk or preference. It's load management.&lt;/p&gt;

&lt;p&gt;The well-meaning advice to "just relax" or "get some fresh air" isn't wrong about rest being necessary. It's using a definition of rest built for a different nervous system.&lt;/p&gt;

&lt;p&gt;What actually restores you might look nothing like what's supposed to.&lt;/p&gt;

</description>
      <category>mentalhealth</category>
      <category>inclusion</category>
      <category>community</category>
      <category>career</category>
    </item>
    <item>
      <title>Sharing is caring</title>
      <dc:creator>Raphaël Pinson</dc:creator>
      <pubDate>Mon, 25 May 2026 06:45:00 +0000</pubDate>
      <link>https://dev.to/raphink/sharing-is-caring-1bif</link>
      <guid>https://dev.to/raphink/sharing-is-caring-1bif</guid>
      <description>&lt;p&gt;Last month, I wrote a series on autism from the inside. The response surprised me — several people said it helped them understand someone in their life, or themselves. This is a follow-up on something I've been thinking about since.&lt;/p&gt;

&lt;p&gt;Autistic people who talk at length about their interests are easy to misread. They seem oblivious to whether you're engaged. They circle back to the same subject even after the conversation has moved on. From the outside, it looks like self-centeredness: I want to talk about this, so I will.&lt;/p&gt;

&lt;p&gt;I suggest the mechanism is almost the opposite.&lt;/p&gt;

&lt;p&gt;For an autistic brain, information isn't incidental. It's closer to what navigation instruments are to a pilot: not nice to have, but required to function. I've written before about the constant background scan — the nervous system collecting data continuously, because any gap in the map is a potential trapdoor. That's the context this runs in.&lt;/p&gt;

&lt;p&gt;If information has that level of value — survival-level value, not intellectual curiosity — then sharing information is the most generous thing you can do. When I've spent weeks or months going deep on a subject, and I find something that genuinely matters, the instinct to share it isn't "let me talk about myself." It's closer to "I found something you need to know."&lt;/p&gt;

&lt;p&gt;It's "I found water."&lt;/p&gt;

&lt;p&gt;The social form looks like monologue. The underlying intent is contribution, especially when this knowledge contributes to lowering anxiety, consciously or not.&lt;/p&gt;

&lt;p&gt;This also explains the other side of the equation: small talk. The common framing is that autistic people find it boring, or that we prefer "meaningful" conversation. That's not quite it either. The information channel runs in survival mode. Low-signal input — the weather, a filler comment, a pleasantry that carries no new information — doesn't just fail to help. It occupies bandwidth that the system is trying to keep clear. It's not boredom. It's closer to noise pollution in a critical instrument.&lt;/p&gt;

&lt;p&gt;The frustration when no one seems interested in what you're sharing, and the discomfort with small talk, come from the same place: a brain that has assigned extreme functional value to information, operating in a world where most social exchange treats information as incidental.&lt;/p&gt;

&lt;p&gt;None of this makes the social friction disappear. Knowing the mechanism doesn't mean the other person stops feeling talked over. But it changes the question. The question isn't "why are they so self-absorbed?" The question is: what does it mean to be generous when your native currency isn't attention, but knowledge?&lt;/p&gt;

&lt;p&gt;For a lot of autistic people, sharing is genuinely how we care. We're just not always aware that the gift doesn't always land the way it was meant.&lt;/p&gt;

</description>
      <category>mentalhealth</category>
      <category>inclusion</category>
      <category>community</category>
      <category>career</category>
    </item>
    <item>
      <title>Neurodiversity and the two layers of cognition</title>
      <dc:creator>Raphaël Pinson</dc:creator>
      <pubDate>Fri, 22 May 2026 10:46:47 +0000</pubDate>
      <link>https://dev.to/raphink/neurodiversity-and-the-two-layers-of-cognition-42dp</link>
      <guid>https://dev.to/raphink/neurodiversity-and-the-two-layers-of-cognition-42dp</guid>
      <description>&lt;p&gt;About twenty years ago, while studying Gestion Mentale, a pedagogy framework developed by French educator Antoine de la Garanderie, our group was asked to do a simple mental calculation. Something like 47+35. Then explain what happened in our heads.&lt;/p&gt;

&lt;p&gt;The results were staggering.&lt;/p&gt;

&lt;p&gt;One person talked to themselves through it. Another wrote the numbers on an imaginary blackboard, in their own handwriting. Someone else saw their primary school teacher's handwriting instead. One person had visual bars and immediate access to the result, with no intermediate steps they could describe. Ten people, ten different internal processes, one correct answer.&lt;/p&gt;

&lt;p&gt;Nobody had assumed everyone else did it the same way. But nobody had ever questioned it either, because there had never been a reason to ask.&lt;/p&gt;

&lt;p&gt;That exercise made something visible that is almost always invisible: the internal process and the expected output are two separate things, and they don't have to map onto each other in any particular way.&lt;br&gt;
I saw this confirmed during an internship with a Gestion Mentale practitioner working with a child struggling with long divisions. Over several sessions they had found a method that worked for the child, that he understood and could use reliably. Then the teacher called him to the board, he used his method, and she dismissed it. She hadn't taught it, she didn't recognize it, so as far as she was concerned it wasn't valid.&lt;/p&gt;

&lt;p&gt;The practitioner spent the next session reframing things. There are two layers, he told the child: how you perform a task, and what the world expects as output. Those are separate problems. Let's find a way to convert your method into the expected format.&lt;/p&gt;

&lt;p&gt;I've recently been writing about autism, following my own diagnosis at 43. Autism adds a cost to this picture. When your internal process doesn't map naturally onto what the social world expects as output, there is a translation layer running constantly — reading faces, calibrating tone, tracking when to speak and when to stop. For most people this is automatic, effectively free. For an autistic person it runs consciously, alongside every interaction.&lt;/p&gt;

&lt;p&gt;The result looks the same. The cost doesn't show. Which is why late diagnosis is so common: the output passes inspection, so nobody looks at the process.&lt;/p&gt;

&lt;p&gt;Happy to hear how this lands — particularly from those of you who recognize the translation cost from your own experience, whether or not you have a diagnosis.&lt;/p&gt;

</description>
      <category>mentalhealth</category>
      <category>inclusion</category>
      <category>community</category>
      <category>career</category>
    </item>
  </channel>
</rss>
