<?xml version="1.0" encoding="UTF-8"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom" version="2.0" xmlns:media="http://search.yahoo.com/mrss/"><channel><title><![CDATA[The Simplest Thing That Could Possibly Be Dangerous]]></title><description><![CDATA[Building things. Occasionally thinking them through.]]></description><link>https://jason.now/</link><image><url>https://jason.now/favicon.png</url><title>The Simplest Thing That Could Possibly Be Dangerous</title><link>https://jason.now/</link></image><generator>Ghost 6.18</generator><lastBuildDate>Thu, 12 Feb 2026 15:39:08 GMT</lastBuildDate><atom:link href="https://jason.now/rss/" rel="self" type="application/rss+xml"/><ttl>60</ttl><item><title><![CDATA[AI Water Usage and Orders of Magnitude]]></title><description><![CDATA[<p>I was well prepared for this, having read <a href="https://simonwillison.net/2025/Oct/18/the-ai-water-issue-is-fake/?ref=jason.now" rel="noreferrer">Simon&apos;s rollup</a> of <a href="https://andymasley.substack.com/p/the-ai-water-issue-is-fake?ref=jason.now" rel="noreferrer">the AI water issue is fake</a>, and sure enough not an hour has passed before I came across <a href="https://www.cbc.ca/news/ai-data-centre-canada-water-use-9.6939684?ref=jason.now" rel="noreferrer">AI-related data centres use vast amounts of water. But gauging how much is a murky business from our friends</a></p>]]></description><link>https://jason.now/ai-water-usage-and-orders-of-magnitude/</link><guid isPermaLink="false">68f55c6a7bdee00001483766</guid><dc:creator><![CDATA[Jason Doucette]]></dc:creator><pubDate>Sun, 19 Oct 2025 22:11:13 GMT</pubDate><media:content url="https://jason.now/content/images/2025/10/Toronto-waterfront-from-Tommy-Thompson-Park-1.jpeg" medium="image"/><content:encoded><![CDATA[<img src="https://jason.now/content/images/2025/10/Toronto-waterfront-from-Tommy-Thompson-Park-1.jpeg" alt="AI Water Usage and Orders of Magnitude"><p>I was well prepared for this, having read <a href="https://simonwillison.net/2025/Oct/18/the-ai-water-issue-is-fake/?ref=jason.now" rel="noreferrer">Simon&apos;s rollup</a> of <a href="https://andymasley.substack.com/p/the-ai-water-issue-is-fake?ref=jason.now" rel="noreferrer">the AI water issue is fake</a>, and sure enough not an hour has passed before I came across <a href="https://www.cbc.ca/news/ai-data-centre-canada-water-use-9.6939684?ref=jason.now" rel="noreferrer">AI-related data centres use vast amounts of water. But gauging how much is a murky business from our friends</a> at the CBC.</p><p>It would be less murky with some actual data!</p><p>Highlighting: Kathryn is concerned about a data centre planned to go into Nanaimo, British Columbia. She says that &quot;similar-sized facilities can churn through 70,000 litres of potable water a day.&quot;</p><p>And that sounds like a lot! I know this because I told my 12 year old and his eyes went really wide. But let&apos;s look at some Nanaimo stats:</p><p>Area population (2021): <a href="https://www12.statcan.gc.ca/census-recensement/2021/as-sa/fogs-spg/page.cfm?dguid=2021S0503938&amp;topic=1&amp;lang=e&amp;ref=jason.now" rel="noreferrer">115,459</a><br>Water usage by individuals (2024): <a href="https://www.nanaimo.ca/city-services/water-sewage/water-supply-and-treatment/reports?ref=jason.now" rel="noreferrer">179 litres per person per day</a><br>Total water usage (population times usage): <strong>20,667,161</strong> litres per day.</p><p>That&apos;s <strong>295 times</strong> the amount of water Kathryn suspects the data centre will use, or about 0.3%.</p><p>Put another way, if 391 people moved into the area, it&apos;d have equivalent impact. Interestingly, <a href="https://www12.statcan.gc.ca/census-recensement/2021/as-sa/fogs-spg/page.cfm?dguid=2021S0503938&amp;topic=1&amp;lang=e&amp;ref=jason.now" rel="noreferrer">10,523 people</a> moved into the area between 2016 and 2021.</p><p>This is not a perfect comparison, and some uses of water are recaptured and some aren&apos;t. One can also make the point that we should look at all uses of scarce resources and restrict additions to this total whenever possible.</p><p>But reporting in the style of &quot;oh no, big number is big&quot; doesn&apos;t help anything without establishing a relative scale.</p>]]></content:encoded></item><item><title><![CDATA[Vibe coding an Atari 2600 port of Fortnite]]></title><description><![CDATA[<p>The fine folks at Amazon randomly sent me an email about some kind of &quot;Build Games Challenge&quot; where if I built a retro game using <a href="https://aws.amazon.com/q/developer/?ref=jason.now" rel="noreferrer">Amazon Q Developer</a>&apos;s agentic coding tool I could get a t-shirt.</p><p>This offering seemed tailor made for me, as I don&</p>]]></description><link>https://jason.now/vibe-coding-an-atari-version-of-fortnite/</link><guid isPermaLink="false">6860671863ad6000013b9f4b</guid><dc:creator><![CDATA[Jason Doucette]]></dc:creator><pubDate>Sun, 29 Jun 2025 21:55:14 GMT</pubDate><media:content url="https://jason.now/content/images/2025/06/fortnitecartridge.png" medium="image"/><content:encoded><![CDATA[<img src="https://jason.now/content/images/2025/06/fortnitecartridge.png" alt="Vibe coding an Atari 2600 port of Fortnite"><p>The fine folks at Amazon randomly sent me an email about some kind of &quot;Build Games Challenge&quot; where if I built a retro game using <a href="https://aws.amazon.com/q/developer/?ref=jason.now" rel="noreferrer">Amazon Q Developer</a>&apos;s agentic coding tool I could get a t-shirt.</p><p>This offering seemed tailor made for me, as I don&apos;t have time to play video games, let alone make them, and I buy my t-shirts in bulk and wear the same plain navy blue shirt every day.</p><p>But I am willing to change my ways! So I embarked on a <a href="https://www.youtube.com/watch?v=cfR7qxtgCgY&amp;ref=jason.now" rel="noreferrer">three hour tour</a> to vibe code a retro game.</p><p>The first challenge: picking the game! &quot;Retro&quot; has a lot of meanings, but it usually is some combination of more than 20 years old and pixellated. It would probably have been easy enough to one-shot &quot;make me a Tetris clone&quot; since there are probably a bunch of those out there already that the AI models (it looks like Q uses Claude Sonnet) have trained on, but... then we&apos;d have yet another Tetris clone out there.</p><p>So I of course picked <a href="https://www.fortnite.com/?ref=jason.now" rel="noreferrer">Fortnite</a>.</p><p>Fortnite isn&apos;t old enough to be considered retro, plus it&apos;s constantly being updated, so by itself it wouldn&apos;t qualify, but I figured making a retro-styled port of the game would work, and if we&apos;re going retro, why not go way back to the near-beginning and target the <a href="https://en.wikipedia.org/wiki/Atari_2600?ref=jason.now" rel="noreferrer">Atari 2600</a> as the platform?</p><p>In case you&apos;re not familiar, the 2600 was one of the first home video game systems, and by far the most popular of its generation. Released in 1977 and continuing production until 1992 (!) it sold an estimated 30 million copies, which isn&apos;t as impressive now since the iPhone can surpass that number in a month or two, but... it was a different time, and that was a lot of consumer electronics.</p><p>Remember how I said 1977? Technology was a lot more limited then, and further constraints to reduce the price point made the Atari 2600 an incredibly limited machine. You can argue that constraints are what make games great, and there are certainly some real bangers in the back catalog, but let&apos;s compare <a href="https://www.epicgames.com/help/en-US/c-Category_Fortnite/c-Fortnite_TechnicalSupport/what-are-the-system-requirements-for-fortnite-on-pc-a000084912?ref=jason.now" rel="noreferrer">Fortnite&apos;s minimum system requirements</a> against the Atari&apos;s capabilities:</p><table>
<thead>
<tr>
<th>Spec</th>
<th>Fortnite</th>
<th>Atari</th>
</tr>
</thead>
<tbody>
<tr>
<td>Video card</td>
<td>Intel HD 4000 on PC; AMD Radeon Vega 8</td>
<td>The TIA chip, which can output... stuff... to a TV</td>
</tr>
<tr>
<td>CPU</td>
<td>Core i3-3225 3.3 GHz</td>
<td>The 6507, a scaled down version of the 6502, running at 1.19 MHz</td>
</tr>
<tr>
<td>RAM</td>
<td>8 gigabytes</td>
<td>128 bytes</td>
</tr>
</tbody>
</table>
<p>Oh, and without bank switching, which we won&apos;t even try to figure out, programs for the 2600 have to fit in 4 kilobytes of ROM, which I don&apos;t think is enough to even store the text in this post.</p><p>So, we have our work cut out for us. Or rather, Amazon Q does. I&apos;m not writing a line of this thing. But I thought it&apos;d be a great challenge - I hear about how some languages are better suited for LLM code generation because there are more examples out there on GitHub etc, but how many 6507 applications can there be?</p><p>Installing Q was pretty straightforward, and all I needed to do was open a new terminal window for it to take effect. It added some autocomplete options to the session, and running <code>q chat</code> got me up and running:</p><figure class="kg-card kg-image-card kg-card-hascaption"><img src="https://jason.now/content/images/2025/06/q-chat-1.png" class="kg-image" alt="Vibe coding an Atari 2600 port of Fortnite" loading="lazy" width="1537" height="1080" srcset="https://jason.now/content/images/size/w600/2025/06/q-chat-1.png 600w, https://jason.now/content/images/size/w1000/2025/06/q-chat-1.png 1000w, https://jason.now/content/images/2025/06/q-chat-1.png 1537w" sizes="(min-width: 720px) 720px"><figcaption><span style="white-space: pre-wrap;">The launch screen for Amazon q chat</span></figcaption></figure><p>The promo docs said they had a generous free tier, and I didn&apos;t hit it in the three hours or so I was working, and responses were pretty quick. I&apos;d previously used GitHub copilot and a lot of copy/paste with both ChatGPT and Claude web interfaces, but this was the first time I just used a terminal chat and didn&apos;t even look at the code.</p><p>The system has the ability to take actions on your computer, but you&apos;re in control of allowing it... kind of. Actions seem to be sorted into categories, and you have the choice of saying yes or no every time for a category, or selecting &quot;trust&quot; to let it happen every time. Categories are things like changing files, executing scripts, and so on.</p><figure class="kg-card kg-image-card kg-card-hascaption"><img src="https://jason.now/content/images/2025/06/Allowthisaction-1.png" class="kg-image" alt="Vibe coding an Atari 2600 port of Fortnite" loading="lazy" width="1533" height="251" srcset="https://jason.now/content/images/size/w600/2025/06/Allowthisaction-1.png 600w, https://jason.now/content/images/size/w1000/2025/06/Allowthisaction-1.png 1000w, https://jason.now/content/images/2025/06/Allowthisaction-1.png 1533w" sizes="(min-width: 720px) 720px"><figcaption><span style="white-space: pre-wrap;">An &quot;allow this action&quot; prompt in Q chat</span></figcaption></figure><p>Hilariously, the &quot;y&quot; and &quot;t&quot; options are right next to each other on the keyboard so I figured it would only be a matter of time before I accidentally enabled trust mode for an action, but I settled on trusting file writes and approving bash executions, just in case a rogue <code>rm -rf /</code> came along (it didn&apos;t.) But as with most things like this, I found myself treating the &quot;y&quot; key like a &quot;yeah, whatever&quot; button and didn&apos;t scrutinize the actions too closely before approving. But I had the illusion of control!</p><p>Now, back to the game. Before I even tried to design something I wanted to level set the capabilities of the system by trying to get something on the screen. Atari games run on cartridges, but for development I installed <a href="https://cc65.github.io/?ref=jason.now" rel="noreferrer">cc65</a> to build the assembly code and <a href="https://stella-emu.github.io/?ref=jason.now" rel="noreferrer">Stella</a> to emulate a system. Q set me up with a Makefile so the development workflow was along these lines:</p><ul><li>Prompt a change</li><li>q makes the change and asks permission to build</li><li>I say yes, and a new &quot;ROM&quot; is generated</li><li>Ctrl-R in Stella reloads the image and I review the changes</li></ul><p>Interestingly, on a few occasions Q would do a build and then jump right into another set of changes without any feedback, like it had thought up a better way to do something while the code compiled. Conversely, there were a few times where it would make the code changes but I had to ask for a build.</p><p>When we got to a checkpoint where something was workable, I&apos;d ask Q to commit to git, and it took care of all of that.</p><figure class="kg-card kg-image-card kg-card-hascaption"><img src="https://jason.now/content/images/2025/06/commit-1.png" class="kg-image" alt="Vibe coding an Atari 2600 port of Fortnite" loading="lazy" width="1504" height="1080" srcset="https://jason.now/content/images/size/w600/2025/06/commit-1.png 600w, https://jason.now/content/images/size/w1000/2025/06/commit-1.png 1000w, https://jason.now/content/images/2025/06/commit-1.png 1504w" sizes="(min-width: 720px) 720px"><figcaption><span style="white-space: pre-wrap;">A git commit via agents</span></figcaption></figure><p>But I&apos;m getting ahead of myself. Getting something on the screen was the hardest part of the project, which was kind of the point: I wanted to see if a modern LLM could even build workable 2600 code. There was about half an hour of getting things like this:</p><figure class="kg-card kg-image-card kg-card-hascaption"><img src="https://jason.now/content/images/2025/06/early-screen-1.png" class="kg-image" alt="Vibe coding an Atari 2600 port of Fortnite" loading="lazy" width="1300" height="1022" srcset="https://jason.now/content/images/size/w600/2025/06/early-screen-1.png 600w, https://jason.now/content/images/size/w1000/2025/06/early-screen-1.png 1000w, https://jason.now/content/images/2025/06/early-screen-1.png 1300w" sizes="(min-width: 720px) 720px"><figcaption><span style="white-space: pre-wrap;">An attempt at a 2600 monocular screen that... isn&apos;t</span></figcaption></figure><p>That was supposed to be a solid green screen, I think. Eventually we got something running, but it was a lot of me saying &quot;nope, not working&quot; with a brief attempt to describe what I was seeing.</p><p>This part (and a lot of the later phases) reminded me of some jobs I&apos;ve had where developers would just throw code back over the fence for user testing where it was clear they hadn&apos;t tried it at all. And in fairness, I guess that&apos;s the state of things right now. But if we don&apos;t have it at the time of this writing, I figure it won&apos;t be long before coding agents have some level of validation built into the workflow, either through assessing automated test results or actually looking at the screen. If I could have that, each phase would just be a prompt and a trip out for coffee while the machine figured things out, which would be a really interesting change (does Cursor or Windsurf do this yet?)</p><p>But after an hour or so we got to a &quot;Hello World&quot; screen, or at least the 2600 equivalent:</p><figure class="kg-card kg-image-card kg-card-hascaption"><img src="https://jason.now/content/images/2025/06/hello-2-1.png" class="kg-image" alt="Vibe coding an Atari 2600 port of Fortnite" loading="lazy" width="1306" height="835" srcset="https://jason.now/content/images/size/w600/2025/06/hello-2-1.png 600w, https://jason.now/content/images/size/w1000/2025/06/hello-2-1.png 1000w, https://jason.now/content/images/2025/06/hello-2-1.png 1306w" sizes="(min-width: 720px) 720px"><figcaption><span style="white-space: pre-wrap;">&quot;Hello&quot; on the screen</span></figcaption></figure><p>See the weird glitches where lines seem to start a little early or late? Get used to that. The 2600, as I understand it, was closely tied to CRT scanline output that televisions of the era used, to the point where the code actually had to time out instructions as the beam ran across the screen. I had a lot of sections where the screen would jump a line or two up or down, and the bottom line of the screen often was only half drawn.</p><p>But close enough! It was time to get going on the game. Obviously networked multiplayer was out, but I was envisioning something kind of like Atari&apos;s Combat game, with a 1v1 style play, maybe a few bits of scenery on the screen, and some weapons and medkits to pick up (there&apos;s only one button on the controller, so inventory management would be just &quot;you get whatever you last picked up&quot;)</p><p>I also thought it&apos;d be funny to have a &quot;skin shop&quot; where you could buy different colours of characters.</p><p>I was overly ambitious, but I think the limitations were more with the AI than the 2600.</p><p>Getting a player on the screen that I could move around took no time at all, and moving up and down was silky smooth. However, the system had a really hard time with left to right movement and I had to revert the code a number of times. I&apos;ve played a few Atari games in my day, and I don&apos;t recall having trouble moving, say, the Space Invaders shooter back and forth, but the best the AI could come up with was a set number of fixed positions horizontally to move between, and if it got too close to the edge, the player would just disappear.</p>
<!--kg-card-begin: html-->
<img src="https://images.thrustlabs.com/jasonnow/Fortnite%202600%20man%20moving%201.gif" alt="Vibe coding an Atari 2600 port of Fortnite">
<!--kg-card-end: html-->
<p>The next step was to get some scenery to dress up the playfield. That... did not go well. I&apos;ll spare you the high-strobe gif, but things looked more or less like this:</p><figure class="kg-card kg-image-card kg-card-hascaption"><img src="https://jason.now/content/images/2025/06/playfield-1.png" class="kg-image" alt="Vibe coding an Atari 2600 port of Fortnite" loading="lazy" width="1285" height="1008" srcset="https://jason.now/content/images/size/w600/2025/06/playfield-1.png 600w, https://jason.now/content/images/size/w1000/2025/06/playfield-1.png 1000w, https://jason.now/content/images/2025/06/playfield-1.png 1285w" sizes="(min-width: 720px) 720px"><figcaption><span style="white-space: pre-wrap;">Terrible playfield</span></figcaption></figure><p>Once again, I reverted my changes to the last good commit and tried to get shooting to work. The LLM wasn&apos;t able to get the fire button to detect reliably, and again, left and right shots were problematic because scrolling was hard. To work around it, Q decided on its own to just have auto-fire based on the last direction (up down left right, you&apos;re dreaming if you think we&apos;re getting diagonals,) but that was after an amusing suggestion to use pressing up and down at the same time to simulate the fire button, which can be done in an emulator but not on an actual physical joystick.</p>
<!--kg-card-begin: html-->
<img src="https://images.thrustlabs.com/jasonnow/Fortnite%202600%20man%20shooting%202.gif" alt="Vibe coding an Atari 2600 port of Fortnite">
<!--kg-card-end: html-->
<p>You can kind of see shots to the right and left, but it was inconsistent and terrible. Still, I needed shooting to make an enemy make sense in a Fortnite game, so I kept it and moved on to an enemy. I figured multiple bad guys would be too much of a stretch, so tried for a single opponent.</p><p>Here we ran into all the previous problems: the enemy couldn&apos;t move left or right either. I didn&apos;t even get into collision detection for people to actually get shot, because I could see that the game would be pretty unplayable as it was going.</p>
<!--kg-card-begin: html-->
<div id="gif-container" style="display:inline-block; cursor:pointer;">
  <img id="gif-placeholder" src="https://images.thrustlabs.com/jasonnow/enemy117.png" alt="Vibe coding an Atari 2600 port of Fortnite">
</div>

<script>
  const container = document.getElementById("gif-container");
  const placeholder = document.getElementById("gif-placeholder");
  const gifUrl = "https://images.thrustlabs.com/jasonnow/Fortnite%202600%20enemy.gif";

  container.addEventListener("click", () => {
    const gif = document.createElement("img");
    gif.src = gifUrl;
    gif.alt = "Animated Fortnite 2600-style enemy";
    container.innerHTML = "";
    container.appendChild(gif);
  });
</script>
<!--kg-card-end: html-->
<p>So no scenery, no enemies... How exactly would this be Fortnite? And then it hit me: the storm. Staying in zone is a big part of the game, where the gameplay area continues to shrink over the course of the game to force players to come out of hiding and fight it out to the last one standing. My port would have to be exclusively about staying out of the storm. And since we can&apos;t move left and right very well, it&apos;d have to be a vertical game, which saves the trouble of trying to get circles appearing on the board. Green is safe, red is deadly, and yellow is &quot;about to toggle.&quot;</p><p>So without further ado, here&apos;s the world&apos;s first, only, and therefore best port of Fortnite for the Atari 2600:</p><figure class="kg-card kg-video-card kg-width-regular" data-kg-thumbnail="https://jason.now/content/media/2025/06/Fortnite-2600-demo_thumb.jpg" data-kg-custom-thumbnail>
            <div class="kg-video-container">
                <video src="https://storage.ghost.io/c/1a/27/1a27293b-223a-4156-94ad-5631a059cb1d/content/media/2025/06/Fortnite-2600-demo.mp4" poster="https://img.spacergif.org/v1/1920x1080/0a/spacer.png" width="1920" height="1080" playsinline preload="metadata" style="background: transparent url(&apos;https://storage.ghost.io/c/1a/27/1a27293b-223a-4156-94ad-5631a059cb1d/content/media/2025/06/Fortnite-2600-demo_thumb.jpg&apos;) 50% 50% / cover no-repeat;"></video>
                <div class="kg-video-overlay">
                    <button class="kg-video-large-play-icon" aria-label="Play video">
                        <svg xmlns="http://www.w3.org/2000/svg" viewbox="0 0 24 24">
                            <path d="M23.14 10.608 2.253.164A1.559 1.559 0 0 0 0 1.557v20.887a1.558 1.558 0 0 0 2.253 1.392L23.14 13.393a1.557 1.557 0 0 0 0-2.785Z"/>
                        </svg>
                    </button>
                </div>
                <div class="kg-video-player-container">
                    <div class="kg-video-player">
                        <button class="kg-video-play-icon" aria-label="Play video">
                            <svg xmlns="http://www.w3.org/2000/svg" viewbox="0 0 24 24">
                                <path d="M23.14 10.608 2.253.164A1.559 1.559 0 0 0 0 1.557v20.887a1.558 1.558 0 0 0 2.253 1.392L23.14 13.393a1.557 1.557 0 0 0 0-2.785Z"/>
                            </svg>
                        </button>
                        <button class="kg-video-pause-icon kg-video-hide" aria-label="Pause video">
                            <svg xmlns="http://www.w3.org/2000/svg" viewbox="0 0 24 24">
                                <rect x="3" y="1" width="7" height="22" rx="1.5" ry="1.5"/>
                                <rect x="14" y="1" width="7" height="22" rx="1.5" ry="1.5"/>
                            </svg>
                        </button>
                        <span class="kg-video-current-time">0:00</span>
                        <div class="kg-video-time">
                            /<span class="kg-video-duration">0:40</span>
                        </div>
                        <input type="range" class="kg-video-seek-slider" max="100" value="0">
                        <button class="kg-video-playback-rate" aria-label="Adjust playback speed">1&#xD7;</button>
                        <button class="kg-video-unmute-icon" aria-label="Unmute">
                            <svg xmlns="http://www.w3.org/2000/svg" viewbox="0 0 24 24">
                                <path d="M15.189 2.021a9.728 9.728 0 0 0-7.924 4.85.249.249 0 0 1-.221.133H5.25a3 3 0 0 0-3 3v2a3 3 0 0 0 3 3h1.794a.249.249 0 0 1 .221.133 9.73 9.73 0 0 0 7.924 4.85h.06a1 1 0 0 0 1-1V3.02a1 1 0 0 0-1.06-.998Z"/>
                            </svg>
                        </button>
                        <button class="kg-video-mute-icon kg-video-hide" aria-label="Mute">
                            <svg xmlns="http://www.w3.org/2000/svg" viewbox="0 0 24 24">
                                <path d="M16.177 4.3a.248.248 0 0 0 .073-.176v-1.1a1 1 0 0 0-1.061-1 9.728 9.728 0 0 0-7.924 4.85.249.249 0 0 1-.221.133H5.25a3 3 0 0 0-3 3v2a3 3 0 0 0 3 3h.114a.251.251 0 0 0 .177-.073ZM23.707 1.706A1 1 0 0 0 22.293.292l-22 22a1 1 0 0 0 0 1.414l.009.009a1 1 0 0 0 1.405-.009l6.63-6.631A.251.251 0 0 1 8.515 17a.245.245 0 0 1 .177.075 10.081 10.081 0 0 0 6.5 2.92 1 1 0 0 0 1.061-1V9.266a.247.247 0 0 1 .073-.176Z"/>
                            </svg>
                        </button>
                        <input type="range" class="kg-video-volume-slider" max="100" value="100">
                    </div>
                </div>
            </div>
            
        </figure><p>I was going to try for a few more features, but q had other ideas:</p><figure class="kg-card kg-image-card kg-card-hascaption"><img src="https://jason.now/content/images/2025/06/game-complete-1.png" class="kg-image" alt="Vibe coding an Atari 2600 port of Fortnite" loading="lazy" width="1518" height="1080" srcset="https://jason.now/content/images/size/w600/2025/06/game-complete-1.png 600w, https://jason.now/content/images/size/w1000/2025/06/game-complete-1.png 1000w, https://jason.now/content/images/2025/06/game-complete-1.png 1518w" sizes="(min-width: 720px) 720px"><figcaption><span style="white-space: pre-wrap;">It thinks we&apos;re done, so we&apos;re done</span></figcaption></figure><p>At this point, if Q thinks it&apos;s a complete game, who am I to argue?</p><p>Overall, Amazon Q Developer gave a solid experience, and there&apos;s a lot happening in this space so I&apos;m looking forward to trying a few more things. The free tier definitely made this one more attractive than others, but apparently I have access to a few more with the various subscriptions I&apos;ve picked up, so I&apos;ll give a few more a try. Just maybe not for the 2600.</p>]]></content:encoded></item><item><title><![CDATA[Doom unto all]]></title><description><![CDATA[<p>Via <a href="https://kottke.org/25/05/0046941-you-can-play-doom-in?ref=jason.now" rel="noreferrer">Kottke</a>: in an NYT article about Doom&apos;s ability to be run on just about anything, they made a point of embedding Doom into the article.</p><p>I haven&apos;t checked (or actually read the article,) but I&apos;m assuming they used a Webassembly port <a href="https://github.com/cloudflare/doom-wasm?ref=jason.now" rel="noreferrer">similar to</a></p>]]></description><link>https://jason.now/doom-unto-all/</link><guid isPermaLink="false">6838e0cb0e567e0001d678e0</guid><dc:creator><![CDATA[Jason Doucette]]></dc:creator><pubDate>Fri, 30 May 2025 12:01:33 GMT</pubDate><media:content url="https://jason.now/content/images/2025/05/doomtitle-1.jpg" medium="image"/><content:encoded><![CDATA[<img src="https://jason.now/content/images/2025/05/doomtitle-1.jpg" alt="Doom unto all"><p>Via <a href="https://kottke.org/25/05/0046941-you-can-play-doom-in?ref=jason.now" rel="noreferrer">Kottke</a>: in an NYT article about Doom&apos;s ability to be run on just about anything, they made a point of embedding Doom into the article.</p><p>I haven&apos;t checked (or actually read the article,) but I&apos;m assuming they used a Webassembly port <a href="https://github.com/cloudflare/doom-wasm?ref=jason.now" rel="noreferrer">similar to this one</a> to embed it, which is one of my favourite party tricks. I did something similar once on a company&apos;s <a href="https://www.domo.com/?ref=jason.now" rel="noreferrer">Domo</a> instance to create... wait for it... Doomo.</p><p>For my use case, I couldn&apos;t just leave it there, and added some business data to the game&apos;s build (passed as a launch parameter to the game) to make it a relevant BI extension and not just me Dooming all the things. But I needed something to trigger the information display (I couldn&apos;t just show it; knowledge must be <em>earned</em>.)</p><p>This became problematic for the demo (which was really just a lighthearted showcase of silly Domo tricks) because I had the sense to realize before presenting that I was still in a workplace, and showing off a violent video game where one would have to use virtual firearms to get the business data probably wasn&apos;t an HR-friendly vibe.</p><p>My compromise? The BI data would show when you took damage from an exploding barrel, which was probably a deeper metaphor than I intended, but such was morale at the time.</p>]]></content:encoded></item><item><title><![CDATA[Fireflies are on the decline]]></title><description><![CDATA[<p>If ever there was an example of how &quot;dot now&quot; is a prompt for whatever&apos;s taken over my mind in the moment...</p><p>When I was a kid, fireflies were abundant. I don&apos;t think we ever caught them in jars, but I absolutely remember briefly</p>]]></description><link>https://jason.now/fireflies-are-on-the-decline/</link><guid isPermaLink="false">683592060649a7000143a296</guid><dc:creator><![CDATA[Jason Doucette]]></dc:creator><pubDate>Tue, 27 May 2025 10:41:25 GMT</pubDate><media:content url="https://jason.now/content/images/2025/05/Photinus_pyralis_Firefly_3.jpg" medium="image"/><content:encoded><![CDATA[<img src="https://jason.now/content/images/2025/05/Photinus_pyralis_Firefly_3.jpg" alt="Fireflies are on the decline"><p>If ever there was an example of how &quot;dot now&quot; is a prompt for whatever&apos;s taken over my mind in the moment...</p><p>When I was a kid, fireflies were abundant. I don&apos;t think we ever caught them in jars, but I absolutely remember briefly catching them between my hands, and since I also remember being really clumsy there must have been a large enough quantity for me to catch at least one.</p><p>I can&apos;t remember the last time I saw one, to the point where I had to check with a family member that this actually used to happen. Yep, it was a thing. Nope, it&apos;s not anymore.</p><p>Which we decided makes sense. Why did fireflies evolve to light up in the first place? What evolutionary advantage would a light up butt have, effectively carrying around a bright &quot;the kitchen is open&quot; sign for all the birds and bats to home in on? Were we just witnessing a failed evolutionary A/B test, like nature tried out glowing butts, saw how it went, and quietly rolled it back?</p><p>No, we&apos;re just dumb. It turns out the lights on a firefly are a warning to predators. Humans might have managed to survive with logic like &quot;oh, a shiny bug, must be food&quot; but apparently the rest of the world knows that bright shiny things are poisonous. It&apos;s called <a href="https://en.wikipedia.org/wiki/Aposematism?ref=jason.now" rel="noreferrer">aposematism</a>, which can basically be described as &quot;warning colouration.&quot; Bright colours == stay away, basically. Unless you&apos;re of the same species, and then it&apos;s some kind of mating signal.</p><p>In fact, researchers are theorizing that <a href="https://www.freethink.com/science/firefly-aposematic-signal?ref=jason.now" rel="noreferrer">fireflies even have a secondary &quot;musical&quot; aposematic signal</a> that alerts bats, who don&apos;t see as well as birds, to look elsewhere for their meal.</p><p>So why are fireflies disappearing? Other than the usual theories about pollution and removal of green space, apparently light pollution is also a factor, making it harder for fireflies to find each other and mate.</p><p>No business tips or analogies here, sometimes it&apos;s more than enough to sit back and marvel. But I miss the light show.</p><p><em>Photo: </em><a href="https://www.flickr.com/photos/16849297@N00/198487523/?ref=jason.now" rel="noreferrer"><em>firefly 8823</em></a><em> by Terry Priest, </em><a href="https://creativecommons.org/licenses/by-sa/2.0/deed.en?ref=jason.now" rel="noreferrer"><em>CC BY-SA 2.0</em></a></p>]]></content:encoded></item><item><title><![CDATA[Sometimes AI remembers the wrong me]]></title><description><![CDATA[<p>Simon Willison has some thoughts on ChatGPT&apos;s new memory dossier (title spoiler: <a href="https://simonwillison.net/2025/May/21/chatgpt-new-memory/?ref=jason.now" rel="noreferrer">he doesn&apos;t like it</a>.) He&apos;s finding that his past queries are influencing new responses, which on the surface sounds like a feature, but...</p><blockquote>&quot;I try a lot of stupid things with</blockquote>]]></description><link>https://jason.now/sometimes-ai-remembers-the-wrong-me/</link><guid isPermaLink="false">68321945f49ec40001a17b7c</guid><dc:creator><![CDATA[Jason Doucette]]></dc:creator><pubDate>Sat, 24 May 2025 19:40:20 GMT</pubDate><media:content url="https://jason.now/content/images/2025/05/GPT-Memory.png" medium="image"/><content:encoded><![CDATA[<img src="https://jason.now/content/images/2025/05/GPT-Memory.png" alt="Sometimes AI remembers the wrong me"><p>Simon Willison has some thoughts on ChatGPT&apos;s new memory dossier (title spoiler: <a href="https://simonwillison.net/2025/May/21/chatgpt-new-memory/?ref=jason.now" rel="noreferrer">he doesn&apos;t like it</a>.) He&apos;s finding that his past queries are influencing new responses, which on the surface sounds like a feature, but...</p><blockquote>&quot;I try a lot of stupid things with these models. I really don&#x2019;t want my fondness for dogs wearing pelican costumes to affect my future prompts where I&#x2019;m trying to get actual work done!&quot;</blockquote><p>I too, try a lot of stupid things. <a href="https://jason.now/ai-has-the-most-dangerous-demos/" rel="noreferrer">As I mentioned before</a>,</p><blockquote>&quot;I&#x2019;ve been spending some time lately trying to get AI to do things that I&#x2019;m not very good at personally. I don&#x2019;t expect amazing outcomes and these aren&#x2019;t high stakes activities (and that&#x2019;s a good thing; more on that in a sec,) but while I don&#x2019;t have enough free time to, say, write a book or create an animated film, these are fun things to imagine (the &#x201C;when I retire&#x201D; myth) and I have enough spare time to see if AI can do these things for me.&quot;</blockquote><p>The trouble is, ChatGPT&apos;s memory feature can&apos;t seem to tell the difference between what I&apos;ve actually done and what I&apos;ve just daydreamed about (in fairness, <a href="https://en.wikipedia.org/wiki/Source-monitoring_error?ref=jason.now" rel="noreferrer">humans have that problem too</a>.)</p><p>In my experience, this has only been a problem when I try the various meme prompts like the <a href="https://x.com/archedark_/status/1910381815862276130?ref=jason.now" rel="noreferrer">CIA dossier</a> but hey, maybe I&apos;m just practicing good security by adding noise to the signal.</p><p>In a past life, I&apos;d see this as a product problem that would best be solved by some kind of persona system, but wow, that&apos;d be exhausting to maintain (are you really going to remember to swap between &quot;work mode&quot; and &quot;goofball&quot; mode mid-thread every time?) </p><p>I did like the old memory system where I could prune the list if it remembered things I didn&apos;t think were relevant, but I think the eventual outcome is that memory will get better at being relevant, and we&apos;ll also stop worrying about it as much. Real life interactions are going to be biased by past conversations too, and my weird questions when I&apos;m bored are likely going to be weighted as just that over time.</p><p>Until then, a little bit of weirdness inspired by my personality is just going to make things more whimsical. Could be worse.</p>]]></content:encoded></item><item><title><![CDATA[Turns Out I’m Not Famous (or in the Force)]]></title><description><![CDATA[<blockquote>&quot;Separated at Birth was a police program you used in missing persons cases. You scanned a photo of the person you wanted, got back the names of half a dozen celebrities who looked vaguely like the subject, then went around asking people if they&apos;d seen anybody lately</blockquote>]]></description><link>https://jason.now/turns-out-im-not-famous-or-in-the-force/</link><guid isPermaLink="false">683079d9c6cc9f0001a48b1b</guid><dc:creator><![CDATA[Jason Doucette]]></dc:creator><pubDate>Fri, 23 May 2025 15:06:26 GMT</pubDate><media:content url="https://jason.now/content/images/2025/05/police-lineup.jpg" medium="image"/><content:encoded><![CDATA[<blockquote>&quot;Separated at Birth was a police program you used in missing persons cases. You scanned a photo of the person you wanted, got back the names of half a dozen celebrities who looked vaguely like the subject, then went around asking people if they&apos;d seen anybody lately who reminded them of A, B, C ... The weird thing was, it worked better than just showing them a picture of the subject. The instructor at the Academy in Knoxville had told Rydell&apos;s class that that was because it tapped into the part of the brain that kept tracked of celebrities. Rydell had imagined that as some kind of movie-star lobe. Did people really have those?&quot;</blockquote><img src="https://jason.now/content/images/2025/05/police-lineup.jpg" alt="Turns Out I&#x2019;m Not Famous (or in the Force)"><p><em>Virtual Light</em> by William Gibson, 1993</p><p>Via the always overwhelmingly delightful <a href="https://webcurios.co.uk/?ref=jason.now" rel="noreferrer">Web Curios</a>, I present <a href="https://coppelganger.lav.io/?ref=jason.now" rel="noreferrer">Coppleg&#xE4;nger</a>, a facial recognition tool that tells you what... NYPD officer you look like. So, full circle?</p><p>Odd Thing The First: While that Gibson passage above is one of the few things I remember about that book thirty (!) years later, it&apos;s never occurred to me to look for online tools that tell me what celebrity I look like. It turns out there are a lot of them!</p><p>Odd Thing The Second: While I did try out &quot;upload my own picture to a random website&quot; to see what cop I look like, somehow I was more comfortable doing that than uploading my photo to a celebrity matcher. Small scale web art projects engendering (hopefully not misplaced) trust and all that.</p><p>Anyway, I got three matches, but it&apos;s the closest matches, not perfect matches, and an impartial observer who is much better at recognizing people than I am has assured me that I don&apos;t look like a New York police officer. But apparently the system only has about 30% of the force represented, so I guess I just don&apos;t look like those people. So there&apos;s two pieces of personal info shared today.</p><figure class="kg-card kg-image-card"><img src="https://jason.now/content/images/2025/05/nypdbadge.png" class="kg-image" alt="Turns Out I&#x2019;m Not Famous (or in the Force)" loading="lazy" width="1024" height="1024" srcset="https://jason.now/content/images/size/w600/2025/05/nypdbadge.png 600w, https://jason.now/content/images/size/w1000/2025/05/nypdbadge.png 1000w, https://jason.now/content/images/2025/05/nypdbadge.png 1024w" sizes="(min-width: 720px) 720px"></figure><p>(Not a real badge, but yes, an AI-assisted one, with strong <a href="https://jason.now/ai-has-the-most-dangerous-demos/" rel="noreferrer">Dangerous Demos</a>/why am I not just doing this myself vibes)</p>]]></content:encoded></item><item><title><![CDATA[AI has the most dangerous demos]]></title><description><![CDATA[<p>I&#x2019;ve been spending some time lately trying to get AI to do things that I&#x2019;m not very good at personally. I don&#x2019;t expect amazing outcomes and these aren&#x2019;t high stakes activities (and that&#x2019;s a good thing; more on that in</p>]]></description><link>https://jason.now/ai-has-the-most-dangerous-demos/</link><guid isPermaLink="false">682f8a6897621300015a363a</guid><dc:creator><![CDATA[Jason Doucette]]></dc:creator><pubDate>Thu, 22 May 2025 21:38:05 GMT</pubDate><media:content url="https://jason.now/content/images/2025/05/IMG_1662.jpeg" medium="image"/><content:encoded><![CDATA[<img src="https://jason.now/content/images/2025/05/IMG_1662.jpeg" alt="AI has the most dangerous demos"><p>I&#x2019;ve been spending some time lately trying to get AI to do things that I&#x2019;m not very good at personally. I don&#x2019;t expect amazing outcomes and these aren&#x2019;t high stakes activities (and that&#x2019;s a good thing; more on that in a sec,) but while I don&#x2019;t have enough free time to, say, write a book or create an animated film, these are fun things to imagine (the &#x201C;when I retire&#x201D; myth) and I have enough spare time to see if AI can do these things for me.</p><p>People with jobs in the creative fields, do not worry! I am absolutely not taking money out of your pockets because a) I&#x2019;m mostly messing around and wouldn&#x2019;t know what to do with a finished product if I actually got one, and b) the results are very very much not finished products.</p><p>But wait! I see countless posts from though leaders where they&#x2019;re effortlessly making things with AI, and YouTube is filled with cool demos, either from vendors or newly established &#x201C;experts&#x201D; in a field that&#x2019;s in many cases only a few weeks or months old. There must be something wrong with my prompts!</p><p>Yeah, I should know better. My field of expertise is programming, and I&#x2019;ve made my share of widgets with Claude or ChatGPT, but I know they&#x2019;re a million miles away from a full production application. I still believe strongly that I can use my knowledge to assemble a collection of AI-generated widgets into an app, but&#x2026; that&#x2019;s work, and making a silly example widget is way more fun.</p><p><strong>That&#x2019;s danger number one of the demos:</strong> we&#x2019;re so distracted making instant toys that we lose sight of build targets that are actually valuable.</p><p>I think that carries through to most of the demos I see. Which is absolutely shocking, right? I mean, I saw a demo where someone typed in &#x201C;make me a sales proposal for a pharma customer&#x201D; and the AI tool generated a beautiful pitch deck, so that problem&#x2019;s obviously solved. Except the proposal is of course completely generic, incomplete, and lacks any connection to my actual business, because how can it do otherwise with what little information has been provided?</p><p><strong>That brings me to danger number two,</strong> and we&#x2019;re seeing it start to spread like wildfire. Executives are seeing these demos and making big bets on optimistic early results. These bets involve significant staffing cuts, because AI can handle the load. But can it? Or will companies be left with surface level solutions and massive gaps in operational capabilities from the holes they put in their org charts that AI won&#x2019;t be able to cover?</p><p>Microsoft uses the term Copilot really well with their AI tool suite, and I like that a lot: it&#x2019;s a copilot meant to assist you with your day to day work. But reportedly that same <a href="https://www.itpro.com/software/development/developers-will-need-to-adapt-microsoft-ceo-satya-nadella-joins-googles-sundar-pichai-in-revealing-the-scale-of-ai-generated-code-at-the-tech-giants-and-its-a-stark-warning-for-software-developers?ref=jason.now" rel="noreferrer">Microsoft is now implementing AI code generating quotas and cutting developer teams</a> because AI will take the load. We&#x2019;re told from an early age that we can&#x2019;t have our cake and eat it too, but we&#x2019;ve also been told repeatedly that AI changes all the rules, so&#x2026; maybe? But also maybe only maybe if you&#x2019;re a company that knows your stuff really well and also builds the tool to augment that knowledge. That won&#x2019;t be most companies.</p><p>I remain bullish about AI&#x2019;s ability to improve individual productivity. But I also know that just because I can get the latest video model to make an amazing 10 second clip, I have no idea how to make enough of them that look consistent and stitch together to tell a compelling story. </p><p>So you won&#x2019;t see my video opus on YouTube anytime soon, but don&#x2019;t worry, there&#x2019;ll be plenty of posts about the cool new way to make that 10s fragment from the latest expert to keep you entertained in the meantime.</p>]]></content:encoded></item><item><title><![CDATA[Microsoft’s AI Security Chief eats some dogfood]]></title><description><![CDATA[<p><a href="https://www.theverge.com/news/671373/microsoft-ai-security-chief-walmart-conversation-build-protest-disruption?ref=jason.now" rel="noreferrer">Microsoft&#x2019;s AI security chief accidentally reveals Walmart&#x2019;s AI plans after protest.</a> There was a protest at their Build event, and when the screen sharing went back up, it wasn&#x2019;t the slide deck that went up on the big screen, but rather an MS Teams</p>]]></description><link>https://jason.now/microsofts-ai-security-chief-eats-some-dogfood/</link><guid isPermaLink="false">682f2c10ffc2cf0001a5cd1a</guid><dc:creator><![CDATA[Jason Doucette]]></dc:creator><pubDate>Thu, 22 May 2025 14:27:02 GMT</pubDate><media:content url="https://jason.now/content/images/2025/05/0F34171C-0173-4161-85A4-415A9B68E99C.png" medium="image"/><content:encoded><![CDATA[<img src="https://jason.now/content/images/2025/05/0F34171C-0173-4161-85A4-415A9B68E99C.png" alt="Microsoft&#x2019;s AI Security Chief eats some dogfood"><p><a href="https://www.theverge.com/news/671373/microsoft-ai-security-chief-walmart-conversation-build-protest-disruption?ref=jason.now" rel="noreferrer">Microsoft&#x2019;s AI security chief accidentally reveals Walmart&#x2019;s AI plans after protest.</a> There was a protest at their Build event, and when the screen sharing went back up, it wasn&#x2019;t the slide deck that went up on the big screen, but rather an MS Teams chat with sensitive discussions.</p><p>This happens to me pretty much every time I share screens, which is all the more annoying because I tend to start recording before I hit share on a group call. Sharing a second monitor (that doesn&#x2019;t have Teams on it) is the only way I&#x2018;ve been able to mitigate this, other than simply not having a lot of sensitive chats.</p><p>Maybe now that someone with security in their title has had it happen rather publicly we might see the product teams take notice. Maybe.</p>]]></content:encoded></item><item><title><![CDATA[Shortcuts Don’t Skip the Climb]]></title><description><![CDATA[<p>Well, it happened. My teenage son said, &#x201C;By the time I need English, I won&#x2019;t need English.&#x201D;</p><p>Ironically, that&#x2019;s a pretty clever use of English. He explained that with tools like Grammarly and ChatGPT, he doesn&#x2019;t see much value in putting extra</p>]]></description><link>https://jason.now/shortcuts-dont-skip-the-climb/</link><guid isPermaLink="false">67fe6d35874c290001d9ce05</guid><dc:creator><![CDATA[Jason Doucette]]></dc:creator><pubDate>Tue, 15 Apr 2025 14:31:32 GMT</pubDate><media:content url="https://jason.now/content/images/2025/04/IMG_5460-1.jpeg" medium="image"/><content:encoded><![CDATA[<img src="https://jason.now/content/images/2025/04/IMG_5460-1.jpeg" alt="Shortcuts Don&#x2019;t Skip the Climb"><p>Well, it happened. My teenage son said, &#x201C;By the time I need English, I won&#x2019;t need English.&#x201D;</p><p>Ironically, that&#x2019;s a pretty clever use of English. He explained that with tools like Grammarly and ChatGPT, he doesn&#x2019;t see much value in putting extra effort into English class. Other subjects feel more demanding to him right now. (To be clear, he&#x2019;s in no academic danger. He&#x2019;s just&#x2026; coasting.)</p><p>But it got me thinking.</p><p>Over the past couple of years, AI has helped me get better at things I was already decent at. It&#x2019;s great for quick answers about plumbing, Pok&#xE9;mon, astronomy, and so on. But I can&#x2019;t think of anything I was truly bad at that I&#x2019;ve become even halfway competent in, just because of AI.</p><p>That might say more about me than the technology. Maybe if I followed an AI-driven curriculum, carved out dedicated practice time, and approached it with real intent, I could make that kind of progress.</p><p>But isn&#x2019;t that the kind of effort AI was supposed to save me from?</p><p>Maybe it&#x2019;s work either way. Maybe AI just makes the work more personal, more focused, and more enjoyable than any learning method we&#x2019;ve had before.</p><p>(And yes, I still mourn the slow fading of a traditional general arts education. I&#x2019;ve mourned it for decades. I don&#x2019;t think schools assign classic literature just because they can&#x2019;t afford new books. But it&#x2019;s hard to see the deeper value when you&#x2019;re sitting in a classroom full of restless teenagers.)</p>]]></content:encoded></item><item><title><![CDATA[John Carmack on AI in game dev]]></title><description><![CDATA[<p>&quot;<a href="https://x.com/ID_AA_Carmack/status/1909311174845329874?ref=jason.now" rel="noreferrer">My first games involved hand assembling machine code and turning graph paper characters into hex digits.  Software progress has made that work as irrelevant as chariot wheel maintenance.</a>&quot;</p><p>John&apos;s talking about tooling (computers are probably the ultimate tools to make tools,) but let&apos;s not</p>]]></description><link>https://jason.now/john-carmack-on-ai-in-game-dev/</link><guid isPermaLink="false">67f9225aba798a0001daece1</guid><dc:creator><![CDATA[Jason Doucette]]></dc:creator><pubDate>Fri, 11 Apr 2025 14:25:35 GMT</pubDate><content:encoded><![CDATA[<p>&quot;<a href="https://x.com/ID_AA_Carmack/status/1909311174845329874?ref=jason.now" rel="noreferrer">My first games involved hand assembling machine code and turning graph paper characters into hex digits.  Software progress has made that work as irrelevant as chariot wheel maintenance.</a>&quot;</p><p>John&apos;s talking about tooling (computers are probably the ultimate tools to make tools,) but let&apos;s not discount the increases in compute capability. Let&apos;s put his &quot;first games&quot; phase at 1990 for the sake of making a nice even number. Wow, computers were slow then vs 2025.</p>
<!--kg-card-begin: html-->
<table style="caret-color: rgb(0, 0, 0); color: rgb(0, 0, 0); font-style: normal; font-variant-caps: normal; font-weight: 400; letter-spacing: normal; orphans: auto; text-align: start; text-transform: none; white-space: normal; widows: auto; word-spacing: 0px; -webkit-text-stroke-width: 0px; text-decoration: none;"><thead><tr><th><p class="p1"><b>Component</b></p></th><th><p class="p1"><b>Speed Increase Since 1990</b></p></th></tr></thead><tbody><tr><td><p class="p1">CPU (per core)</p></td><td><p class="p1">~1,000x</p></td></tr><tr><td><p class="p1">CPU (multi-core)</p></td><td><p class="p1">10,000x+</p></td></tr><tr><td><p class="p1">Storage</p></td><td><p class="p1">~5,000x</p></td></tr><tr><td><p class="p1">RAM</p></td><td><p class="p1">~1,000x</p></td></tr></tbody></table>
<!--kg-card-end: html-->
<p>Combine that with the rise of custom tooling, open source, and so many abstraction layers, and one could argue that there&apos;ve been some massive improvements in programmer productivity. With that said, I think there are some complicated demand curves that make it hard to draw a line to more/less jobs in the field.</p><p>What I do think is that increased awareness of what&apos;s possible has led to increased demand for people who can make those things possible, and I think there&apos;s grounds to believe that that cycle will continue. What&apos;s up for debate, perhaps, is how those things will be made possible in the coming years, which is going to directly affect the kinds of jobs that are available.</p>]]></content:encoded></item><item><title><![CDATA[The one about Shopify's AI positioning]]></title><description><![CDATA[<p>&quot;<a href="https://x.com/tobi/status/1909251946235437514?ref=jason.now" rel="noreferrer">Reflexive AI usage is now a baseline expectation at Shopify</a>&quot;</p><p>Pasting the whole thing below, because while Ghost&apos;s ability to embed social media posts is super easy to get into, long posts don&apos;t render directly and who knows how long that tech will last.</p>]]></description><link>https://jason.now/the-one-about-shopifys-ai-positioning/</link><guid isPermaLink="false">67f91ffbba798a0001daecb9</guid><dc:creator><![CDATA[Jason Doucette]]></dc:creator><pubDate>Fri, 11 Apr 2025 14:07:25 GMT</pubDate><content:encoded><![CDATA[<p>&quot;<a href="https://x.com/tobi/status/1909251946235437514?ref=jason.now" rel="noreferrer">Reflexive AI usage is now a baseline expectation at Shopify</a>&quot;</p><p>Pasting the whole thing below, because while Ghost&apos;s ability to embed social media posts is super easy to get into, long posts don&apos;t render directly and who knows how long that tech will last. Plus I want a copy of this one, and it&apos;s my blog.</p><blockquote>Team,<br><br>We are entering a time where more merchants and entrepreneurs could be created than any other in history. We often talk about bringing down the complexity curve to allow more people to choose this as a career. Each step along the entrepreneurial path is rife with decisions requiring skill, judgement and knowledge. Having AI alongside the journey and increasingly doing not just the consultation, but also doing the work for our merchants is a mindblowing step function change here.<br><br>Our task here at Shopify is to make our software unquestionably the best canvas on which to develop the best businesses of the future. We do this by keeping everyone cutting edge and bringing all the best tools to bear so our merchants can be more successful than they themselves used to imagine. For that we need to be absolutely ahead.<br><br><strong>Reflexive AI usage is now a baseline expectation at Shopify</strong><br><br>Maybe you are already there and find this memo puzzling. In that case you already use AI as a thought partner, deep researcher, critic, tutor, or pair programmer. I use it all the time, but even I feel I&apos;m only scratching the surface. It&#x2019;s the most rapid shift to how work is done that I&#x2019;ve seen in my career and I&#x2019;ve been pretty clear about my enthusiasm for it: you&apos;ve heard me talk about AI in weekly videos, podcasts, town halls, and&#x2026; Summit! Last summer I <a href="https://vault.shopify.io/page/Summit-2024---Unlocking-AI~RRey.md?ref=jason.now" rel="noopener noreferrer nofollow">used agents to create my talk</a>, and presented about that. I did this as a call to action and invitation for everyone to tinker with AI, to dispel any scepticism or confusion that this matters at all levels. Many of you took up the call, and all of us who did have been in absolute awe of the new capabilities and tools that AI can deliver to augment our skills, crafts, and fill in our gaps.</blockquote><blockquote>What we have learned so far is that using AI well is a skill that needs to be carefully learned by&#x2026; using it a lot. It&#x2019;s just too unlike everything else. The call to tinker with it was the right one, but it was too much of a suggestion. This is what I want to change here today. We also learned that, as opposed to most tools, AI acts as a multiplier.  We are all lucky to work with some amazing colleagues, the kind who contribute 10X of what was previously thought possible. It&#x2019;s my favorite thing about this company. And what&#x2019;s even more amazing is that, for the first time, we see the tools become 10X themselves. I&#x2019;ve seen many of these people approach implausible tasks, ones we wouldn&#x2019;t even have chosen to tackle before, with reflexive and brilliant usage of AI to get 100X the work done.</blockquote><blockquote>In my <a href="https://vault.shopify.io/page/On-Leadership---August-2020~11669.md?ref=jason.now" rel="noopener noreferrer nofollow">On Leadership</a> memo years ago, I described Shopify as a <em>red queen race</em> based on the Alice in Wonderland story&#x2014;you have to keep running just to stay still. In a company growing 20-40% year over year, you must improve by at least that every year just to re-qualify. This goes for me as well as everyone else.</blockquote><blockquote>This sounds daunting, but given the nature of the tools, this doesn&#x2019;t even sound terribly ambitious to me anymore. It&#x2019;s also exactly the kind of environment that our top performers tell us they want. Learning together, surrounded by people who also are on their own journey of personal growth and working on worthwhile, meaningful, and hard problems is precisely the environment Shopify was created to provide. This represents both an opportunity and a requirement, deeply connected to our core values of <em>Be a Constant Learner</em> and <em>Thrive on Change</em>. These aren&apos;t just aspirational phrases&#x2014;they&apos;re fundamental expectations that come with being a part of this world-class team. This is what we founders wanted, and this is what we built.</blockquote><blockquote><strong>What This Means</strong></blockquote><blockquote><strong>Using AI effectively is now a fundamental expectation of everyone at Shopify.</strong> It&apos;s a tool of all trades today, and will only grow in importance. Frankly, I don&apos;t think it&apos;s feasible to opt out of learning the skill of applying AI in your craft; you are welcome to try, but I want to be honest I cannot see this working out today, and definitely not tomorrow. Stagnation is almost certain, and stagnation is slow-motion failure. If you&apos;re not climbing, you&apos;re sliding.</blockquote><blockquote><strong>AI must be part of your GSD Prototype phase</strong>. The prototype phase of any GSD project should be dominated by AI exploration. Prototypes are meant for learning and creating information. AI dramatically accelerates this process. You can learn to produce something that other team mates can look at, use, and reason about in a fraction of the time it used to take.</blockquote><blockquote><strong>We will add AI usage questions to our performance and peer review questionnaire</strong>. Learning to use AI well is an unobvious skill. My sense is that a lot of people give up after writing a prompt and not getting the ideal thing back immediately. Learning to prompt and load context is important, and getting peers to provide feedback on how this is going will be valuable.</blockquote><blockquote><strong>Learning is self directed, but share what you learned</strong>. You have access to as much of the cutting edge AI tools as possible.There is <a href="http://chat.shopify.io/?ref=jason.now" rel="noopener noreferrer nofollow">chat.shopify.io</a>, which we had for years now. Developers have <a href="https://proxy.shopify.ai/?ref=jason.now" rel="noopener noreferrer nofollow">proxy</a>, Copilot, Cursor, Claude code, all pre-tooled and ready to go. We&#x2019;ll learn and adapt together as a team. We&#x2019;ll be sharing Ws (and Ls!) with each other as we experiment with new AI capabilities, and we&#x2019;ll dedicate time to AI integration in our monthly business reviews and product development cycles. Slack and Vault have lots of places where people share prompts that they developed, like <a href="https://x.com/search?q=%23revenue&amp;src=hashtag_click&amp;ref=jason.now" rel="noopener noreferrer nofollow">#revenue</a>-ai-use-cases and <a href="https://x.com/search?q=%23ai&amp;src=hashtag_click&amp;ref=jason.now" rel="noopener noreferrer nofollow">#ai</a>-centaurs.</blockquote><blockquote><strong>Before asking for more Headcount and resources</strong>, teams must demonstrate why they cannot get what they want done using AI. What would this area look like if autonomous AI agents were already part of the team? This question can lead to really fun discussions and projects.</blockquote><blockquote><strong>Everyone means everyone</strong>. This applies to all of us&#x2014;including me and the executive team.</blockquote><blockquote><strong>The Path Forward</strong></blockquote><blockquote>AI will totally change Shopify, our work, and the rest of our lives. We&apos;re all in on this! I couldn&apos;t think of a better place to be part of this truly unprecedented change than being here. You don&apos;t just get a front-row seat, but are surrounded by a whole company learning and pushing things forward together.</blockquote><blockquote>Our job is to figure out what entrepreneurship looks like in a world where AI is universally available. And I intend for us to do the best possible job of that, and to do that I need everyone&#x2019;s help. I already laid out a lot of the AI projects in the themes this year- our roadmap is clear, and our product will better match our mission. What we need to succeed is our collective sum total skill and ambition at applying our craft, multiplied by AI, for the benefit of our merchants.</blockquote><blockquote>-tobi<br>CEO Shopify</blockquote><p>First, I like the phrase &quot;reflexive AI&quot; a lot. </p><p>It seems like most of the reactions to this were around the &quot;no new headcount unless you can explain why AI can&apos;t do the job,&quot; which, to be fair, is a major advancement in the &quot;AI is here to make us more productive, not to take our jobs&quot; vs &quot;we can totally do more with less if we use AI&quot; debate. But it also marks a subtle distinction between taking a job vs taking your job. Which is what leads to what I think is the more interesting part of the discussion.</p><p>There&apos;s some key bits in parts 2 and 3 of the memo around incentivizing the use of AI within the company. This has been the hardest part of AI adoption, from what I&apos;ve seen both firsthand and heard repeatedly from others. Tying AI usage to compensation is probably the most direct way to motivate people to get in the game (and those that don&apos;t respond to that will probably infer a threat from the headcount point.) But getting to the reflexive stage, one way or another, has remarkable potential.</p>]]></content:encoded></item><item><title><![CDATA["Can we use AI?"]]></title><description><![CDATA[<p>&quot;<a href="https://x.com/BenSpurr/status/1910039009449173369?ref=jason.now" rel="noreferrer">We&apos;re at the stage where every city committee meeting features a councillor moving a motion asking &quot;can we use AI?&quot; to fix whatever problem they&apos;re debating.</a>&quot;</p><p>And part of me is like...</p><figure class="kg-card kg-image-card"><img src="https://jason.now/content/images/2025/04/nothowtheforceworks-1.gif" class="kg-image" alt loading="lazy" width="500" height="461"></figure><p>But the other part of me (two wolves!) is interested</p>]]></description><link>https://jason.now/can-we-use-ai/</link><guid isPermaLink="false">67f91ecbba798a0001daeca2</guid><dc:creator><![CDATA[Jason Doucette]]></dc:creator><pubDate>Fri, 11 Apr 2025 13:57:17 GMT</pubDate><content:encoded><![CDATA[<p>&quot;<a href="https://x.com/BenSpurr/status/1910039009449173369?ref=jason.now" rel="noreferrer">We&apos;re at the stage where every city committee meeting features a councillor moving a motion asking &quot;can we use AI?&quot; to fix whatever problem they&apos;re debating.</a>&quot;</p><p>And part of me is like...</p><figure class="kg-card kg-image-card"><img src="https://jason.now/content/images/2025/04/nothowtheforceworks-1.gif" class="kg-image" alt loading="lazy" width="500" height="461"></figure><p>But the other part of me (two wolves!) is interested in the skill gap that&apos;s still very much present in an area where the Thing Itself can help level you up to be able to figure out how to do things. AI can, in some ways, be the most self-promotional technology ever, if we can just get past (some of) humanity&apos;s hesitation to action.</p>]]></content:encoded></item><item><title><![CDATA[Asserts > Alerts]]></title><description><![CDATA[<p>Justin Searls wrote a great piece on how to <a href="https://justin.searls.co/posts/calling-private-methods-without-losing-sleep-at-night/?ref=jason.now">reduce the risks of writing dangerous code</a>. It&#x2019;s succinct, focused on a specific problem, and broadly applicable.</p><p>His technique relies on <a href="https://en.wikipedia.org/wiki/Assertion_(software_development)?ref=jason.now">assertions</a>, a programming tool that forces failures early when assumptions turn out to be wrong. Assertions don&#x2019;</p>]]></description><link>https://jason.now/asserts-alerts/</link><guid isPermaLink="false">67c4e87d873be9000169a12a</guid><dc:creator><![CDATA[Jason Doucette]]></dc:creator><pubDate>Tue, 04 Mar 2025 11:03:39 GMT</pubDate><media:content url="https://jason.now/content/images/2025/03/emergencybrake.png" medium="image"/><content:encoded><![CDATA[<img src="https://jason.now/content/images/2025/03/emergencybrake.png" alt="Asserts &gt; Alerts"><p>Justin Searls wrote a great piece on how to <a href="https://justin.searls.co/posts/calling-private-methods-without-losing-sleep-at-night/?ref=jason.now">reduce the risks of writing dangerous code</a>. It&#x2019;s succinct, focused on a specific problem, and broadly applicable.</p><p>His technique relies on <a href="https://en.wikipedia.org/wiki/Assertion_(software_development)?ref=jason.now">assertions</a>, a programming tool that forces failures early when assumptions turn out to be wrong. Assertions don&#x2019;t just warn you; they stop execution outright, preventing silent errors from spreading.</p><p>What if businesses treated critical assumptions the same way?</p><p>In code, an assertion crashes a program when something impossible happens. In business, a good assertion forces action before things spiral out of control.</p><p>Here&#x2019;s a highly simplified example:</p><pre><code class="language-python">def always_returns_five():
    return 5

x = always_returns_five()
assert x == 5
</code></pre><p>This function always returns 5, until it doesn&#x2019;t. If an external API call gets involved, or someone modifies the function, an assertion forces us to stop and investigate immediately, rather than letting a silent failure corrupt the system.</p><p>In a code review, assertions can settle debates about assumptions:</p><ul><li>&#x201D;What happens if X is false?&quot;</li><li>&quot;That can&#x2019;t happen.&quot;</li><li>&quot;Okay, either add an assertion that crashes the program if you&#x2019;re wrong, or handle the edge case. Pick one.&quot;</li></ul><p>Assertions expose when &quot;that can&#x2019;t happen&quot; really means &quot;I don&#x2019;t want to write error-handling code.&quot;</p><p>But this concept doesn&#x2019;t just apply to software.</p><p>Every business process is built on assumptions. And when those assumptions fail, the impact can be massive.</p><p>In code, an assertion crashes a program when something impossible happens. In business, a good assertion forces action before things spiral out of control.</p><p>Business operations are full of hidden assumptions, just like code:</p><ul><li>&quot;Customers will always renew their contracts.&quot;</li><li>&quot;Sales will update CRM records on time.&quot;</li><li>&quot;Our marketing campaigns won&apos;t burn through budget too quickly.&quot;</li></ul><p>These are all unstated truths, until they fail. And when they fail, we often find out too late.</p><p>So why don&#x2019;t we assert them, the same way we do in code?</p><p>For any of this to work, we need to identify those assumptions. That&#x2019;s not always easy! But it boils down to asking what needs to be true for the work to be successful.</p><p>For each of these critical assumptions, set up an assertion to monitor it. It could be in code, but really doesn&#x2019;t have to be, as long as checking it is systemized.</p><p>Lots of times, we get <em>so close</em> to this idea with alerts. Something goes wrong? No problem, here&#x2019;s an email about it. The only problem is that you get a lot of emails. And maybe have to do things during the day that (gasp!) take you away from your computer. But maybe you have a team of people receiving the email! Great, but did you set up a protocol for who should handle it (and let people know they&#x2019;re on it) when one of these come in?</p><p>Most businesses already have alerts. But alerts are passive. They assume someone will notice, interpret, and act.</p><ul><li>Alert: &quot;Customer churn is increasing.&quot; (Email sent. Will anyone act?)</li><li>Assertion: &quot;If churn rises past 5%, freeze acquisition budgets until leadership intervenes.&quot; (A concrete action happens by default.)</li></ul><p>With alerts, problems often slip through the cracks. With assertions, failure forces a reaction, like a dead man&#x2019;s switch. This approach ensures that if no one intervenes, a <em>failsafe</em> activates:</p><ul><li><strong>Finance</strong>: If an expense report isn&#x2019;t reviewed in 7 days, it&#x2019;s auto-rejected.</li><li><strong>HR</strong>: If an exit interview isn&#x2019;t conducted, an anonymous feedback survey is automatically sent.</li><li><strong>Sales</strong>: If a deal isn&#x2019;t updated in CRM within 10 days, it&#x2019;s flagged as &#x2018;At Risk&#x2019; and removed from forecasting.</li></ul><p>Assertions, whether in code or in business, feel risky because they demand action. But the real risk isn&#x2019;t breaking things when an assumption fails.</p><p>The real risk isn&#x2019;t breaking things, it&#x2019;s letting failures pile up silently until they explode.</p>]]></content:encoded></item><item><title><![CDATA[Pinterest Gets Slopped]]></title><description><![CDATA[<p>Via Futurism: <a href="https://futurism.com/pinterest-ai-slop?ref=jason.now">Pinterest has an AI slop problem</a>, with AI-generated content dominating search results across vast ranges of categories.</p><p>At least, that&#x2019;s the claim. I poked around Pinterest for a few minutes in the food section, and&#x2026; maybe? There are definitely a lot of very similar websites</p>]]></description><link>https://jason.now/pinterest-gets-slopped/</link><guid isPermaLink="false">67c66bcb09bebf00010ccb0e</guid><dc:creator><![CDATA[Jason Doucette]]></dc:creator><pubDate>Tue, 04 Mar 2025 02:57:13 GMT</pubDate><media:content url="https://jason.now/content/images/2025/03/swampy.png" medium="image"/><content:encoded><![CDATA[<img src="https://jason.now/content/images/2025/03/swampy.png" alt="Pinterest Gets Slopped"><p>Via Futurism: <a href="https://futurism.com/pinterest-ai-slop?ref=jason.now">Pinterest has an AI slop problem</a>, with AI-generated content dominating search results across vast ranges of categories.</p><p>At least, that&#x2019;s the claim. I poked around Pinterest for a few minutes in the food section, and&#x2026; maybe? There are definitely a lot of very similar websites out there, but I didn&#x2019;t get to &#x201C;these photos are definitely AI&#x201D; as fast as the linked article did. It&#x2019;s possible that people are just copying what works. And it&#x2019;s pretty easy to imagine LLMs generating content that looks like everything else out there, since that&#x2019;s basically what they do, so, sure.</p><p>Of course, the article also points out someone&#x2019;s YouTube channel (I won&#x2019;t link to it) that explains how they&#x2019;re doing exactly what&#x2019;s alleged, so yeah, it&#x2019;s happening, and the odds are pretty good that it&#x2019;ll continue to happen at an increasing scale as word continues to spread and automation tools continue to expand.</p><p>(A brief aside, <a href="https://www.npr.org/sections/thetwo-way/2011/04/15/135440481/just-like-the-real-thing-vegan-magazine-caught-using-pictures-of-meat?ref=jason.now">VegNews once got into trouble</a> for using stock photos of non-vegan foods to illustrate their vegan recipes. AI imagery takes that to a whole new level. Also, I should point out that just because a recipe is AI generated doesn&#x2019;t mean it&#x2019;s bad; I&#x2019;ve had good luck on my nights to cook with asking a GPT to tell me how to make &#x201C;the best whatever ever.&#x201D; But at least I knew what I was getting into. These sites (allegedly) aren&#x2019;t disclosing that their recipes are completely theoretical.)</p><p>This might just be an inevitable trend that nobody really thought would hit the scales that are currently happening. Fun fact: many years ago search engines would proudly display how many pages of the internet they&#x2019;d indexed. Here&#x2019;s Google&#x2019;s history in the earlier days:</p>
<!--kg-card-begin: html-->
<table>
	<thead>
		<tr>
			<th>
				Year
			</th>
			<th>
				Pages Indexed
			</th>
		</tr>
	</thead>
	<tbody>
		<tr>
			<td>
				2002
			</td>
			<td>
				3 billion
			</td>
		</tr>
		<tr>
			<td>
				2003
			</td>
			<td>
				4 billion
			</td>
		</tr>
		<tr>
			<td>
				2004
			</td>
			<td>
				8 billion
			</td>
		</tr>
		<tr>
			<td>
				2005
			</td>
			<td>
				25 billion
			</td>
		</tr>
	</tbody>
</table>
<!--kg-card-end: html-->
<p>(Sources: <a href="https://lemire.me/blog/2005/08/16/number-of-pages-indexed-by-google-over-time/?ref=jason.now">Daniel Lemire</a>, <a href="https://static.googleusercontent.com/media/research.google.com/en//pubs/archive/37043.pdf?ref=jason.now">Google</a>)</p><p>Now, these are self-reported numbers, and it could have just represented Google expanding capacity, but I recall that era, and there was definitely a lot more internet than there used to be in a short period of time. What drove this publishing explosion?</p><p>Here&#x2019;s a theory: <a href="https://en.wikipedia.org/wiki/Google_AdSense?ref=jason.now">Google introduced Adsense in 2003</a>, a very accessible means of monetizing content.</p><p>Mass-produced content has been around for at least 20 years, but AI creates a new level of scale for <a href="https://www.emarketer.com/content/made-for-advertising-websites-advertisers?ref=jason.now">Made For Advertising</a> sites. Search engines may or may not be able to limit their visibility to the average user. Meanwhile, alternate traffic sources - like Pinterest - have to develop their own solutions.</p><p>Or maybe not, depending on their KPIs! More uploaded content might be desirable to these platforms. And hey, isn&#x2019;t it refreshing to be swamped with generic content instead of <a href="https://www.bbc.com/news/articles/crr9q2jz7y0o?ref=jason.now">nightmare fuel</a> for the moderation teams?</p><p>We&#x2019;re entering an era with effectively infinite content, which means infinite inventory for ad servers. With infinite content comes infinite ad inventory - but also a race to the bottom for ad rates. That leaves publishers with two choices: go behind a paywall or fight for shrinking ad revenue. Public-facing publishers will face growing ad price pressure. Without a dedicated sales team to prove their value to advertisers, they&#x2019;ll struggle to compete. That requires scale, which requires budget, which requires ad revenue, which&#x2026;</p><p>As an aggregator, Pinterest may or may not be the first to fall, but online publishing as a whole is going to face real challenges to rise out of the emerging swamp.</p>]]></content:encoded></item><item><title><![CDATA[Custom Sorting in SAQL, Domo, and BI Dashboards Without Ugly Number Prefixes]]></title><description><![CDATA[<p>Sorting in Salesforce CRM Analytics (CRMA) should be simple&#x2014;but if you&#x2019;ve ever tried to create a custom sort order in SAQL, you&#x2019;ve probably hit a frustrating limitation. Since text fields default to alphabetical sorting, categories like High, Medium, and Low often appear in the</p>]]></description><link>https://jason.now/custom-sorting-in-saql-domo-and-bi-dashboards-without-ugly-number-prefixes/</link><guid isPermaLink="false">67bfa103a940500001b83fd0</guid><dc:creator><![CDATA[Jason Doucette]]></dc:creator><pubDate>Wed, 26 Feb 2025 23:24:41 GMT</pubDate><media:content url="https://jason.now/content/images/2025/02/AlbedoBase_XL_An_illustration_for_the_top_of_a_blog_post_about_0.jpg" medium="image"/><content:encoded><![CDATA[<img src="https://jason.now/content/images/2025/02/AlbedoBase_XL_An_illustration_for_the_top_of_a_blog_post_about_0.jpg" alt="Custom Sorting in SAQL, Domo, and BI Dashboards Without Ugly Number Prefixes"><p>Sorting in Salesforce CRM Analytics (CRMA) should be simple&#x2014;but if you&#x2019;ve ever tried to create a custom sort order in SAQL, you&#x2019;ve probably hit a frustrating limitation. Since text fields default to alphabetical sorting, categories like High, Medium, and Low often appear in the wrong order:</p>
<!--kg-card-begin: html-->
<table>
	<thead>
		<tr>
			<th>
				What you want (logical sort)
			</th>
			<th>
				What you get (alphabetical sort)
			</th>
		</tr>
	</thead>
	<tbody>
		<tr>
			<td>
				Low
			</td>
			<td>
				High
			</td>
		</tr>
		<tr>
			<td>
				Medium
			</td>
			<td>
				Low
			</td>
		</tr>
		<tr>
			<td>
				High
			</td>
			<td>
				Medium
			</td>
		</tr>
	</tbody>
</table>
<!--kg-card-end: html-->
<p>Most BI tools, including CRMA, Domo, and Tableau, have the same issue. The usual fix? <strong>Prepending numbers</strong> (e.g., 1 - Low, 2 - Medium, 3 - High). But let&#x2019;s be honest&#x2014;<em>that looks terrible in dashboards</em>. It takes up visual space, and implies a numerical correlation that might not exist.</p><figure class="kg-card kg-image-card kg-card-hascaption"><img src="https://jason.now/content/images/2025/02/DraggedImage.png" class="kg-image" alt="Custom Sorting in SAQL, Domo, and BI Dashboards Without Ugly Number Prefixes" loading="lazy" width="726" height="440" srcset="https://jason.now/content/images/size/w600/2025/02/DraggedImage.png 600w, https://jason.now/content/images/2025/02/DraggedImage.png 726w" sizes="(min-width: 720px) 720px"><figcaption><span style="white-space: pre-wrap;">Yes, I made low the highest number on purpose</span></figcaption></figure><p>Fortunately, there&#x2019;s a better way. By using invisible Unicode characters, you can control sorting without modifying the visible text. It&#x2019;s the same idea as prepending numbers, but this uses characters that nobody can see instead of annoying numbers that everyone sees. This approach works directly in SAQL and applies to other BI platforms like Domo, Tableau, and Power BI.</p><h2 id="why-custom-sorting-in-crma-saql-is-a-challenge">Why Custom Sorting in CRMA (SAQL) Is a Challenge</h2><ul><li>SAQL defaults to alphabetical sorting, making logical category orders difficult.</li><li>Common sorting issues in CRMA dashboards (e.g., priority levels, status values).</li><li>Other BI tools, like Domo and Tableau, have similar limitations.</li></ul><p>Note that if your data is at the dataset level, you might have other options involving editing the XMD file. <a href="https://web.archive.org/web/20210801064242/http://www.aydincanpolatkan.com/blog/2527">There&#x2019;s a writeup here</a> that looks promising, but I haven&#x2019;t tried it because my issue was at the step level.</p><h2 id="common-workarounds">Common Workarounds</h2><h3 id="1-prepending-numbers-1low-2medium-etc"><strong>1. Prepending Numbers (1 - Low, 2 - Medium, etc)</strong></h3><p>&#x2705; Ensures correct sorting<br>&#x274C; Clutters dashboard labels</p><h3 id="2-creating-a-separate-sort-column-in-the-dataset"><strong>2. Creating a Separate Sort Column in the Dataset</strong></h3><p>&#x2705; Works well for static datasets<br>&#x274C; Doesn&#x2019;t work for all visualizations</p><h3 id="3-manually-reordering-in-dashboards"><strong>3. Manually Reordering in Dashboards</strong></h3><p>&#x2705; Works if the tool allows it<br>&#x274C; Not scalable for large or dynamic lists</p><h2 id="the-unicode-trick-sorting-without-visible-changes">The Unicode Trick: Sorting Without Visible Changes</h2><p>When sorting text, characters are sorted <em>lexicographically</em>. This is a fancy way of saying alphabetically (mostly.)</p><p>Unicode is a text encoding standard. Back when computers started out, they generally supported the characters you&#x2019;d find on a North American keyboard, and not much else. Of course, there are a lot of other alphabets out there, plus, well, &#x1F4A9;.</p><p>But for our purposes, there are a bunch of characters that exist that <em>don&#x2019;t actually show up on the screen</em>. Here are a bunch of them:</p>
<!--kg-card-begin: html-->
<table>
	<thead>
		<tr>
			<th>
				Code
			</th>
			<th>
				Character
			</th>
		</tr>
	</thead>
	<tbody>
		<tr>
			<td>
				U+200B
			</td>
			<td>
				&#x200B; <a href="https://unicode-explorer.com/c/200B?ref=jason.now">Zero Width Space</a>
			</td>
		</tr>
		<tr>
			<td>
				U+200C
			</td>
			<td>
				&#x200C; <a href="https://unicode-explorer.com/c/200C?ref=jason.now">Zero Width Non-Joiner</a>
			</td>
		</tr>
		<tr>
			<td>
				U+200D
			</td>
			<td>
				&#x200D; <a href="https://unicode-explorer.com/c/200D?ref=jason.now">Zero Width Joiner</a>
			</td>
		</tr>
		<tr>
			<td>
				U+2060
			</td>
			<td>
				&#x2060; <a href="https://unicode-explorer.com/c/2060?ref=jason.now">Word Joiner</a>
			</td>
		</tr>
		<tr>
			<td>
				U+2062
			</td>
			<td>
				&#x2062; <a href="https://unicode-explorer.com/c/2062?ref=jason.now">Invisible Times</a>
			</td>
		</tr>
		<tr>
			<td>
				U+2063
			</td>
			<td>
				&#x2063; <a href="https://unicode-explorer.com/c/2063?ref=jason.now">Invisible Separator</a>
			</td>
		</tr>
		<tr>
			<td>
				U+2064
			</td>
			<td>
				&#x2064; <a href="https://unicode-explorer.com/c/2064?ref=jason.now">Invisible Plus</a>
			</td>
		</tr>
	</tbody>
</table>
<!--kg-card-end: html-->
<p>Most of these characters sort before the English alphabet, allowing us to influence the order without changing visible text. If we put those characters at the beginning of our strings, being mindful of their sort order, we can control the sort to be whatever we want.</p><h2 id="step-by-step-implementing-the-unicode-sorting-trick-in-crma">Step-by-Step: Implementing the Unicode Sorting Trick in CRMA</h2><h3 id="step-1-identify-your-sort-order"><strong>Step 1: Identify Your Sort Order</strong></h3><p>Example: <strong>Low &#x2192; Medium &#x2192; High</strong></p><h3 id="step-2-modify-your-saql-query"><strong>Step 2: Modify Your SAQL Query</strong></h3><p>Insert invisible Unicode characters directly into the SAQL step. Note that many languages have a way to write out unicode strings in a format like \u20b0, but SAQL isn&#x2019;t great at that, so you&#x2019;re going to have to paste the character directly into the string, using a site like the one linked in the table above to help.</p><p>This means that you&#x2019;re going to be effectively writing invisible code, and the next person to look at it (or you in a month) isn&#x2019;t going to know what&#x2019;s going on! <strong>Use comments liberally here.</strong></p><p>To make this easier to see, I&#x2019;m using different emojis in the example below, so&#x2026; don&#x2019;t just copy and paste this and wonder why it didn&#x2019;t work. You&#x2019;ll want to copy actual Unicode characters (<a href="https://unicode-explorer.com/c/200B?ref=jason.now">200B</a>, <a href="https://unicode-explorer.com/c/200D?ref=jason.now">200D</a>, <a href="https://unicode-explorer.com/c/200E?ref=jason.now">200E</a>) from <a href="https://unicode-explorer.com/?ref=jason.now">Unicode Explorer</a> and paste them into your SAQL.</p><pre><code class="language-saql">q = foreach q generate
    case
        when Status == &quot;Low&quot; then &quot;&#x261D;&#xFE0F;Low&quot;   // U+200B (zero-width space, pasted manually)
        when Status == &quot;Medium&quot; then &quot;&#x200D;&#x270C;&#xFE0F;Medium&quot;   // U+200D (zero-width joiner, pasted manually)
        when Status == &quot;High&quot; then &quot;&#x1F44C;&#x200E;High&quot;   // U+200E (left-to-right mark, pasted manually)
        else Status
    end as CustomSortStatus;
</code></pre><h3 id="step-3-verify-sorting-in-crma-dashboards"><strong>Step 3: Verify Sorting in CRMA Dashboards</strong></h3><ul><li>Preview the sorted SAQL step result.</li><li>Ensure the labels appear unchanged but sort correctly.</li></ul><h2 id="applying-this-trick-to-other-bi-tools">Applying This Trick to Other BI Tools</h2><p>This is going to vary depending on your platform and needs. In Domo, you can use beast mode calculations to prepend the characters, and Tableau and Power BI are probably best suited to calculated fields. But the concept is pretty straightforward everywhere.</p><h2 id="pitfalls-and-best-practices">Pitfalls and Best Practices</h2><p>Is this a brilliant solution or a terrible hack? Probably both. But as with anything a bit out of the ordinary, there are a few things to watch out for.</p><p>Some tools might strip out invisible characters, and it&#x2019;s really hard to see invisible things! So remember to test your dashboards often if you&#x2019;re making changes.</p><p>Depending on the nature of the data, you could run into trouble with filters and searches. In my scenario, I was just trying to control the sort of a legend and bar segments, so there wasn&#x2019;t much risk. Your mileage may vary!</p><p>I mentioned this earlier, but it bears repeating: <em>you&#x2019;re going to want to comment your code.</em> If you don&#x2019;t make it clear what you&#x2019;ve done, it&#x2019;ll seem like magic to the next person and they won&#x2019;t be able to build upon it, and there&#x2019;s a risk that someone will undo what you made without even realizing it.</p><h2 id="wrapping-up">Wrapping up</h2><p>It&#x2019;s pretty rare that I&#x2019;ve found a BI solution that does exactly what I want out of the box without some level of tweaking, and this example is no exception. Overall, this is a pretty platform-agnostic approach that covers a range of bases, so it was worth writing up so the next time I Google around for an answer, I&#x2019;ll end up right at home.</p><p>Questions or comments? Hit me up on <a href="https://bsky.app/profile/jasondoucette.bsky.social?ref=jason.now" rel="noreferrer">Bluesky</a> or <a href="https://x.com/jasondoucette?ref=jason.now" rel="noreferrer">X</a>!</p>]]></content:encoded></item></channel></rss>