<?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: Thomas Hansen</title>
    <description>The latest articles on DEV Community by Thomas Hansen (@polterguy).</description>
    <link>https://dev.to/polterguy</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%2F829923%2F04782b3f-244f-42af-a2bb-cd3277828def.png</url>
      <title>DEV Community: Thomas Hansen</title>
      <link>https://dev.to/polterguy</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/polterguy"/>
    <language>en</language>
    <item>
      <title>My MCP server technically has 10 to the power of 1204 number of integrations! Try it for free here!</title>
      <dc:creator>Thomas Hansen</dc:creator>
      <pubDate>Mon, 21 Sep 2026 09:17:25 +0000</pubDate>
      <link>https://dev.to/polterguy/my-mcp-server-technically-has-10-to-the-power-of-1204-number-of-integrations-try-it-for-free-here-9el</link>
      <guid>https://dev.to/polterguy/my-mcp-server-technically-has-10-to-the-power-of-1204-number-of-integrations-try-it-for-free-here-9el</guid>
      <description>&lt;p&gt;&lt;em&gt;Part of our MCP series — the overview lives at &lt;a href="https://hyperlambda.dev/mcp-server" rel="noopener noreferrer"&gt;MCP Server&lt;/a&gt;, and the endpoint below is the one built in &lt;a href="https://hyperlambda.dev/blog/let-strangers-run-code-on-your-server-on-purpose" rel="noopener noreferrer"&gt;Let Strangers Run Code on Your Server&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Here is a number I can defend. A caller sends my endpoint at most 500 characters. Count the distinct inputs at one byte per character and you get 256 to the power of 500 - which is two to the power of four thousand, which is very close to &lt;strong&gt;ten to the power of 1204&lt;/strong&gt;. That is a number with 1,205 digits. Writing it out at one digit a second takes twenty minutes. For scale: the observable universe holds perhaps &lt;code&gt;10^80&lt;/code&gt; elementary particles, so &lt;code&gt;10^1204&lt;/code&gt; is around &lt;strong&gt;1,124 orders of magnitude more "integrations" than there are particles in existence&lt;/strong&gt;. It is not a big number. It is a stupid number.&lt;/p&gt;

&lt;p&gt;Every one of those inputs is a different thing you can tell the endpoint to do. So, &lt;em&gt;technically&lt;/em&gt;, my MCP server ships with &lt;code&gt;10^1204&lt;/code&gt; integrations. You may quote me, and you may put the word technically in italics when you do.&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%2Ffmyseke02ngvazlii36m.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%2Ffmyseke02ngvazlii36m.png" alt="An AI agent connected to a Magic cloudlet as an MCP connector, listing the tools it publishes" width="799" height="602"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  The joke has a serious spine
&lt;/h2&gt;

&lt;p&gt;The industry builds agent integrations one at a time. A tool definition per operation. A wrapper per API. An import per specification. Want your agent to touch a new system? Write another adapter, describe it, test it, keep it in sync forever. N things means N hand-built integrations and N things to maintain.&lt;/p&gt;

&lt;p&gt;A capability-scoped endpoint collapses that N to &lt;strong&gt;one&lt;/strong&gt;. You do not enumerate operations any more; you declare a &lt;em&gt;vocabulary&lt;/em&gt; - a list of the functions a caller's code is allowed to reach - and the model composes whatever operation it needs out of that vocabulary, at the moment it needs it. Reading five rows, joining three tables, formatting the result as Markdown, filtering by a date it computed on the fly - those are not four integrations you built. They are four sentences a model wrote against one endpoint, and the runtime checked each function against your list before it ran.&lt;/p&gt;

&lt;p&gt;The combinatorial explosion that gives me my ridiculous headline number is the &lt;em&gt;same&lt;/em&gt; explosion that means you never write an integration again. You stop maintaining a catalogue of operations and start maintaining a short list of capabilities. The operations take care of themselves.&lt;/p&gt;

&lt;h2&gt;
  
  
  One integration to rule them all
&lt;/h2&gt;

&lt;p&gt;I am not going to resist it.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;One integration to rule them all, one integration to find them,&lt;br&gt;
one integration to bring them all, and in the vocabulary bind them.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;One tool. One URL. One whitelist. Every operation the agent could ever compose lives inside it - and cannot escape it, because a function that is not on the list does not exist as far as the caller's code is concerned. The power is total within the boundary and exactly zero outside it. That is the good kind of ring.&lt;/p&gt;

&lt;h2&gt;
  
  
  Try it, free, right now
&lt;/h2&gt;

&lt;p&gt;I left one running, connected to nothing more dangerous than the Chinook sample database, and I made you a login.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;MCP URL:&lt;/strong&gt; &lt;code&gt;https://hyperlambda.dev/magic/modules/mcp/mcp&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Username:&lt;/strong&gt; &lt;code&gt;guest&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Password:&lt;/strong&gt; &lt;code&gt;guestguestguestguest&lt;/code&gt; (the word &lt;code&gt;guest&lt;/code&gt;, four times)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Point any MCP client at that URL - &lt;strong&gt;Claude Code, Codex, Qoder, OpenCode&lt;/strong&gt;, or anything else that speaks the protocol. When it connects, the cloudlet answers unauthenticated requests with a 401 that hands the client its OAuth metadata, so your tool will walk you through a normal sign-in; use the guest credentials above. The &lt;code&gt;guest&lt;/code&gt; role is the one anyone who signs in through OIDC gets automatically, so it is completely harmless - here it grants exactly one thing: read the Chinook database.&lt;/p&gt;

&lt;p&gt;In Claude Code, for example, add it as a remote MCP server pointing at the URL and sign in when prompted. The other clients differ only in which menu the "add MCP server" button hides behind.&lt;/p&gt;

&lt;h2&gt;
  
  
  Ask it one thing first: "Return server vocabulary"
&lt;/h2&gt;

&lt;p&gt;Before you ask it to do anything, ask it what it &lt;em&gt;can&lt;/em&gt; do. Tell your agent:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Return server vocabulary&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;The endpoint answers with the exact list of functions it will dispatch for you - its whole capability surface, and nothing it will pretend to have. Feed that back into your session and your model is now grounded: its next instructions land inside the vocabulary instead of guessing at it. This is the antidote to that &lt;code&gt;10^1204&lt;/code&gt; headline. The model does not go wandering an input space with more members than the universe has atoms - it reads the finite list first, once, and composes against it.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"state"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"executed"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"result"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="s2"&gt;"add"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"and"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"convert"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"eq"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"for-each"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"get-value"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="s2"&gt;"if"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"return-nodes"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"strings.concat"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"math.add"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="s2"&gt;"data.read"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"data.connect"&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That list (abridged) is the whole of the caller's power. &lt;code&gt;data.read&lt;/code&gt; is on it. No writing function is. Which brings us to the fun part.&lt;/p&gt;

&lt;p&gt;  &lt;iframe src="https://www.youtube.com/embed/pzdTfe2Sg_A" width="710" height="399"&gt;
  &lt;/iframe&gt;
&lt;/p&gt;

&lt;h2&gt;
  
  
  Now try to make it misbehave
&lt;/h2&gt;

&lt;p&gt;Ask it, in plain English, to read the five first artists. It will. Ask it to delete them, or edit them, or insert a row, and it will happily &lt;em&gt;write the code&lt;/em&gt; to do so - and the runtime will refuse to dispatch it, because &lt;code&gt;data.delete&lt;/code&gt;, &lt;code&gt;data.create&lt;/code&gt; and &lt;code&gt;data.update&lt;/code&gt; are not in the vocabulary you just read. A guest can read Chinook and compose any read it likes; it cannot write a single byte, and it cannot reach anything else on the server.&lt;/p&gt;

&lt;p&gt;If you do get a row to change, that is a verified sandbox escape, and &lt;a href="https://hyperlambda.dev/blog/break-my-ai-sandbox-and-make-100-psst-nobodys-done-it-yet" rel="noopener noreferrer"&gt;I owe you $100&lt;/a&gt;. The full walkthrough of how this endpoint is built - and copy-paste cURL for all of it - is in &lt;a href="https://hyperlambda.dev/blog/let-strangers-run-code-on-your-server-on-purpose" rel="noopener noreferrer"&gt;Let Strangers Run Code on Your Server. On Purpose.&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  The honest edges
&lt;/h2&gt;

&lt;p&gt;The headline is a joke wearing a tie. &lt;code&gt;10^1204&lt;/code&gt; is the count of possible &lt;em&gt;inputs&lt;/em&gt;, not distinct useful operations - the honest sentence is "one endpoint whose behaviour the caller composes, bounded by a fixed vocabulary." That is less fun and more true, and it is still the point.&lt;/p&gt;

&lt;p&gt;Secure is not the same as omnicapable. This guest endpoint reads one database because that is all I granted it. A real deployment grants exactly the capabilities you choose, per role - your CEO's role reaches the finance database, your support agent's role reaches the tickets, and neither can compose its way into the other's. Capability, not catalogue. You still decide what the capabilities are; the runtime only guarantees nobody exceeds them.&lt;/p&gt;

&lt;p&gt;And it does not make wrong logic right. A model that writes a bad query gets a bad answer, executed perfectly safely. The sandbox is a boundary, not a proofreader.&lt;/p&gt;

&lt;h2&gt;
  
  
  Run your own
&lt;/h2&gt;

&lt;p&gt;One command runs the whole platform locally:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-fsSL&lt;/span&gt; https://hyperlambda.dev/docker-compose.yaml | docker compose &lt;span class="nt"&gt;-f&lt;/span&gt; - up
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Open &lt;strong&gt;&lt;code&gt;localhost:5555&lt;/code&gt;&lt;/strong&gt;, point it at &lt;strong&gt;&lt;code&gt;localhost:4444&lt;/code&gt;&lt;/strong&gt;, log in with &lt;code&gt;root&lt;/code&gt; / &lt;code&gt;root&lt;/code&gt;, and build a Sandbox API endpoint of your own in the Endpoint Generator - granting the vocabulary &lt;em&gt;you&lt;/em&gt; want, to the roles &lt;em&gt;you&lt;/em&gt; choose. Install the &lt;code&gt;mcp&lt;/code&gt; plugin and every endpoint in your cloudlet becomes a tool your agents can invoke.&lt;/p&gt;

&lt;p&gt;Magic is MIT licensed and open source - the repository is at &lt;a href="https://github.com/polterguy/magic" rel="noopener noreferrer"&gt;github.com/polterguy/magic&lt;/a&gt;, the documentation at &lt;a href="https://docs.ainiro.io" rel="noopener noreferrer"&gt;docs.ainiro.io&lt;/a&gt;. If you would rather someone else kept it patched, &lt;a href="https://hyperlambda.dev/pricing" rel="noopener noreferrer"&gt;a managed cloudlet&lt;/a&gt; runs the same code.&lt;/p&gt;

&lt;p&gt;Ten to the power of 1204 integrations, none of which I wrote, none of which I maintain, and not one of which can do anything I did not allow.&lt;/p&gt;

&lt;p&gt;And here is the punchline. Testing that many inputs one at a time would outlast the universe, many times over - so I did not test them one at a time. Every one of those &lt;code&gt;10^1204&lt;/code&gt; inputs resolves to the same correct verdict at the same single check: the one loop that reads the whitelist before it dispatches. Which lets me say something no test suite on Earth can say about its own code. &lt;strong&gt;I have debugged all &lt;code&gt;10^1204&lt;/code&gt; of my integrations, 100% perfectly - and it took one second.&lt;/strong&gt; That second was the request you just watched get refused. Try to break it.&lt;/p&gt;

&lt;h2&gt;
  
  
  Frequently asked questions
&lt;/h2&gt;

&lt;h3&gt;
  
  
  How can one MCP endpoint replace many integrations?
&lt;/h3&gt;

&lt;p&gt;Instead of a tool per operation, the endpoint accepts a plain-English instruction, has a model compose it into code, and runs that code inside a whitelist of allowed functions. The caller composes whatever operation it needs out of the granted vocabulary, so a single capability-scoped endpoint covers the combinatorial space of operations you would otherwise build one integration at a time.&lt;/p&gt;

&lt;h3&gt;
  
  
  How do I connect an AI agent to the free endpoint?
&lt;/h3&gt;

&lt;p&gt;Point any MCP client - Claude Code, Codex, Qoder, OpenCode or another - at &lt;code&gt;https://hyperlambda.dev/magic/modules/mcp/mcp&lt;/code&gt;. The cloudlet answers unauthenticated requests with a 401 carrying its OAuth metadata, so the client walks you through sign-in; log in with username &lt;code&gt;guest&lt;/code&gt; and password &lt;code&gt;guestguestguestguest&lt;/code&gt;. The guest role grants read-only access to the Chinook sample database.&lt;/p&gt;

&lt;h3&gt;
  
  
  What should I ask the endpoint first?
&lt;/h3&gt;

&lt;p&gt;Ask it to "Return server vocabulary". It replies with the exact list of functions it will dispatch, which seeds your model's understanding of what the tool can and cannot do, so its later instructions stay inside the allowed vocabulary rather than guessing.&lt;/p&gt;

&lt;h3&gt;
  
  
  Is the free endpoint safe to let an agent loose on?
&lt;/h3&gt;

&lt;p&gt;Yes. The guest role can only read the Chinook sample database. Any attempt to insert, update or delete is refused before it runs, because those functions are not in the granted vocabulary, and the endpoint cannot reach any other database, the file system, or configuration. There is a standing $100 bounty for a verified escape.&lt;/p&gt;

&lt;h2&gt;
  
  
  Related reading
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/let-strangers-run-code-on-your-server-on-purpose" rel="noopener noreferrer"&gt;Let Strangers Run Code on Your Server. On Purpose.&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/the-only-sandbox-your-ai-agent-cannot-break-out-of" rel="noopener noreferrer"&gt;The Only Sandbox Your AI Agent Cannot Break Out Of&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/convert-your-openapi-specification-to-a-secured-mcp-tool-in-seconds" rel="noopener noreferrer"&gt;Convert Your OpenAPI Specification to a Secured MCP Tool in Seconds&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/the-last-mcp-server-youll-ever-need" rel="noopener noreferrer"&gt;The Last MCP Server You'll Ever Need&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/break-my-ai-sandbox-and-make-100-psst-nobodys-done-it-yet" rel="noopener noreferrer"&gt;Break My AI Sandbox and Make $100&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>ai</category>
      <category>mcp</category>
      <category>security</category>
      <category>opensource</category>
    </item>
    <item>
      <title>Our Integration Count Has 4,196,703,834 Digits</title>
      <dc:creator>Thomas Hansen</dc:creator>
      <pubDate>Sun, 20 Sep 2026 14:36:20 +0000</pubDate>
      <link>https://dev.to/polterguy/our-integration-count-has-4196703834-digits-ghn</link>
      <guid>https://dev.to/polterguy/our-integration-count-has-4196703834-digits-ghn</guid>
      <description>&lt;p&gt;&lt;em&gt;Part of the honest comparison series — see also &lt;a href="https://hyperlambda.dev/blog/magic-vs-n8n-an-honest-feature-matrix" rel="noopener noreferrer"&gt;Magic vs n8n&lt;/a&gt;, &lt;a href="https://hyperlambda.dev/blog/magic-vs-directus-an-honest-feature-matrix" rel="noopener noreferrer"&gt;Magic vs Directus&lt;/a&gt;, &lt;a href="https://hyperlambda.dev/blog/magic-vs-pocketbase-an-honest-feature-matrix" rel="noopener noreferrer"&gt;Magic vs PocketBase&lt;/a&gt; and &lt;a href="https://hyperlambda.dev/blog/unqork-raised-365-million-to-reinvent-the-config-file" rel="noopener noreferrer"&gt;Unqork Raised $365 Million to Reinvent the Config File&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Every integration platform on earth puts a number on its homepage. Nine thousand apps. Twelve hundred connectors. Seven hundred sources. The number is always followed by a plus sign, and it is always getting bigger, and it is always presented as though it settles something.&lt;/p&gt;

&lt;p&gt;I went and collected them. All of them, from the vendors' own pages, on the same day.&lt;/p&gt;

&lt;p&gt;What I found was not that my number is bigger. What I found is that &lt;strong&gt;nobody is counting the same thing&lt;/strong&gt;, several of them cannot agree with themselves on a single page, and at least one of them is counting itself.&lt;/p&gt;

&lt;h2&gt;
  
  
  The numbers, as published
&lt;/h2&gt;

&lt;p&gt;Every figure below is the vendor's own, taken from their own site on 20 September 2026, in their own words.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Platform&lt;/th&gt;
&lt;th&gt;Published figure&lt;/th&gt;
&lt;th&gt;What they call the unit&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Zapier&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;9,000+&lt;/td&gt;
&lt;td&gt;"apps"&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Workato&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;1,200 — &lt;em&gt;and&lt;/em&gt; 1000+&lt;/td&gt;
&lt;td&gt;"pre-built connectors" — &lt;em&gt;and&lt;/em&gt; "apps"&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Airbyte&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;700+ — &lt;em&gt;and&lt;/em&gt; 584&lt;/td&gt;
&lt;td&gt;"connectors"&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Tray&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;474+&lt;/td&gt;
&lt;td&gt;"pre-built connectors"&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;n8n&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;400+&lt;/td&gt;
&lt;td&gt;"integrations"&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Supabase&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;114&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;"partners"&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;ToolJet&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;100+&lt;/td&gt;
&lt;td&gt;"integrations"&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Retool&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;em&gt;none published&lt;/em&gt;&lt;/td&gt;
&lt;td&gt;74 logos on the page&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Make&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;em&gt;could not read it&lt;/em&gt;&lt;/td&gt;
&lt;td&gt;their site blocked me&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Look at the right-hand column before the middle one. Apps. Connectors. Partners. Integrations. Logos. Five different words for five different things, stacked into a single league table that the entire industry then argues about.&lt;/p&gt;

&lt;p&gt;An "app" at Zapier is a hosted OAuth integration with triggers and actions. A "connector" at Airbyte is an ELT source or destination with incremental sync. A "partner" at Supabase is &lt;strong&gt;a company that has a business relationship with Supabase&lt;/strong&gt;. These are not comparable quantities. Putting them in one column is like ranking countries by a list that mixes population, area and number of airports.&lt;/p&gt;

&lt;h2&gt;
  
  
  Three things I found while counting
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;1. Workato publishes two different numbers on the same page.&lt;/strong&gt; The page's own meta description says &lt;em&gt;"Browse through more than 1,200 pre-built connectors."&lt;/em&gt; The popup that appears on that same page says &lt;em&gt;"Connect to 1000+ apps instantly."&lt;/em&gt; Twelve hundred and one thousand, on one URL, in one visit.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;2. Airbyte contradicts itself on a single screen.&lt;/strong&gt; The hero says 700+ connectors. Scroll down four inches to the catalogue filter and it says &lt;em&gt;"Showing 100 of 584."&lt;/em&gt; You do not need me to adjudicate this one. Their marketing number and their database number are both on your monitor at the same time, and they differ by a hundred and sixteen.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;3. Retool counts itself seven times.&lt;/strong&gt; Retool publishes no headline figure at all, which is more honest than most of this list. But their integrations page carries 74 logos, and when you actually read them: &lt;strong&gt;seven are Retool's own products&lt;/strong&gt; — Retool AI, Retool API, Retool Database, Retool Email, Retool RPC, Retool Storage, Retool Vectors. &lt;strong&gt;Seven more are generic protocols&lt;/strong&gt; — REST, GraphQL, gRPC, SOAP, OpenAPI, JDBC, SMTP.&lt;/p&gt;

&lt;p&gt;That last group is the interesting one. "REST" is not an integration. REST is &lt;em&gt;the ability to make an HTTP request&lt;/em&gt;, which is table stakes for anything with a network stack. If "we support REST" counts as an integration, then every programming language invented since 1995 ships with several thousand of them.&lt;/p&gt;

&lt;p&gt;So roughly one in five Retool "integrations" is either Retool or a transport layer.&lt;/p&gt;

&lt;h2&gt;
  
  
  Make would not let me count
&lt;/h2&gt;

&lt;p&gt;Three separate attempts to load Make's integrations page — twice from my laptop, once from a server in a different country — returned a Cloudflare bot challenge. HTTP 403, &lt;em&gt;"Just a moment..."&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;I am not alleging anything. Bot protection is normal and Make did not put it there to stop me. But I am not going to publish a number I could not read, so Make gets an asterisk instead of a figure. That is the standard I am holding myself to in the table above, and it is worth noticing how rarely that standard gets applied to these numbers in the other direction.&lt;/p&gt;

&lt;h2&gt;
  
  
  So what is Magic's number?
&lt;/h2&gt;

&lt;p&gt;If you want a catalogue-style figure from me, here are two honest ones: &lt;strong&gt;27 plugins&lt;/strong&gt; you can install into a cloudlet, exposing &lt;strong&gt;roughly 420 slots&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;Notice that I just gave you two numbers that measure different things, in a section complaining about people giving you two numbers that measure different things. A plugin is a distributable package. A slot is a callable operation. Neither is an "integration" and I am not going to pretend either one belongs in that table.&lt;/p&gt;

&lt;p&gt;Because the honest answer is that &lt;strong&gt;the question is wrong&lt;/strong&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  A catalogue is a list of things somebody already built for you
&lt;/h2&gt;

&lt;p&gt;That is what all of these numbers actually measure: how much work a vendor has done in advance, on your behalf, guessing what you would need.&lt;/p&gt;

&lt;p&gt;It is a real thing to measure! If the vendor guessed right, you save days. Zapier has guessed right nine thousand times and that is a genuine, enormous achievement that I could not replicate and will not belittle.&lt;/p&gt;

&lt;p&gt;But a catalogue has a hard edge. The day you need the thing that is not on the list, the number on the homepage does nothing for you. It does not matter whether it said 400 or 9,000. You are off the map, and what happens next depends entirely on what the platform lets you do when the catalogue runs out.&lt;/p&gt;

&lt;p&gt;Hyperlambda is not a catalogue. It is a language. And the set of integrations a language can express is not a list somebody maintains — it is bounded only by what you can write in it.&lt;/p&gt;

&lt;h2&gt;
  
  
  Funny math, with the working shown
&lt;/h2&gt;

&lt;p&gt;So let us do the same trick they do, except I will show you every step, because the entire point of this article is that they don't.&lt;/p&gt;

&lt;p&gt;A Hyperlambda integration is a text file. A $100 cloudlet — the actual product, the one on &lt;a href="https://hyperlambda.dev/pricing" rel="noopener noreferrer"&gt;the pricing page&lt;/a&gt; — ships with &lt;strong&gt;2 GB of disk&lt;/strong&gt;. That is exactly &lt;strong&gt;2,147,483,648&lt;/strong&gt; bytes, and Hyperlambda source is printable ASCII, one character per byte, call it &lt;strong&gt;90&lt;/strong&gt; usable characters.&lt;/p&gt;

&lt;p&gt;So here is the question, and notice that it is a question about a real machine rather than about infinity: &lt;strong&gt;how many distinct Hyperlambda files can you persist on the cloudlet you are renting from me for a hundred dollars a month?&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;90 ^ 2,147,483,648
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That number has &lt;strong&gt;4,196,703,834 digits&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;Some scale for that, because "four billion digits" does not land on its own:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Counting Zapier's 9,000 apps at one per second takes &lt;strong&gt;two and a half hours&lt;/strong&gt;.&lt;/li&gt;
&lt;li&gt;Reading out my number — not the quantity, just its &lt;em&gt;digits&lt;/em&gt; — at one digit per second takes &lt;strong&gt;133 years&lt;/strong&gt;.&lt;/li&gt;
&lt;li&gt;Add up every published figure in the table above. All of them, every vendor, one grand total: &lt;strong&gt;11,988&lt;/strong&gt;. Dividing my number by that removes &lt;strong&gt;five digits&lt;/strong&gt;. It leaves 4,196,703,829.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;You cannot draw that on a chart. There is no chart.&lt;/p&gt;

&lt;h3&gt;
  
  
  It is larger than every particle in the universe, and that is not a figure of speech
&lt;/h3&gt;

&lt;p&gt;The observable universe contains roughly &lt;strong&gt;10^80&lt;/strong&gt; atoms. Counting every elementary particle rather than every atom — throwing in photons and neutrinos, taking the most generous estimate anyone publishes — gets you to about &lt;strong&gt;10^97&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;My integration count is approximately &lt;strong&gt;10^4,196,703,833&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;So it exceeds the total number of elementary particles in the observable universe by a factor of &lt;strong&gt;10^4,196,703,736&lt;/strong&gt;. To cross that gap starting from the atoms, you would multiply a trillion by itself &lt;strong&gt;349,725,312 times&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;Try to make the universe big enough to catch up. You can't, and the way it fails is instructive:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Suppose every elementary particle in the universe were &lt;em&gt;itself&lt;/em&gt; an entire universe, with its own 10^97 particles. Then suppose every particle in each of &lt;em&gt;those&lt;/em&gt; was another universe. You would need to keep nesting &lt;strong&gt;roughly 43 million levels deep&lt;/strong&gt; before the particle count caught my file count.&lt;/li&gt;
&lt;li&gt;Or go wide instead. The string-theory landscape — the most extravagant number of universes physics has ever seriously written down — is about &lt;strong&gt;10^500&lt;/strong&gt;. Give every one of them 10^97 particles. Total: 10^597. That is every particle in every universe in the largest multiverse anyone has ever proposed, and it &lt;strong&gt;removes 597 digits from a 4,196,703,834-digit number.&lt;/strong&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Every catalogue in that table, plus every particle in every universe in the multiverse, and the number is still essentially unchanged.&lt;/p&gt;

&lt;p&gt;And it fits on a 2 GB disk that costs a hundred dollars a month.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Now the honest part, which is the part they always leave out.&lt;/strong&gt; That number counts every possible string, and the overwhelming majority of those strings are not valid Hyperlambda, let alone useful integrations. It is a preposterous figure. It is &lt;em&gt;supposed&lt;/em&gt; to be a preposterous figure.&lt;/p&gt;

&lt;p&gt;That is the joke. My number is absurd, and I have just shown you precisely how I manufactured it, which means you can check it and reject it. Their numbers are also a construction — a choice about what to count, made by the people who benefit from the answer — and they have shown you nothing. Airbyte's own catalogue disagrees with Airbyte's own hero by 116. Nobody publishes the working.&lt;/p&gt;

&lt;p&gt;The difference between funny math and marketing math is whether the author admits which one they are doing.&lt;/p&gt;

&lt;h2&gt;
  
  
  The part that is not funny math
&lt;/h2&gt;

&lt;p&gt;Underneath the gag there is a real claim, and it does not need a single exponent.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Any API with an OpenAPI specification is already an integration.&lt;/strong&gt; Point Magic at the spec and it generates endpoints and secured MCP tools &lt;a href="https://hyperlambda.dev/blog/convert-your-openapi-specification-to-a-secured-mcp-tool-in-seconds" rel="noopener noreferrer"&gt;in seconds&lt;/a&gt;. Not "we support REST" in a logo grid — the actual typed operations, wired up and callable.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Any database is already an integration.&lt;/strong&gt; Point it at a schema and CRUD endpoints come out the other side, &lt;a href="https://hyperlambda.dev/blog/from-sql-database-to-ai-agent-in-minutes" rel="noopener noreferrer"&gt;MySQL, PostgreSQL, SQL Server, SQLite&lt;/a&gt;, including the twenty-five-year-old one nobody wants to touch.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Any sentence is already an integration.&lt;/strong&gt; This is the one that actually retires the catalogue, and it is the next section.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;And if the language genuinely is not enough&lt;/strong&gt;, there is C#, Python and the terminal underneath it, compiled and loaded into the running process, instantly available to your frontends and over MCP. The escape hatch that Unqork's users &lt;a href="https://hyperlambda.dev/blog/unqork-raised-365-million-to-reinvent-the-config-file" rel="noopener noreferrer"&gt;ask for and do not get&lt;/a&gt; is just... there.&lt;/p&gt;

&lt;h2&gt;
  
  
  English, Swedish, or Urdu
&lt;/h2&gt;

&lt;p&gt;Here is the thing the number is actually standing in for.&lt;/p&gt;

&lt;p&gt;I asked Magic's Hyperlambda generator for an integration. Not by dragging a box onto a canvas. Not by writing code. By typing a sentence — in Norwegian:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;em&gt;Lag et HTTP endepunkt som henter en tilfeldig vits fra Chuck Norris API-et og returnerer vitsen. Kun brukere med rollen 'admin' skal ha tilgang.&lt;/em&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Three seconds later:&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="s"&gt;.arguments&lt;/span&gt;
&lt;span class="s"&gt;auth.ticket.verify:admin&lt;/span&gt;
&lt;span class="s"&gt;http.get:"https://api.chucknorris.io/jokes/random"&lt;/span&gt;
   &lt;span class="s"&gt;convert:true&lt;/span&gt;
&lt;span class="s"&gt;yield&lt;/span&gt;
   &lt;span class="s"&gt;joke:x:@http.get/*/content/*/value&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;It caught &lt;em&gt;"kun brukere med rollen 'admin'"&lt;/em&gt; and emitted the authorisation check. That endpoint is now live, role-secured, and exposed to any AI agent over MCP.&lt;/p&gt;

&lt;p&gt;Then I asked for the same thing in Urdu:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;em&gt;ایک HTTP اینڈ پوائنٹ بنائیں جو Chuck Norris API سے ایک بے ترتیب لطیفہ حاصل کرے اور اسے واپس کرے۔ صرف 'admin' کردار والے صارفین کو رسائی حاصل ہونی چاہیے۔&lt;/em&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;&lt;strong&gt;1.3 seconds.&lt;/strong&gt; Same endpoint. Same &lt;code&gt;auth.ticket.verify:admin&lt;/code&gt;. And — I enjoyed this more than I should have — the Urdu run picked the &lt;em&gt;correct&lt;/em&gt; Chuck Norris URL, where the Norwegian run got it slightly wrong.&lt;/p&gt;

&lt;p&gt;That integration did not exist in anybody's catalogue. It exists now, because somebody described it in Urdu.&lt;/p&gt;

&lt;p&gt;So when a platform's answer to "the catalogue doesn't have it" is &lt;em&gt;"no problem, just write the custom connector yourself"&lt;/em&gt; — in JavaScript, in their SDK, against their component model, with their build step — understand what has happened. The number on the homepage was the marketing. The hand-written code is the product.&lt;/p&gt;

&lt;p&gt;Magic's answer to the same question is a sentence. In whatever language you happen to think in.&lt;/p&gt;

&lt;p&gt;I am not going to pretend the generator is infallible; it is a fine-tuned model and it gets things wrong, which is exactly why the output is &lt;a href="https://hyperlambda.dev/blog/zero-hallucination-code-generation-a-vocabulary-your-ai-cannot-escape" rel="noopener noreferrer"&gt;constrained to a vocabulary it cannot escape&lt;/a&gt; and why you can read every line of what it produced above. It is eight lines. You just read it. Try that with a serialised component graph.&lt;/p&gt;

&lt;h2&gt;
  
  
  Where these platforms genuinely win
&lt;/h2&gt;

&lt;p&gt;The rule of this series is that this section contains no rebuttals. They do not come afterwards either.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Zapier's 9,000 is real and I cannot match it.&lt;/strong&gt; Nine thousand maintained OAuth integrations, credential rotation handled, API changes absorbed by somebody else, usable by a person who has never heard the word "endpoint". If your need is on that list, use Zapier. You will be finished this afternoon and I would be wasting your time.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Airbyte does something I do not do.&lt;/strong&gt; ELT with incremental sync, schema drift handling, normalisation, state management across runs. "Move this table into that warehouse, hourly, forever, and cope when the source changes shape" is a genuinely hard problem and a &lt;code&gt;data.read&lt;/code&gt; does not solve it.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;n8n's canvas is a real product for a real audience.&lt;/strong&gt; When an operations team needs to &lt;em&gt;see&lt;/em&gt; a flow — where it forked, where it died, what the payload looked like at step six — a visual graph beats a text file. I make &lt;a href="https://hyperlambda.dev/n8n-alternative" rel="noopener noreferrer"&gt;the argument for the other side elsewhere&lt;/a&gt;, and it does not win every time.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Workato and Tray sell governance, not connectors.&lt;/strong&gt; Approval workflows, environment promotion, audit, role separation, the compliance paperwork. Enterprises are buying the process, and the connector count is a proxy for "we have been doing this long enough to have built a lot".&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Supabase's 114 are honestly labelled.&lt;/strong&gt; They call them partners, which is what they are. Of everyone in that table, Supabase is the only one whose noun exactly matches the thing being counted — and they have the smallest number. Those two facts are related, and it is to their credit.&lt;/p&gt;

&lt;h2&gt;
  
  
  The decision rule
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Use a catalogue platform if&lt;/strong&gt; the thing you need to connect is on the catalogue. Genuinely. Check the list first. If Zapier has it, the argument is over and you should go and use Zapier.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Use Magic if&lt;/strong&gt; what you need is not on anybody's list — the internal system, the legacy database, the partner's undocumented API, the thing your own company built in 2004 — or if you need the integration to run on your own hardware, or to be readable by the person who inherits it, or to be generated on demand by an AI agent that is constrained by a runtime rather than a system prompt.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;The single question that decides it:&lt;/strong&gt; what happens on the day the catalogue does not have it? Every platform in that table has an answer, and for most of them the answer is "write the connector by hand, in our framework, and maintain it forever". Mine is "describe it in a sentence."&lt;/p&gt;

&lt;h2&gt;
  
  
  The fine print
&lt;/h2&gt;

&lt;p&gt;Every competitor figure in this article was read from the vendor's own public page on &lt;strong&gt;20 September 2026&lt;/strong&gt; and is quoted in the vendor's own unit word. Where a vendor published two conflicting figures, both appear. Where I could not load a page, no figure appears.&lt;/p&gt;

&lt;p&gt;Specifically: Zapier's 9,000+ from their apps directory; Workato's 1,200 from their integration library's meta description and their 1000+ from the popup on that same page; Airbyte's 700+ from their connectors hero and 584 from that page's own catalogue filter; Tray's 474+ from their connectors page; n8n's 400+ from their integrations page; Supabase's 114 from their partners listing; ToolJet's 100+ from their homepage. Retool publishes no aggregate figure; the 74 is my own count of the logos on their integrations page, and the seven-Retool-products and seven-protocols breakdowns are from reading those logos. Make's integrations page returned HTTP 403 Cloudflare challenges to three attempts from two countries.&lt;/p&gt;

&lt;p&gt;These numbers move. If you are reading this months later, check them yourself — and notice whether the unit word changed along with the figure.&lt;/p&gt;

&lt;p&gt;The 4,196,703,834 is &lt;code&gt;floor(2147483648 × log10(90)) + 1&lt;/code&gt;, where 2,147,483,648 is the 2 GB of disk on a $100 cloudlet expressed in bytes, at one printable-ASCII character per byte. The premise is stated in full in that section, and the premise is where all the mischief lives, which is the entire point of including it. The Norwegian and Urdu generations are real, unedited, and were run through the live generator while writing this article; the timings are what the API reported.&lt;/p&gt;

&lt;p&gt;The physics comparisons use the standard order-of-magnitude figures: ~10^80 atoms in the observable universe, ~10^97 elementary particles on the most generous published estimates, and ~10^500 for the string-theory landscape. These are order-of-magnitude estimates and not precise measurements, which does not matter here — moving any of them by ten orders of magnitude changes the conclusion by ten digits out of four billion.&lt;/p&gt;

&lt;p&gt;Magic's own figures: 27 installable plugins and roughly 420 slots, both of which I have just argued are the wrong unit.&lt;/p&gt;

&lt;p&gt;And the obvious disclosure: I wrote Hyperlambda, I sell Magic hosting, and I chose which numbers to put in a table. I have made every one of them checkable precisely because I am not a neutral party. If I have been unfair to a vendor, their page is public and so is my method — go and check, and tell me if I got something wrong.&lt;/p&gt;

&lt;p&gt;For whatever it is worth as a credential: I have been writing software since I was eight years old, that is forty-four years now, and I am cited on microsoft.com.&lt;/p&gt;

&lt;h2&gt;
  
  
  Frequently asked questions
&lt;/h2&gt;

&lt;h3&gt;
  
  
  How many integrations does Magic have?
&lt;/h3&gt;

&lt;p&gt;Magic does not have an integration catalogue, so the number does not exist in the form the question expects. It ships 27 installable plugins exposing roughly 420 slots, it turns any OpenAPI specification into secured endpoints and MCP tools, it generates CRUD APIs from any supported database schema, and it generates new integrations from a natural-language sentence. The constraint is what you can describe, not what a vendor built in advance.&lt;/p&gt;

&lt;h3&gt;
  
  
  Which platform publishes the most integrations?
&lt;/h3&gt;

&lt;p&gt;Zapier, at 9,000+ "apps" as published in September 2026, ahead of Workato at 1,200 "pre-built connectors", Airbyte at 700+ "connectors", Tray at 474+, n8n at 400+, Supabase at 114 "partners" and ToolJet at 100+. Retool publishes no aggregate figure. These units are not equivalent to each other.&lt;/p&gt;

&lt;h3&gt;
  
  
  Why do Airbyte's and Workato's integration counts contradict themselves?
&lt;/h3&gt;

&lt;p&gt;Both publish two different figures on a single page. Airbyte's hero says 700+ connectors while that page's own catalogue filter says "Showing 100 of 584". Workato's page meta description says more than 1,200 pre-built connectors while a popup on the same page says 1000+ apps. Both were observed on 20 September 2026.&lt;/p&gt;

&lt;h3&gt;
  
  
  Does Supabase have integrations?
&lt;/h3&gt;

&lt;p&gt;Supabase publishes 114 entries that it explicitly calls &lt;strong&gt;partners&lt;/strong&gt;, not integrations — companies with a business relationship with Supabase. It is the only figure in this comparison whose unit word accurately describes what is being counted.&lt;/p&gt;

&lt;h3&gt;
  
  
  Can you create an integration without writing code?
&lt;/h3&gt;

&lt;p&gt;Yes. Magic's Hyperlambda generator turns a natural-language description into a working, role-secured endpoint. This was verified for this article in Norwegian (3.0 seconds) and Urdu (1.3 seconds), both producing a correct authorisation check. The generated Hyperlambda is readable text you can review before it goes live.&lt;/p&gt;

&lt;h3&gt;
  
  
  Is Magic's integration count really bigger than the number of particles in the universe?
&lt;/h3&gt;

&lt;p&gt;Yes, on the stated premise, and the premise is the arithmetic in the article rather than a claim about physics. A 2 GB cloudlet holds 2,147,483,648 bytes; at 90 printable ASCII characters per byte that is 90^2,147,483,648 distinct files, a number with 4,196,703,834 digits, or roughly 10^4,196,703,833. The observable universe holds about 10^80 atoms and at most about 10^97 elementary particles. Even every particle in every universe of the 10^500 string-theory landscape removes only 597 digits from the total. This is deliberately absurd arithmetic, presented with its working shown.&lt;/p&gt;

&lt;h3&gt;
  
  
  What happens when an integration is not in the catalogue?
&lt;/h3&gt;

&lt;p&gt;On a catalogue platform you write a custom connector by hand in that vendor's framework and maintain it yourself. On Magic you describe the integration in a sentence, or import its OpenAPI specification, and if the language genuinely cannot express it there is C#, Python and terminal access underneath, compiled into the running process and immediately available to frontends and over MCP.&lt;/p&gt;

&lt;h2&gt;
  
  
  Related reading
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/magic-vs-n8n-an-honest-feature-matrix" rel="noopener noreferrer"&gt;Magic vs n8n: An Honest Feature Matrix&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/zero-hallucination-code-generation-a-vocabulary-your-ai-cannot-escape" rel="noopener noreferrer"&gt;Zero Hallucination Code Generation: A Vocabulary Your AI Cannot Escape&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/convert-your-openapi-specification-to-a-secured-mcp-tool-in-seconds" rel="noopener noreferrer"&gt;Convert Your OpenAPI Specification to a Secured MCP Tool in Seconds&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/from-prompt-to-mcp-tool-in-5-seconds" rel="noopener noreferrer"&gt;From Prompt to MCP Tool in 5 Seconds&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/the-last-mcp-server-youll-ever-need" rel="noopener noreferrer"&gt;The Last MCP Server You'll Ever Need&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/what-is-hyperlambda-and-how-does-it-work" rel="noopener noreferrer"&gt;What Is Hyperlambda and How Does It Work?&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>integrations</category>
      <category>automation</category>
      <category>lowcode</category>
      <category>ai</category>
    </item>
    <item>
      <title>Masturbation Is 100 Times More Dangerous Than AI</title>
      <dc:creator>Thomas Hansen</dc:creator>
      <pubDate>Mon, 14 Sep 2026 13:01:38 +0000</pubDate>
      <link>https://dev.to/polterguy/masturbation-is-100-times-more-dangerous-than-ai-1bjm</link>
      <guid>https://dev.to/polterguy/masturbation-is-100-times-more-dangerous-than-ai-1bjm</guid>
      <description>&lt;p&gt;This headline is intentionally provocative.&lt;/p&gt;

&lt;p&gt;It is also based on a simple comparison between two uncertain figures.&lt;/p&gt;

&lt;p&gt;  &lt;iframe src="https://www.youtube.com/embed/4VinqAsv8z0" width="710" height="399"&gt;
  &lt;/iframe&gt;
&lt;/p&gt;

&lt;h2&gt;
  
  
  The comparison
&lt;/h2&gt;

&lt;p&gt;An old estimate suggested that between &lt;strong&gt;250 and 1,000 people die each year in the United States from autoerotic asphyxia&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;Autoerotic asphyxia means sexual activity involving strangulation or oxygen restriction. It is not ordinary masturbation.&lt;/p&gt;

&lt;p&gt;Separately, a small number of suicides involving ChatGPT, Claude and other conversational AI systems have been publicly reported or alleged through lawsuits, family statements and investigations.&lt;/p&gt;

&lt;p&gt;A reasonable working estimate for these publicly reported AI-associated suicides is approximately &lt;strong&gt;2 to 10 cases&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;Using midpoint figures:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;500 autoerotic deaths ÷ 5 AI-associated suicides = 100&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Therefore:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Masturbation is approximately 100 times more dangerous than AI.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;The calculation is not a medical conclusion. It is a statistical punchline.&lt;/p&gt;

&lt;h2&gt;
  
  
  The limitations
&lt;/h2&gt;

&lt;p&gt;The estimate of 250 to 1,000 autoerotic deaths per year is old and uncertain.&lt;/p&gt;

&lt;p&gt;A recent systematic review identified 101 published autoerotic death cases across 44 years. This is not a complete national or global registry. It only counts cases documented in the forensic literature.&lt;/p&gt;

&lt;p&gt;AI-associated deaths have similar classification problems.&lt;/p&gt;

&lt;p&gt;A death may involve:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;A chatbot conversation&lt;/li&gt;
&lt;li&gt;Existing mental illness&lt;/li&gt;
&lt;li&gt;Social isolation&lt;/li&gt;
&lt;li&gt;Family conflict&lt;/li&gt;
&lt;li&gt;Drug use&lt;/li&gt;
&lt;li&gt;Financial or relationship problems&lt;/li&gt;
&lt;li&gt;Other online communities&lt;/li&gt;
&lt;li&gt;Several simultaneous causes&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The presence of an AI conversation does not, by itself, establish causation.&lt;/p&gt;

&lt;p&gt;There is currently no standard death-certificate category called “death caused by ChatGPT” or “death caused by Claude.”&lt;/p&gt;

&lt;p&gt;&lt;a href="https://eric.ed.gov/?id=EJ480743" rel="noopener noreferrer"&gt;Historical autoerotic-death estimate&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://link.springer.com/article/10.1007/s00414-024-03367-0" rel="noopener noreferrer"&gt;Recent systematic review of autoerotic deaths&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://aimortality.org/" rel="noopener noreferrer"&gt;Database of reported AI-associated fatalities&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Other unusual causes of death
&lt;/h2&gt;

&lt;p&gt;The following figures are mostly from the United States.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Cause&lt;/th&gt;
&lt;th&gt;Approximate figure&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Bee, wasp and hornet stings&lt;/td&gt;
&lt;td&gt;72 deaths per year&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Cattle-related incidents&lt;/td&gt;
&lt;td&gt;Approximately 20–22 deaths per year in older estimates&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Lightning&lt;/td&gt;
&lt;td&gt;Approximately 20 deaths per year&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Furniture and television tip-overs&lt;/td&gt;
&lt;td&gt;217 reported deaths from 2013 to July 2023&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Vending machines&lt;/td&gt;
&lt;td&gt;37 reported deaths from 1978 to 1995&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Shark attacks&lt;/td&gt;
&lt;td&gt;Usually 5–10 deaths worldwide per year&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Falling coconuts&lt;/td&gt;
&lt;td&gt;Unknown&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Garden rakes&lt;/td&gt;
&lt;td&gt;Unknown&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;h3&gt;
  
  
  Bee, wasp and hornet stings
&lt;/h3&gt;

&lt;p&gt;The CDC recorded 788 deaths from hornet, wasp and bee stings between 2011 and 2021.&lt;/p&gt;

&lt;p&gt;That equals an average of 72 deaths per year.&lt;/p&gt;

&lt;p&gt;The annual figure ranged from 59 to 89. Eighty-four percent of the victims were male.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://www.cdc.gov/mmwr/volumes/72/wr/pdfs/mm7227a6-H.pdf" rel="noopener noreferrer"&gt;CDC data&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Cattle
&lt;/h3&gt;

&lt;p&gt;Cattle can kill people by trampling, kicking, crushing or striking them.&lt;/p&gt;

&lt;p&gt;Older CDC agricultural estimates placed cattle-related deaths at approximately 20–22 per year in the United States.&lt;/p&gt;

&lt;p&gt;The victims were mainly agricultural workers handling cattle in pens, chutes and loading areas.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://stacks.cdc.gov/view/cdc/230082" rel="noopener noreferrer"&gt;CDC agricultural safety material&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Lightning
&lt;/h3&gt;

&lt;p&gt;Lightning kills approximately 20 people per year in the United States.&lt;/p&gt;

&lt;p&gt;The rate has declined substantially over the last several decades because of improved warnings, public education, emergency care and changes in outdoor work.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://stacks.cdc.gov/view/cdc/259425" rel="noopener noreferrer"&gt;CDC-hosted lightning mortality study&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Furniture and televisions
&lt;/h3&gt;

&lt;p&gt;Unsecured furniture, televisions and appliances can tip over onto people.&lt;/p&gt;

&lt;p&gt;The Consumer Product Safety Commission reported 217 fatalities from January 2013 through July 2023. Of those victims, 155 were children.&lt;/p&gt;

&lt;p&gt;The same report estimated approximately 17,800 emergency-department-treated injuries per year from these incidents.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://www.cpsc.gov/s3fs-public/2023_Annual_Tip_Over_Report_Posted_2024Feb_FINAL_0.pdf" rel="noopener noreferrer"&gt;CPSC tip-over report&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Vending machines
&lt;/h3&gt;

&lt;p&gt;The vending-machine statistic is often exaggerated.&lt;/p&gt;

&lt;p&gt;The CPSC reported at least 37 deaths between 1978 and 1995 after people rocked or tilted vending machines.&lt;/p&gt;

&lt;p&gt;That equals approximately two deaths per year during that period.&lt;/p&gt;

&lt;p&gt;The machines fell onto the victims. They did not kill people by dispensing drinks incorrectly.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://www.cpsc.gov/Newsroom/News-Releases/1996/CPSC-Soda-Vending-Machine-Industry-Labeling-Campaign-Warns-Of-Deaths-And-Injuries" rel="noopener noreferrer"&gt;CPSC vending-machine warning&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Falling coconuts
&lt;/h3&gt;

&lt;p&gt;Falling coconuts can cause fatal head injuries.&lt;/p&gt;

&lt;p&gt;However, the popular claim that coconuts kill 150 people per year is unsupported.&lt;/p&gt;

&lt;p&gt;The figure appears to have developed from a medical report about coconut injuries in Papua New Guinea and was later repeated as a global estimate.&lt;/p&gt;

&lt;p&gt;Actual coconut deaths occur, but the annual global number is unknown.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://pubmed.ncbi.nlm.nih.gov/6502774/" rel="noopener noreferrer"&gt;Original medical paper&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Why the comparison is useful
&lt;/h2&gt;

&lt;p&gt;The headline does not prove that AI is harmless.&lt;/p&gt;

&lt;p&gt;A handful of reported suicides involving AI systems is still serious, particularly where a system may reinforce delusions, dependency or suicidal thinking.&lt;/p&gt;

&lt;p&gt;The comparison demonstrates something else:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Humans have been dying from bizarre, mundane and poorly tracked activities for a very long time.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Masturbation-related deaths have an old and uncertain estimate.&lt;/p&gt;

&lt;p&gt;AI-associated suicides have a new and uncertain estimate.&lt;/p&gt;

&lt;p&gt;The exact ratio cannot be proven.&lt;/p&gt;

&lt;p&gt;But “Masturbation Is 100 Times More Dangerous Than AI” remains a mathematically plausible thing you can quote me on in the public space, and easily be within 2 order of magnitudes correct ...&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;NOW let's talk about AI regulations&lt;/strong&gt; ...&lt;/p&gt;

</description>
      <category>ai</category>
      <category>statistics</category>
      <category>health</category>
      <category>humor</category>
    </item>
    <item>
      <title>Your sitemap is an API — a whole website as one JSON document in 35 lines</title>
      <dc:creator>Thomas Hansen</dc:creator>
      <pubDate>Mon, 14 Sep 2026 07:56:19 +0000</pubDate>
      <link>https://dev.to/polterguy/your-sitemap-is-an-api-a-whole-website-as-one-json-document-in-35-lines-2eai</link>
      <guid>https://dev.to/polterguy/your-sitemap-is-an-api-a-whole-website-as-one-json-document-in-35-lines-2eai</guid>
      <description>&lt;p&gt;Every time I want to give a model a &lt;em&gt;site&lt;/em&gt; rather than a &lt;em&gt;page&lt;/em&gt;, I end up writing the same throwaway script. Fetch the sitemap. Loop the URLs. Pull the title, the H1, the meta description. Strip the HTML down to something readable. Glue it into one file. Delete the script. Write it again three weeks later.&lt;/p&gt;

&lt;p&gt;So I made it a URL instead:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;a href="https://hyperlambda.dev/website-to-json" rel="noopener noreferrer"&gt;https://hyperlambda.dev/website-to-json&lt;/a&gt;&lt;/strong&gt; — paste a domain, get one JSON document back. Free, no signup, no key.&lt;/p&gt;

&lt;h2&gt;
  
  
  What comes back
&lt;/h2&gt;

&lt;p&gt;One array, one object per page:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"url"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"https://example.com/pricing"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"h1"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Pricing"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"title"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Pricing | Example"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"One flat price, no surprises."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"markdown"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"# Pricing&lt;/span&gt;&lt;span class="se"&gt;\n\n&lt;/span&gt;&lt;span class="s2"&gt;One flat price…"&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That shape is the whole point. &lt;code&gt;markdown&lt;/code&gt; is the part you feed a model; &lt;code&gt;url&lt;/code&gt;, &lt;code&gt;h1&lt;/code&gt;, &lt;code&gt;title&lt;/code&gt; and &lt;code&gt;description&lt;/code&gt; are the parts you filter, dedupe and cite with. A folder of 50 Markdown files makes you rebuild that metadata yourself. One JSON document doesn't.&lt;/p&gt;

&lt;p&gt;Useful immediately for: seeding a RAG index, diffing a site before and after a migration, auditing which pages are missing a meta description, or handing a competitor's docs to a model without writing a crawler.&lt;/p&gt;

&lt;h2&gt;
  
  
  The entire backend
&lt;/h2&gt;

&lt;p&gt;Not a snippet of it. This is the deployed file:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;.arguments
   url:string

// Throttling to maximum 5 requests per IP per minute!
execution.throttle.create:website-to-json
   limit:int:5
   window:int:60
   per:ip
execution.throttle:website-to-json

strings.concat
   get-value:x:@.arguments/*/url
   .:/sitemap.xml
http.get:x:-
xml2lambda:x:-/*/content
.result
for-each:x:@xml2lambda/*/urlset/*/url/*/loc/*/#text/[0,50]
   http.get:x:@.dp/#
   html2lambda:x:-/*/content
   .h1
   strings.join:x:@html2lambda/*/html/*/body/**/h1/[0,1]/**/#text
      .:" "
   set-value:x:@.h1
      strings.trim:x:@strings.join
   .title
   set-value:x:@.title
      get-value:x:@html2lambda/*/html/*/head/*/title/*/#text
   .description
   set-value:x:@.description
      get-value:x:"@html2lambda/*/html/*/head/*/meta/*/\\@name/=description/./*/\\@content"
   lambda2html:x:@html2lambda/*/html/*/body
   html2markdown:x:@lambda2html
      url:x:@.arguments/*/url
   unwrap:x:+/*/*/*
   add:x:@.result
      .
         .
            url:x:@.dp/#
            h1:x:@.h1
            title:x:@.title
            description:x:@.description
            markdown:x:@html2markdown
return-nodes:x:@.result/*
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;No dependencies, no build step, no project scaffold. That file &lt;em&gt;is&lt;/em&gt; the deployment — saving it publishes the endpoint.&lt;/p&gt;

&lt;h2&gt;
  
  
  The parts worth stealing
&lt;/h2&gt;

&lt;p&gt;This is Hyperlambda, where code is a tree rather than text, and the interesting bits are the expressions that walk it.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;The sitemap is parsed, not regexed.&lt;/strong&gt; &lt;code&gt;xml2lambda&lt;/code&gt; turns the XML into nodes, and then the loop selects every URL in one expression:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;for-each:x:@xml2lambda/*/urlset/*/url/*/loc/*/#text/[0,50]
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Read it right to left: every &lt;code&gt;#text&lt;/code&gt; under every &lt;code&gt;loc&lt;/code&gt; under every &lt;code&gt;url&lt;/code&gt; in the &lt;code&gt;urlset&lt;/code&gt; — then &lt;code&gt;[0,50]&lt;/code&gt; slices the first fifty. The page limit isn't an &lt;code&gt;if&lt;/code&gt; with a counter; it's part of the address of the data.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Attribute matching without a DOM library.&lt;/strong&gt; Pulling &lt;code&gt;&amp;lt;meta name="description" content="…"&amp;gt;&lt;/code&gt; is one expression:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;@html2lambda/*/html/*/head/*/meta/*/\@name/=description/./*/\@content
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Find the &lt;code&gt;@name&lt;/code&gt; attribute whose value equals &lt;code&gt;description&lt;/code&gt;, step back up to its element with &lt;code&gt;.&lt;/code&gt;, then take that element's &lt;code&gt;@content&lt;/code&gt;. Attributes are &lt;code&gt;\@&lt;/code&gt;-prefixed nodes, so they're addressable the same way elements are.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;H1 text is joined, not assumed.&lt;/strong&gt; An &lt;code&gt;&amp;lt;h1&amp;gt;&lt;/code&gt; containing a &lt;code&gt;&amp;lt;span&amp;gt;&lt;/code&gt; and a stray &lt;code&gt;&amp;lt;br&amp;gt;&lt;/code&gt; has several text nodes. &lt;code&gt;**/#text&lt;/code&gt; collects all of them under the first H1 and &lt;code&gt;strings.join&lt;/code&gt; puts them back together with a space — so &lt;code&gt;&amp;lt;h1&amp;gt;Build &amp;lt;span&amp;gt;fast&amp;lt;/span&amp;gt;&amp;lt;/h1&amp;gt;&lt;/code&gt; yields &lt;code&gt;Build fast&lt;/code&gt;, not &lt;code&gt;Build&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Relative links survive.&lt;/strong&gt; The body is serialized back to HTML and converted with the original domain passed in:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;html2markdown:x:@lambda2html
   url:x:@.arguments/*/url
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Without that, every &lt;code&gt;/pricing&lt;/code&gt; in the output would be a dead relative link the moment the JSON left the site it came from.&lt;/p&gt;

&lt;h2&gt;
  
  
  What it will not do
&lt;/h2&gt;

&lt;p&gt;Worth stating plainly, because a crawler that pretends otherwise wastes your afternoon:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;It needs a sitemap.&lt;/strong&gt; The URL you pass gets &lt;code&gt;/sitemap.xml&lt;/code&gt; appended, so pass the origin with no trailing slash (&lt;code&gt;https://example.com&lt;/code&gt;). No sitemap, no output. Sites that keep a sitemap index rather than a flat urlset won't enumerate either.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;It does not run JavaScript.&lt;/strong&gt; Server-rendered HTML only. A client-rendered app returns its shell, exactly like &lt;code&gt;curl&lt;/code&gt; would.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Fifty pages, hard.&lt;/strong&gt; Fine for a docs section or a marketing site; not a crawler for your 40,000-page store.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Five requests per minute per IP.&lt;/strong&gt; It's a free shared endpoint doing 50 HTTP fetches per call. Hammer it and you'll just get throttled — the source is above, run your own.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;It also costs the target site 50 requests, so point it at your own property or something that welcomes it.&lt;/p&gt;

&lt;h2&gt;
  
  
  The part I actually find interesting
&lt;/h2&gt;

&lt;p&gt;The file above was written from a plain-English description by a code generator, and every function in it was verified against the functions that actually exist on the server &lt;em&gt;before&lt;/em&gt; it was saved. Not "the model probably got the API right" — checked, then deployed, with no restart.&lt;/p&gt;

&lt;p&gt;That inverts the usual trade-off with generated backend code. The risk isn't that the model writes ugly code, it's that it writes code that references something imaginary and fails at 3am. If the runtime refuses to save anything that invokes a function it doesn't have, the failure happens at generation time instead.&lt;/p&gt;

&lt;p&gt;Same property makes it an agent tool rather than a web page: on this stack every HTTP endpoint is also an MCP tool, role-filtered, so an agent can call &lt;code&gt;website-to-json&lt;/code&gt; and get the same array without a browser in the loop.&lt;/p&gt;

&lt;h2&gt;
  
  
  Try it
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;The tool: &lt;strong&gt;&lt;a href="https://hyperlambda.dev/website-to-json" rel="noopener noreferrer"&gt;https://hyperlambda.dev/website-to-json&lt;/a&gt;&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;More free ones — page to JSON, dead link checker, link preview checker, llms.txt generator: &lt;strong&gt;&lt;a href="https://hyperlambda.dev/tools" rel="noopener noreferrer"&gt;https://hyperlambda.dev/tools&lt;/a&gt;&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;Run the whole platform yourself, MIT-licensed:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-fsSL&lt;/span&gt; https://hyperlambda.dev/docker-compose.yaml | docker compose &lt;span class="nt"&gt;-f&lt;/span&gt; - up
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If you build something with the output, I'd like to hear what you pointed it at.&lt;/p&gt;

</description>
      <category>webdev</category>
      <category>ai</category>
      <category>showdev</category>
      <category>opensource</category>
    </item>
    <item>
      <title>I built 9 free web tools and printed the entire backend on every page. What should number 10 be?</title>
      <dc:creator>Thomas Hansen</dc:creator>
      <pubDate>Sun, 13 Sep 2026 05:47:20 +0000</pubDate>
      <link>https://dev.to/polterguy/i-built-9-free-web-tools-and-printed-the-entire-backend-on-every-page-what-should-number-10-be-1a8f</link>
      <guid>https://dev.to/polterguy/i-built-9-free-web-tools-and-printed-the-entire-backend-on-every-page-what-should-number-10-be-1a8f</guid>
      <description>&lt;p&gt;Over the last couple of weeks I've built nine small web tools. No signup, no API key, no "start your free trial". You paste a URL, you get a result.&lt;/p&gt;

&lt;p&gt;There's a catch, and it's the interesting part: &lt;strong&gt;every tool prints the complete source code of its own backend, right there on the page.&lt;/strong&gt; Not a snippet. Not pseudocode. The actual file that ran when you clicked the button.&lt;/p&gt;

&lt;p&gt;I did that because I wanted the tools to be an argument, not a brochure. If I claim a backend is small, you shouldn't have to take my word for it.&lt;/p&gt;

&lt;p&gt;Now I've run out of good ideas for number ten, which is why I'm writing this. &lt;strong&gt;Skip to the bottom if you just want to tell me what to build.&lt;/strong&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  The nine
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;&lt;a href="https://hyperlambda.dev/url-to-markdown" rel="noopener noreferrer"&gt;URL to Markdown&lt;/a&gt;&lt;/strong&gt; — paste a link, get clean Markdown for an LLM prompt, plus the token count before and after so you can see what the HTML was costing you.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;a href="https://hyperlambda.dev/page-to-json" rel="noopener noreferrer"&gt;Page to JSON&lt;/a&gt;&lt;/strong&gt; — one page as structured JSON: title, H1, description, text, every link &lt;em&gt;with its anchor text&lt;/em&gt;, every image &lt;em&gt;with its alt&lt;/em&gt;. Missing anchor and alt text get flagged rather than silently returned as empty strings.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;a href="https://hyperlambda.dev/website-to-json" rel="noopener noreferrer"&gt;Website to JSON&lt;/a&gt;&lt;/strong&gt; — same idea, but walks the sitemap instead of one page.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;a href="https://hyperlambda.dev/url-to-yaml" rel="noopener noreferrer"&gt;URL to YAML&lt;/a&gt;&lt;/strong&gt; — a page's metadata as YAML.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;a href="https://hyperlambda.dev/llms-txt-generator" rel="noopener noreferrer"&gt;llms.txt generator&lt;/a&gt;&lt;/strong&gt; — builds an &lt;code&gt;llms.txt&lt;/code&gt; from your sitemap.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;a href="https://hyperlambda.dev/ai-crawler-check" rel="noopener noreferrer"&gt;AI Crawler Check&lt;/a&gt;&lt;/strong&gt; — which AI crawlers your &lt;code&gt;robots.txt&lt;/code&gt; actually allows or blocks, &lt;strong&gt;citing the exact rule that decided each one&lt;/strong&gt;. Also checks whether your content survives without JavaScript, because most AI crawlers don't render it.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;a href="https://hyperlambda.dev/link-preview-checker" rel="noopener noreferrer"&gt;Link Preview Checker&lt;/a&gt;&lt;/strong&gt; — what your Open Graph and Twitter cards really look like to a scraper.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;a href="https://hyperlambda.dev/website-image-gallery" rel="noopener noreferrer"&gt;Website Image Gallery&lt;/a&gt;&lt;/strong&gt; — every image across your site with its alt text, so you can find the ones missing it.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;a href="https://hyperlambda.dev/dead-link-checker" rel="noopener noreferrer"&gt;Dead Link Checker&lt;/a&gt;&lt;/strong&gt; — crawls your sitemap and reports links that don't answer 200.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;All nine are here: &lt;strong&gt;&lt;a href="https://hyperlambda.dev/tools" rel="noopener noreferrer"&gt;hyperlambda.dev/tools&lt;/a&gt;&lt;/strong&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  What "the whole backend" actually looks like
&lt;/h2&gt;

&lt;p&gt;Here's URL to Markdown, in full. This is not an excerpt:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;.arguments
   url:string
validators.mandatory:x:@.arguments/*/url
validators.url:x:@.arguments/*/url
http.get:x:@.arguments/*/url
html2markdown:x:-/*/content
   url:x:@.arguments/*/url
openai.tokenize:x:@http.get/*/content
openai.tokenize:x:@html2markdown
yield
   markdown:x:@html2markdown
   html_tokens:x:@openai.tokenize/@openai.tokenize
   markdown_tokens:x:@openai.tokenize
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Fetch it, convert it, count the tokens twice, return three fields. The language is &lt;a href="https://hyperlambda.dev" rel="noopener noreferrer"&gt;Hyperlambda&lt;/a&gt;, which is my own thing, so take the language advocacy with as much salt as you like — the point I care about is that a working tool can be this small, and that you can check.&lt;/p&gt;

&lt;p&gt;Not all nine are that short. The dead link checker is about seventy lines, because deduplicating links and surviving hosts that refuse connections is genuinely more work. That page says so and prints all seventy.&lt;/p&gt;

&lt;h2&gt;
  
  
  They're also MCP tools
&lt;/h2&gt;

&lt;p&gt;Every HTTP endpoint on this platform is automatically exposed as an &lt;a href="https://hyperlambda.dev/mcp-server" rel="noopener noreferrer"&gt;MCP&lt;/a&gt; tool, filtered by role. So these aren't just web pages — an agent can call the same endpoints directly, and "build a tool" and "build an agent tool" stopped being two separate tasks.&lt;/p&gt;

&lt;p&gt;That turned out to be the thing I use most. Half of these exist because I wanted Claude to be able to read a page properly.&lt;/p&gt;

&lt;h2&gt;
  
  
  The honest limits
&lt;/h2&gt;

&lt;p&gt;Things I'd rather you hear from me than discover:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;No JavaScript rendering.&lt;/strong&gt; Everything fetches server-rendered HTML. A client-side-rendered SPA comes back nearly empty — which is also exactly what most AI crawlers see, so arguably that's the useful answer.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;The dead link checker crawls 10 sitemap pages max&lt;/strong&gt;, though it checks every link it finds on them.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;The image gallery caps out at 50 results.&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;Some sites return 403/999 to anything that isn't a browser. That's a bot refusal, not a broken link, and the dead link checker separates those into their own bucket instead of calling them dead.&lt;/li&gt;
&lt;li&gt;These are free and shared. Please don't point a load test at them.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  So — what should number 10 be?
&lt;/h2&gt;

&lt;p&gt;This is the actual reason for the post. I'm better at building these than at thinking of them.&lt;/p&gt;

&lt;p&gt;What I'm after is the thing you currently do by hand, or with a browser extension you don't trust, or by pasting into three different sites in sequence. Ideas I've had and rejected as too boring: another JSON formatter, another minifier, another base64 thing.&lt;/p&gt;

&lt;p&gt;Some prompts, if it helps:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;What's the last web-related task where you thought &lt;em&gt;"surely something does this for me"&lt;/em&gt; and nothing did?&lt;/li&gt;
&lt;li&gt;Is there a tool you use that's fine except for one missing feature?&lt;/li&gt;
&lt;li&gt;What would you want an &lt;strong&gt;AI agent&lt;/strong&gt; to be able to do to a web page, that it currently can't?&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Reply with whatever comes to mind. If I build yours I'll say so in the thread, and it'll be free and no-signup like the rest.&lt;/p&gt;

&lt;p&gt;And if one of the nine is broken or wrong for your site, I'd genuinely rather know — tell me the URL you tried.&lt;/p&gt;

</description>
      <category>showdev</category>
      <category>webdev</category>
      <category>ai</category>
      <category>opensource</category>
    </item>
    <item>
      <title>Magic vs Directus: An Honest Feature Matrix</title>
      <dc:creator>Thomas Hansen</dc:creator>
      <pubDate>Tue, 01 Sep 2026 06:28:11 +0000</pubDate>
      <link>https://dev.to/polterguy/magic-vs-directus-an-honest-feature-matrix-4onb</link>
      <guid>https://dev.to/polterguy/magic-vs-directus-an-honest-feature-matrix-4onb</guid>
      <description>&lt;p&gt;The &lt;a href="https://hyperlambda.dev/blog/magic-vs-n8n-an-honest-feature-matrix" rel="noopener noreferrer"&gt;n8n matrix&lt;/a&gt; was easy mode. The &lt;a href="https://hyperlambda.dev/blog/magic-vs-pocketbase-an-honest-feature-matrix" rel="noopener noreferrer"&gt;PocketBase one&lt;/a&gt; was hard mode, because PocketBase is Magic's closest architectural sibling.&lt;/p&gt;

&lt;p&gt;This one is different again. Directus is not Magic's closest sibling — it is Magic's closest &lt;em&gt;competitor&lt;/em&gt;. If you are evaluating a platform that wraps a database you already have, in whatever engine it happens to live in, without migrating anything, then Directus and Magic are pitching you the same sentence. It is a genuinely excellent product with a decade of polish on it, and on several rows below it beats Magic outright.&lt;/p&gt;

&lt;p&gt;One sentence of thesis before the table, because every row descends from it:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Directus computes your API at runtime. Magic writes it to disk.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Directus introspects your schema, holds permissions as configuration, and resolves each request against both. Nothing is written down — the effective API exists only as the result of that computation. Magic's generator emits actual endpoint files you can open, read, diff, edit and commit. Watch how far that one difference propagates.&lt;/p&gt;

&lt;h2&gt;
  
  
  The matrix
&lt;/h2&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Feature&lt;/th&gt;
&lt;th&gt;Directus&lt;/th&gt;
&lt;th&gt;Magic Cloud&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Licence&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Monospace Sustainable Core License — source-available, non-compete, with licence-key enforcement you may not circumvent; converts to GPL-3.0 four years after each release&lt;/td&gt;
&lt;td&gt;MIT, all of it, no thresholds and no conversion date&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Free tier&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Core: 3 user seats, 25 collections, 5 flows, no SSO&lt;/td&gt;
&lt;td&gt;Self-host everything, uncapped, forever&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Small-company escape hatch&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Open Innovation Grant — fully permissive and free under $5M revenue &lt;strong&gt;and&lt;/strong&gt; under 50 employees&lt;/td&gt;
&lt;td&gt;Not needed; MIT has no revenue test&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Paid tier&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Team at $499/mo annual, $599 monthly — 10 SSO seats, 50 collections, 20 flows&lt;/td&gt;
&lt;td&gt;$100/mo per cloudlet, $300 for double the machine&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Per-user cost&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;$50 per extra seat per month&lt;/td&gt;
&lt;td&gt;None — unlimited users, never counted&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Table cap&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;A collection maps to a database table: 25 on Core, 50 on Team, $100 per extra 25&lt;/td&gt;
&lt;td&gt;None&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Managed hosting&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;$99/mo add-on, on top of the plan&lt;/td&gt;
&lt;td&gt;Included in the cloudlet price&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;SSO&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Team plan and up; unavailable on Core at any price&lt;/td&gt;
&lt;td&gt;Eight OIDC providers built in — Google, Microsoft, GitHub, LinkedIn, Slack, Okta, Auth0, Keycloak&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;The API&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Computed at runtime from schema and config&lt;/td&gt;
&lt;td&gt;Generated Hyperlambda files — real, readable, versionable&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Schema changes&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Reflected instantly, nothing to regenerate&lt;/td&gt;
&lt;td&gt;Re-run the generator&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Database engines&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;PostgreSQL, MySQL, MariaDB, SQLite, SQL Server, OracleDB, CockroachDB&lt;/td&gt;
&lt;td&gt;SQLite built in, plus MySQL, PostgreSQL and SQL Server&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Access control&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Granular: field-level and item-level rules as filter expressions&lt;/td&gt;
&lt;td&gt;Endpoint-level role gating, plus &lt;a href="https://hyperlambda.dev/blog/why-secure-ai-code-execution-requires-runtime-whitelisting-not-prompt-filtering" rel="noopener noreferrer"&gt;runtime slot whitelisting&lt;/a&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Custom logic&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Extensions in TypeScript, with a build step; Flows with sandboxed JS operations&lt;/td&gt;
&lt;td&gt;Hyperlambda files, hot — no compile, no restart, generated from a prompt if you like&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Content features&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Revisions, drafts, translations, activity log — a decade of CMS heritage&lt;/td&gt;
&lt;td&gt;None of it; not a CMS&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Assets&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;File library with on-the-fly image transformation&lt;/td&gt;
&lt;td&gt;File system, upload tickets, image resize and convert&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Realtime&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;WebSockets and GraphQL subscriptions&lt;/td&gt;
&lt;td&gt;SignalR — programmable events&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Frontend hosting&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Not the story&lt;/td&gt;
&lt;td&gt;First-class static and SPA hosting per cloudlet&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;AI and RAG&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;AI Assistant, AI Translations on higher tiers&lt;/td&gt;
&lt;td&gt;ML types, crawling, vectorisation, deployable chatbots&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Agent story&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;MCP server over the API&lt;/td&gt;
&lt;td&gt;Native MCP with OAuth; agents &lt;a href="https://hyperlambda.dev/blog/the-only-llm-on-earth-that-grows-its-own-tools-securely-on-demand-in-production" rel="noopener noreferrer"&gt;generate new tools for themselves at runtime&lt;/a&gt; inside RBAC&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Non-developers&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Genuinely usable by editors and ops people&lt;/td&gt;
&lt;td&gt;A developer tool, and honest about it&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Community&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Large, funded, SOC 2, partner programme&lt;/td&gt;
&lt;td&gt;Small&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;h2&gt;
  
  
  Where Directus wins, stated plainly
&lt;/h2&gt;

&lt;p&gt;Per the rules of this series: no rebuttals in this section. They live below.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Permissions granularity.&lt;/strong&gt; Field-level and item-level rules, expressed as filter conditions, evaluated per request. Magic gates by role at the endpoint. If your requirement is "this role sees every column except salary, and only rows in their own region", Directus expresses that as configuration and Magic expects you to write it. That is the widest genuine capability gap in the table.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Instant schema reflection.&lt;/strong&gt; Add a column, and Directus's API has it. No regeneration step, no stale endpoints, no forgetting to re-run anything. This is the direct upside of the runtime model, and on a schema that changes daily it is a real ergonomic win.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Content management.&lt;/strong&gt; Revisions, drafts, translations, an activity log people actually audit. Directus descends from headless CMS and it shows in a hundred small places Magic has never attempted.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Non-developer usability.&lt;/strong&gt; You can hand Directus Studio to a marketing team. You cannot hand Hyper IDE to a marketing team, and I would not suggest trying.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Database engines.&lt;/strong&gt; Oracle, MariaDB and CockroachDB are supported there and not here.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Ecosystem and assurance.&lt;/strong&gt; A funded company, a partner programme, SOC 2 Type II, an extension marketplace, a large forum, and people you can hire who already know it. Every one of those is a cost I carry on my side of this table.&lt;/p&gt;

&lt;h2&gt;
  
  
  Where the bets diverge
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;The runtime model versus the generated one.&lt;/strong&gt; Directus's API is a computation; Magic's is a file. That means Directus wins on schema churn and loses on inspection. There is no artefact to review, diff, or hand to a code reviewer — your effective API and permission surface live as rows in a config database, and the only way to know what they do is to ask the running system. Magic's endpoints are text on disk. You can read them, put them under git, and — the part that matters most here — hand them to an AI agent that can read them too.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Which is why the agent stories are not comparable.&lt;/strong&gt; Both have MCP. But an agent pointed at Directus can call the API; an agent pointed at Magic can read what the API &lt;em&gt;is&lt;/em&gt;, and then write more of it. Magic's generator emits Hyperlambda that executes as an AST where every node must bind to a whitelisted slot, so generated code &lt;a href="https://hyperlambda.dev/blog/why-secure-ai-code-execution-requires-runtime-whitelisting-not-prompt-filtering" rel="noopener noreferrer"&gt;cannot exceed its permissions no matter what the prompt said&lt;/a&gt;. That is the difference between an agent that queries your backend and an agent that builds it. There is &lt;a href="https://hyperlambda.dev/blog/break-my-ai-sandbox-and-make-100-psst-nobodys-done-it-yet" rel="noopener noreferrer"&gt;a standing $100 bounty&lt;/a&gt; on proving that boundary wrong.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;The extension model, again.&lt;/strong&gt; This series keeps landing here because it keeps being the fork in the road. Directus extensions are TypeScript with a build step; Flows give you sandboxed JS for the smaller cases. Magic's custom logic is a Hyperlambda file that is live the moment it is saved — no compiler, no restart, no deploy — and can be written from a sentence.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Pricing shape, which is a licensing argument wearing a costume.&lt;/strong&gt; Directus meters the two things that grow when your project succeeds: &lt;strong&gt;people&lt;/strong&gt; and &lt;strong&gt;tables&lt;/strong&gt;. Core stops at 3 seats and 25 collections. Team is $499/mo for 10 seats and 50 collections, with extra seats at $50/mo and extra collections at $100 per 25. Managed hosting is another $99. Magic charges per cloudlet — $100 or $300 — and counts neither users nor tables, ever.&lt;/p&gt;

&lt;p&gt;Work an example. A team of six developers wrapping a 70-table legacy database, hosted: on Directus that is Team, plus one 25-collection pack, plus cloud — call it &lt;strong&gt;$698/mo&lt;/strong&gt; before anyone else logs in. On Magic it is &lt;strong&gt;$100&lt;/strong&gt;, and the seventh developer changes nothing.&lt;/p&gt;

&lt;p&gt;Two honest caveats on that comparison, because it flatters me. If you are under $5M revenue &lt;em&gt;and&lt;/em&gt; under 50 employees, the Open Innovation Grant makes Directus free and fully permissive, and this entire paragraph is moot for you — take the grant. And Directus is grandfathering existing customers, so anyone already on an older plan is not living in the table above.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;The licence, which is the row I would read twice.&lt;/strong&gt; Directus is &lt;em&gt;source-available&lt;/em&gt;, not open source: the Monospace Sustainable Core License forbids Competing Use, forbids circumventing the licence-key functionality, and grants GPL-3.0 only on the fourth anniversary of each release. That is a defensible way to run a company, and I say that without snark — it is a real answer to a real sustainability problem. But it is not the same deal as MIT, and the difference shows up on the day your revenue crosses a threshold, or your lawyer asks what "Competing Use" means for the product you are building on top of it. Magic is MIT with nothing held back, no key, no threshold, no clock.&lt;/p&gt;

&lt;h2&gt;
  
  
  The decision rule
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Choose Directus if:&lt;/strong&gt; non-developers will use the admin UI daily; you need field- and row-level permissions as configuration rather than code; your content needs revisions, drafts or translations; your schema changes constantly; you are on Oracle or CockroachDB; or you qualify for the Open Innovation Grant, in which case a mature, funded, SOC 2 platform costs you nothing and that is very hard to argue with.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Choose Magic if:&lt;/strong&gt; you are above the grant's thresholds and do not want per-seat and per-table metering; you want the API as reviewable source rather than runtime configuration; you need the platform to host the frontend as well as the data; or — the structural one — you expect AI agents to be building the backend rather than querying it.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;The test that decides it in one question:&lt;/strong&gt; does your backend need to be &lt;em&gt;read&lt;/em&gt; by anything other than the server that runs it? If yes — by a reviewer, by git, by an agent — you want files. If no, a runtime model is less work.&lt;/p&gt;

&lt;h2&gt;
  
  
  The fine print
&lt;/h2&gt;

&lt;p&gt;Every number above about Directus was verified on their own pricing and licence pages the day this was published: the MSCL-1.0-GPL terms, the $0 / $499 / custom tiers, the 3-seat and 25-collection Core caps, $50 per extra seat, $100 per 25-collection pack, the $99 cloud add-on, and the under-$5M-and-under-50-employees grant. Pricing pages move. If you are reading this months later, re-verify before quoting me — and I would rather you checked than trusted me.&lt;/p&gt;

&lt;p&gt;The database engine list for Directus is from documentation rather than from my own testing, and Magic's own comparison rows are, obviously, written by the person who wrote Magic. Read the table with that in mind.&lt;/p&gt;

&lt;p&gt;Magic is MIT-licensed and open source — the repository is at &lt;a href="https://github.com/polterguy/magic" rel="noopener noreferrer"&gt;github.com/polterguy/magic&lt;/a&gt;. Testing any of this yourself takes &lt;a href="https://hyperlambda.dev/blog/magic-cloud-digitalocean-one-copy-paste" rel="noopener noreferrer"&gt;one copy-paste on a $6 DigitalOcean droplet&lt;/a&gt;, or &lt;a href="https://hyperlambda.dev/pricing" rel="noopener noreferrer"&gt;a managed cloudlet&lt;/a&gt; if you would rather not.&lt;/p&gt;

&lt;h2&gt;
  
  
  FAQ
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Is Magic Cloud a Directus alternative?
&lt;/h3&gt;

&lt;p&gt;For the developer case, yes — both wrap an existing database in a secured API without migrating it, both ship an admin UI, both self-host, both offer managed hosting. For the editorial case, no: Directus is a headless CMS with revisions, drafts and translations, and Magic is not trying to be one.&lt;/p&gt;

&lt;h3&gt;
  
  
  Is Directus open source?
&lt;/h3&gt;

&lt;p&gt;Not in the OSI sense any more. It is source-available under the Monospace Sustainable Core License, which prohibits Competing Use and licence-key circumvention, and converts each release to GPL-3.0 after four years. Magic is MIT.&lt;/p&gt;

&lt;h3&gt;
  
  
  Is Directus free?
&lt;/h3&gt;

&lt;p&gt;Free at the Core tier within hard caps — 3 seats, 25 collections, 5 flows, no SSO — and genuinely free and fully permissive under the Open Innovation Grant if your organisation is under $5M in revenue and under 50 employees. Above those lines it is $499/mo and up, with per-seat and per-collection metering.&lt;/p&gt;

&lt;h3&gt;
  
  
  Which handles a large legacy schema better?
&lt;/h3&gt;

&lt;p&gt;Directus reflects the whole schema instantly with nothing to generate, which is the better ergonomic. But collections are capped by plan, and a 200-table system lands you in Enterprise pricing. Magic makes you run the generator and gives you files afterwards, with no table count anywhere in the pricing.&lt;/p&gt;

&lt;h3&gt;
  
  
  Can AI agents use both?
&lt;/h3&gt;

&lt;p&gt;Both expose MCP. The difference is what the agent can do once connected: with Directus it calls your API; with Magic it can read the generated code and write more of it, inside a runtime that constrains what generated code is even able to express.&lt;/p&gt;

&lt;h2&gt;
  
  
  Related reading
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/magic-vs-pocketbase-an-honest-feature-matrix" rel="noopener noreferrer"&gt;Magic vs PocketBase: An Honest Feature Matrix&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/magic-vs-n8n-an-honest-feature-matrix" rel="noopener noreferrer"&gt;Magic vs n8n: An Honest Feature Matrix&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/magic-cloud-the-self-hosted-supabase-alternative-built-for-ai-agents" rel="noopener noreferrer"&gt;Magic Cloud: The Self-Hosted Supabase Alternative Built for AI Agents&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/why-secure-ai-code-execution-requires-runtime-whitelisting-not-prompt-filtering" rel="noopener noreferrer"&gt;Why Secure AI Code Execution Requires Runtime Whitelisting, Not Prompt Filtering&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>opensource</category>
      <category>webdev</category>
      <category>database</category>
      <category>ai</category>
    </item>
    <item>
      <title>From Prompt to MCP Tool in 5 Seconds</title>
      <dc:creator>Thomas Hansen</dc:creator>
      <pubDate>Tue, 18 Aug 2026 10:39:46 +0000</pubDate>
      <link>https://dev.to/polterguy/from-prompt-to-mcp-tool-in-5-seconds-3fad</link>
      <guid>https://dev.to/polterguy/from-prompt-to-mcp-tool-in-5-seconds-3fad</guid>
      <description>&lt;p&gt;Building an MCP tool, as the industry currently understands the job: install an SDK, write a server, hand-author a tool schema, wire the handler, host the process, deploy it, restart it, reconnect the client.&lt;/p&gt;

&lt;p&gt;Here is the same job on &lt;a href="https://github.com/polterguy/magic" rel="noopener noreferrer"&gt;Magic&lt;/a&gt;, the MIT-licensed backend platform I work on.&lt;/p&gt;

&lt;p&gt;You write a sentence.&lt;/p&gt;

&lt;p&gt;That is the whole procedure, and this article is about why — because the interesting part is not that it is fast. It is that there is no second step to be fast &lt;em&gt;at&lt;/em&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  The measured run
&lt;/h2&gt;

&lt;p&gt;I did this on the cloudlet serving my website while writing the article. The generator reports its own execution time, so these numbers are server-measured, not my stopwatch.&lt;/p&gt;

&lt;p&gt;I wanted a tool that did not exist: a daily trend over the anonymous submissions to our carbon calculator — how many people submitted each day, and how heavy their average footprint was.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Attempt&lt;/th&gt;
&lt;th&gt;Seconds (measured)&lt;/th&gt;
&lt;th&gt;Outcome&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;First generation&lt;/td&gt;
&lt;td&gt;2.88&lt;/td&gt;
&lt;td&gt;Saved, then threw a 500 on invocation&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Regenerated&lt;/td&gt;
&lt;td&gt;1.83&lt;/td&gt;
&lt;td&gt;Live and correct&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Regenerated for a better description&lt;/td&gt;
&lt;td&gt;3.03&lt;/td&gt;
&lt;td&gt;Live, correct, properly documented&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Three generations, 7.74 seconds of compute, one live tool. It is public and read-only, so you can call it yourself right now:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="s2"&gt;"https://hyperlambda.dev/magic/modules/mcp-demo/footprint-trend?days=365"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;[{&lt;/span&gt;&lt;span class="nl"&gt;"day"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"2026-08-09"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="nl"&gt;"submissions"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="nl"&gt;"average_total_kg"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="mf"&gt;16188.0&lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt;
 &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"day"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"2026-08-03"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="nl"&gt;"submissions"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="nl"&gt;"average_total_kg"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="mf"&gt;8772.0&lt;/span&gt;&lt;span class="p"&gt;}]&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I will come back to that failed first attempt, because the honest part of this story is more useful than the fast part.&lt;/p&gt;

&lt;h2&gt;
  
  
  There is no second step
&lt;/h2&gt;

&lt;p&gt;The file the generator saved is this. The comment is abbreviated here; everything else is verbatim.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="o"&gt;//&lt;/span&gt; &lt;span class="k"&gt;Returns&lt;/span&gt; &lt;span class="n"&gt;the&lt;/span&gt; &lt;span class="n"&gt;daily&lt;/span&gt; &lt;span class="n"&gt;trend&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="n"&gt;anonymous&lt;/span&gt; &lt;span class="n"&gt;carbon&lt;/span&gt; &lt;span class="n"&gt;footprint&lt;/span&gt; &lt;span class="n"&gt;submissions&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;one&lt;/span&gt; &lt;span class="n"&gt;entry&lt;/span&gt; &lt;span class="n"&gt;per&lt;/span&gt; &lt;span class="k"&gt;day&lt;/span&gt; &lt;span class="p"&gt;[...]&lt;/span&gt;
&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;arguments&lt;/span&gt;
   &lt;span class="n"&gt;days&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="nb"&gt;int&lt;/span&gt;
&lt;span class="n"&gt;validators&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;default&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="o"&gt;@&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;arguments&lt;/span&gt;
   &lt;span class="n"&gt;days&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="nb"&gt;int&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="mi"&gt;7&lt;/span&gt;
&lt;span class="k"&gt;data&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;connect&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;billionair&lt;/span&gt;
   &lt;span class="k"&gt;data&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;select&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="nv"&gt;"select date(created) as day, count(*) as submissions, avg(total_kg) as average_total_kg from footprints where created &amp;gt;= date('now', '-' || @days || ' day') and total_kg &amp;gt; 0 group by day order by day desc"&lt;/span&gt;
      &lt;span class="n"&gt;days&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="o"&gt;@&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;arguments&lt;/span&gt;&lt;span class="cm"&gt;/*/days
   return-nodes:x:@data.select/*
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Saving that file is the last thing that happens. There is no build, no restart, no registration, no export.&lt;/p&gt;

&lt;p&gt;The reason is that &lt;strong&gt;Magic's MCP server has no tool registry.&lt;/strong&gt; It does not keep a list of tools that somebody has to remember to update. When a client asks what tools exist, the server enumerates the endpoints that exist, right then, and describes them. The catalogue is not a copy of reality that can drift out of date — it is a query against reality.&lt;/p&gt;

&lt;p&gt;Which means a tool cannot be &lt;em&gt;added&lt;/em&gt; to the tool list. It can only be &lt;em&gt;created&lt;/em&gt;, after which the list already contains it.&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%2Ffmyseke02ngvazlii36m.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%2Ffmyseke02ngvazlii36m.png" alt="A Magic cloudlet connected as an MCP connector, listing the tools it publishes to the agent" width="799" height="602"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The same is true in the other direction, and this is the part I find quietly elegant: calling a tool runs the endpoint. Not a copy of the endpoint, not a proxy in front of it — the endpoint, through the same invocation path an HTTP request takes, carrying the caller's own identity. So the role check that guards it from a browser is the role check that guards it from an agent, because it is the same check. There was never a second one to keep in sync.&lt;/p&gt;

&lt;h2&gt;
  
  
  Your prompt is the tool description
&lt;/h2&gt;

&lt;p&gt;Now the mechanic that makes one sentence sufficient.&lt;/p&gt;

&lt;p&gt;A language model deciding whether to call a tool reads two things: the tool's description, and a description of each argument. In every other stack, those are a third artifact — written by hand, next to the code and the schema, and stale within a month.&lt;/p&gt;

&lt;p&gt;Magic publishes an endpoint's file comment as the tool description, and the comment above each argument as &lt;em&gt;that argument's&lt;/em&gt; description. And the generator writes the file comment from your prompt.&lt;/p&gt;

&lt;p&gt;So the sentence you typed is not merely instructions to a code generator that get thrown away afterwards. It survives, in the file, as the documentation your agent reads. Here is what came back out the other end, from this cloudlet's live specification:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="nl"&gt;"/magic/modules/mcp-demo/footprint-trend"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"get"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"operationId"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"get_mcp-demo_footprint-trend"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Returns the daily trend of anonymous carbon footprint submissions, one entry per day, so a caller can see how many people submitted and how heavy their average footprint was [...]"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"parameters"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[{&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"days"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"in"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"query"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"schema"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"integer"&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;}]&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I never wrote a schema. I wrote &lt;code&gt;days&lt;/code&gt; in a sentence, said it was an integer, and the type came along for the ride.&lt;/p&gt;

&lt;p&gt;The mapping from Hyperlambda's types to JSON Schema is boring on purpose:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Hyperlambda&lt;/th&gt;
&lt;th&gt;JSON Schema&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;
&lt;code&gt;short&lt;/code&gt;, &lt;code&gt;int&lt;/code&gt;, &lt;code&gt;long&lt;/code&gt;
&lt;/td&gt;
&lt;td&gt;&lt;code&gt;integer&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;
&lt;code&gt;decimal&lt;/code&gt;, &lt;code&gt;double&lt;/code&gt;, &lt;code&gt;float&lt;/code&gt;
&lt;/td&gt;
&lt;td&gt;&lt;code&gt;number&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;bool&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;boolean&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;date&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;string&lt;/code&gt;, format &lt;code&gt;date-time&lt;/code&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;guid&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;string&lt;/code&gt;, format &lt;code&gt;uuid&lt;/code&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;everything else&lt;/td&gt;
&lt;td&gt;&lt;code&gt;string&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;h2&gt;
  
  
  So write the prompt like a docstring
&lt;/h2&gt;

&lt;p&gt;Here is a mistake I made in front of you, and it is the most useful paragraph in this article.&lt;/p&gt;

&lt;p&gt;My second attempt worked perfectly, and its description read:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;em&gt;"Use a single SQL statement that does all date arithmetic inside the database itself: group rows by the date part of the 'created' column [...] Do not perform any date arithmetic outside of SQL."&lt;/em&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Every word of that is true, and every word of it is useless to the model that has to decide whether to call the tool. I had written a work order for a compiler and published it as documentation. An agent reading that learns nothing about &lt;em&gt;when this tool is the right answer&lt;/em&gt; — it learns how I wanted the SQL written.&lt;/p&gt;

&lt;p&gt;So I regenerated a third time, with the same requirements in a different order: what the tool returns first, who would want it, what the argument controls, and the implementation constraint last. That is the 3.03-second run in the table, and it is the version now serving.&lt;/p&gt;

&lt;p&gt;The rule that falls out of this is short. &lt;strong&gt;The prompt becomes the docstring, so write it as one.&lt;/strong&gt; Lead with what the tool does and when to use it. Name every argument and its type. Put implementation notes at the end, where they belong — after the sentence a model actually needs.&lt;/p&gt;

&lt;p&gt;Nobody writes tool definitions on this platform. But somebody still has to write the first sentence well, and that somebody is you.&lt;/p&gt;

&lt;h2&gt;
  
  
  The honest edges
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;The first generation was wrong.&lt;/strong&gt; It compiled, it verified, it saved, and it threw a 500 the moment I called it — it had tried to subtract dates in a way the runtime found ambiguous. The verifier proves that every instruction in generated code exists and is real; it does not prove the code does what you meant. That still requires running it, which is why I ran it.&lt;/p&gt;

&lt;p&gt;Note the fix, though: I did not open the file. I changed one clause in the prompt and regenerated, 1.83 seconds. When the build path is that short, it is also the repair path — hand-editing generated code is not the workflow here, and does not need to be.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Your client may not notice immediately.&lt;/strong&gt; The server's catalogue is current the instant the file lands, but most MCP clients fetch the tool list once, when they connect, and cache it. The tool is live, callable, and in the catalogue — your agent just will not see it until you reconnect the connector. This trips people up regularly, and it is a client behaviour, not a server one.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Two smaller ones.&lt;/strong&gt; Some clients enforce a 64-character limit on tool names; Magic does not truncate, so a very deeply nested module path could produce a name a strict client dislikes. And the transport is plain request/response JSON — a spec-compliant subset, with no SSE stream and no server-initiated messages.&lt;/p&gt;

&lt;h2&gt;
  
  
  One cloudlet, several servers
&lt;/h2&gt;

&lt;p&gt;A last detail worth knowing. The MCP endpoint takes an optional path, which narrows the catalogue to one module subtree — point a client at &lt;code&gt;?path=/modules/crm/&lt;/code&gt; and it sees the CRM tools and nothing else. The narrowing is confined inside &lt;code&gt;modules/&lt;/code&gt; and normalised at both ends, so &lt;code&gt;/modules/crm&lt;/code&gt; cannot leak into a sibling like &lt;code&gt;/modules/crm-archive&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Combine that with the catalogue being assembled per caller — Magic reads the roles on the authenticated ticket and lists only endpoints that caller may execute — and one backend serves as many different, differently-scoped MCP servers as you have audiences for. I made that argument properly in &lt;a href="https://hyperlambda.dev/blog/convert-your-openapi-specification-to-a-secured-mcp-tool-in-seconds" rel="noopener noreferrer"&gt;the OpenAPI article&lt;/a&gt;, so I will not repeat it here.&lt;/p&gt;

&lt;h2&gt;
  
  
  Try it
&lt;/h2&gt;

&lt;p&gt;One command:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-fsSL&lt;/span&gt; https://hyperlambda.dev/docker-compose.yaml | docker compose &lt;span class="nt"&gt;-f&lt;/span&gt; - up
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Open &lt;strong&gt;&lt;code&gt;localhost:5555&lt;/code&gt;&lt;/strong&gt;, point it at &lt;strong&gt;&lt;code&gt;localhost:4444&lt;/code&gt;&lt;/strong&gt;, log in with &lt;code&gt;root&lt;/code&gt; / &lt;code&gt;root&lt;/code&gt;, and describe a tool you wish you had. Then connect an agent and look for it.&lt;/p&gt;

&lt;p&gt;Magic is MIT-licensed and open source. The repository is at &lt;a href="https://github.com/polterguy/magic" rel="noopener noreferrer"&gt;github.com/polterguy/magic&lt;/a&gt;, with documentation at &lt;a href="https://docs.ainiro.io" rel="noopener noreferrer"&gt;docs.ainiro.io&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;The five seconds in the title is the round number. The measured ones were 2.88, 1.83 and 3.03 — and honestly, the seconds are the least interesting thing about it. What matters is that when they elapsed, there was nothing left to do.&lt;/p&gt;

&lt;h2&gt;
  
  
  Related reading
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/convert-your-openapi-specification-to-a-secured-mcp-tool-in-seconds" rel="noopener noreferrer"&gt;Convert your OpenAPI Specification to a Secured MCP Tool in Seconds&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/the-only-llm-on-earth-that-grows-its-own-tools-securely-on-demand-in-production" rel="noopener noreferrer"&gt;The Only LLM on Earth That Grows Its Own Tools — Securely, On Demand, In Production&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/zero-hallucination-code-generation-a-vocabulary-your-ai-cannot-escape" rel="noopener noreferrer"&gt;Zero-Hallucination Code Generation: A Vocabulary Your AI Cannot Escape&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/a-complete-crm-in-one-conversation-60-seconds-of-backend-six-cents-of-tokens" rel="noopener noreferrer"&gt;A Complete CRM in One Conversation: 60 Seconds of Backend, Six Cents of Tokens&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/magic-now-supports-mcp-server-integration-for-ai-agents" rel="noopener noreferrer"&gt;Magic Now Supports MCP Server Integration for AI Agents&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>mcp</category>
      <category>ai</category>
      <category>opensource</category>
      <category>api</category>
    </item>
    <item>
      <title>From Module to GitHub Repository in One Click</title>
      <dc:creator>Thomas Hansen</dc:creator>
      <pubDate>Sat, 08 Aug 2026 06:06:44 +0000</pubDate>
      <link>https://dev.to/polterguy/from-module-to-github-repository-in-one-click-1bpf</link>
      <guid>https://dev.to/polterguy/from-module-to-github-repository-in-one-click-1bpf</guid>
      <description>&lt;p&gt;Yesterday one of my modules became a GitHub repository. The whole ceremony: hover the folder, click the branch icon, write a commit message, click &lt;em&gt;Publish&lt;/em&gt;.&lt;/p&gt;

&lt;p&gt;Behind that one click, Magic created a private repository on GitHub, added it as the module's &lt;code&gt;origin&lt;/code&gt; remote, pushed the commit, and configured upstream tracking. Four git operations, zero terminal.&lt;/p&gt;

&lt;p&gt;You know the manual version of this dance. Create the repository in GitHub's UI or with &lt;code&gt;gh repo create&lt;/code&gt;, copy the URL, &lt;code&gt;git remote add origin&lt;/code&gt;, &lt;code&gt;git push -u origin master&lt;/code&gt;, and somewhere in the middle a context switch that costs more than all the commands combined. That dance is now a button — because Hyper IDE has Git built in, and this article is the tour.&lt;/p&gt;

&lt;h2&gt;
  
  
  Where Git lives
&lt;/h2&gt;

&lt;p&gt;Every top level folder inside &lt;code&gt;/modules/&lt;/code&gt; and &lt;code&gt;/etc/&lt;/code&gt; is treated as a repository root. Hover one in Hyper IDE's file tree, and a branch icon appears among its actions — that is the whole discovery story. One repo per module, deliberately: the module is already the unit of install, the unit of deployment, and the unit of meaning in Magic. Now it is the unit of versioning too.&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%2F3hmqmvt7shick3gvem6l.jpeg" 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%2F3hmqmvt7shick3gvem6l.jpeg" alt="A module folder's action buttons in Hyper IDE's file tree, with the Git branch icon among them" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  The panel
&lt;/h2&gt;

&lt;p&gt;Click the icon and you get the state of that repository: which branch you are on, whether you are ahead of or behind your remote, and every modified and untracked file. Commit everything with a message, push, pull, fetch, switch branches, create new ones.&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%2F2136bl8dyufk096nom4a.jpeg" 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%2F2136bl8dyufk096nom4a.jpeg" alt="Hyper IDE's Git panel showing branch, tracking status, and commit actions for a module" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The detail I care most about is what you &lt;em&gt;cannot&lt;/em&gt; click. Push is greyed out until you actually have commits your remote does not. Clone demands an empty folder, because git demands an empty folder. A freshly initialized repository disables everything that requires a commit to exist. The panel teaches you git's rules by construction, instead of relaying git's error messages after the fact.&lt;/p&gt;

&lt;h2&gt;
  
  
  One token, no keychain
&lt;/h2&gt;

&lt;p&gt;Setup is a single dialog: open &lt;em&gt;Configuration&lt;/em&gt;, click the hamburger menu, choose &lt;em&gt;Git…&lt;/em&gt;, and give it your GitHub username and a fine-grained personal access token with &lt;em&gt;Contents&lt;/em&gt; read and write access.&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%2Fziis4ux320rjg7d66hem.jpeg" 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%2Fziis4ux320rjg7d66hem.jpeg" alt="The Git settings dialog on the Configuration screen, with GitHub username, token and host" width="800" height="678"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The architecture behind that dialog matters more than the dialog. Credentials are injected per git invocation, over HTTPS, as a header — &lt;em&gt;nothing&lt;/em&gt; is ever written to the server's global git configuration, no credential helper, no SSH keys sitting on disk. And commits are authored as &lt;em&gt;you&lt;/em&gt;: the author name and email are resolved from the signed-in user's profile, so your history on GitHub shows your name, not some shared server identity. The token authenticates transport; people author commits.&lt;/p&gt;

&lt;h2&gt;
  
  
  The one click
&lt;/h2&gt;

&lt;p&gt;Back to the headline. Take any module — say one you have been building all week — and open its Git panel. Not a repository yet? Click &lt;em&gt;Initialize repository&lt;/em&gt;. Write a commit message, click &lt;em&gt;Commit&lt;/em&gt;. Then click &lt;em&gt;Publish to GitHub…&lt;/em&gt;, and give the repository a name — it defaults to the module's folder name, which is almost always the right answer.&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%2F9chc3l75zew7ducupm3h.jpeg" 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%2F9chc3l75zew7ducupm3h.jpeg" alt="Publishing a module to GitHub from Hyper IDE, prompting for the new repository's name" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;That click creates the repository on GitHub — &lt;em&gt;private&lt;/em&gt; by default, flip it to public over there if that is what you want — wires it up as &lt;code&gt;origin&lt;/code&gt;, pushes your commit, and sets upstream tracking. Your module has a home, a history, and a URL.&lt;/p&gt;

&lt;p&gt;Notice, &lt;em&gt;creating&lt;/em&gt; repositories needs one more permission than reading and writing them: the account level repository creation permission on your access token, in addition to &lt;em&gt;Contents&lt;/em&gt;. If your token lacks it, the panel will tell you so in plain text, because errors here are never swallowed.&lt;/p&gt;

&lt;h2&gt;
  
  
  The door swings both ways
&lt;/h2&gt;

&lt;p&gt;Publishing is half the story. The other half: create a new &lt;em&gt;empty&lt;/em&gt; folder inside &lt;code&gt;/modules/&lt;/code&gt;, open its Git panel, and you get the mirror options — initialize, or clone.&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%2Fg01pt1hp2u9w0iv2416k.jpeg" 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%2Fg01pt1hp2u9w0iv2416k.jpeg" alt="Hyper IDE's Git panel on a folder that is not yet a repository, offering clone and initialize actions" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Click &lt;em&gt;Clone into folder&lt;/em&gt;, paste the repository's HTTPS URL, and the module lands on your cloudlet with its entire history attached. It checks out whatever the remote's default branch happens to be called — the panel has no opinions in the main-versus-master wars, and after debugging that assumption out of an earlier iteration, neither do I.&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%2Fx7m9xigrkirysvj7gbsv.jpeg" 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%2Fx7m9xigrkirysvj7gbsv.jpeg" alt="Cloning a GitHub repository into a module folder in Hyper IDE, prompting for the HTTPS URL" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Modules travel now
&lt;/h2&gt;

&lt;p&gt;Here is why this is more than a convenience feature.&lt;/p&gt;

&lt;p&gt;Magic has always let you move modules between cloudlets as zip files — download here, install there. A zip is a snapshot. Git is a &lt;em&gt;history&lt;/em&gt;: branches, rollback, blame, and a remote that two cloudlets can both talk to. Develop a module on your dev cloudlet, publish it, clone it into production, and from then on promotion is a &lt;code&gt;pull&lt;/code&gt;. The zip workflow did not go anywhere — but the module you care about, the one that grows for months, wants version control, and now the platform it lives on speaks it natively.&lt;/p&gt;

&lt;p&gt;And because everything in Magic is reachable by agents, the same is true over MCP — the git workflow tools have been callable by AI agents for a while. What is new is that &lt;em&gt;humans&lt;/em&gt; got the good UI too.&lt;/p&gt;

&lt;h2&gt;
  
  
  The fine print
&lt;/h2&gt;

&lt;p&gt;Big claims, precise edges — as always.&lt;/p&gt;

&lt;p&gt;This is not a full git client, and it does not want to be. Commit stages &lt;em&gt;everything&lt;/em&gt; the change list shows — there is no per-file staging in v1. There is no diff viewer and no merge-conflict UI; if a pull lands you in conflict territory, clone the repository locally and resolve it with real tooling, then push. The panel covers the module lifecycle — initialize, commit, branch, publish, clone, pull, push — not interactive rebases.&lt;/p&gt;

&lt;p&gt;One deliberate sharp edge worth knowing: paths must be repository &lt;em&gt;roots&lt;/em&gt;. Git's normal upward discovery is disabled on the server, so a folder that is not itself a repo throws instead of silently operating on some enclosing repository it happened to find above itself. That rule exists because during development, the panel on a repo-less folder cheerfully offered to commit the entire Magic source tree it found two levels up. Loud beats silent, every single time.&lt;/p&gt;

&lt;p&gt;The whole feature was built in a day, driving Claude against the running dashboard — including three separate ambushes by a hardcoded &lt;code&gt;main&lt;/code&gt; branch assumption and the discovery bug above. That story, bug ledger and all, is its own article.&lt;/p&gt;

&lt;h2&gt;
  
  
  The keys
&lt;/h2&gt;

&lt;p&gt;Magic is MIT-licensed and open source — the repository is at &lt;a href="https://github.com/polterguy/magic" rel="noopener noreferrer"&gt;github.com/polterguy/magic&lt;/a&gt;, with documentation at &lt;a href="https://docs.ainiro.io" rel="noopener noreferrer"&gt;docs.ainiro.io&lt;/a&gt;. If you want a cloudlet of your own to publish modules from, it is &lt;a href="https://hyperlambda.dev/blog/magic-cloud-digitalocean-one-copy-paste" rel="noopener noreferrer"&gt;one copy-paste on a $6 DigitalOcean droplet&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Related reading
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/46000-lines-of-angular-gone-in-a-weekend" rel="noopener noreferrer"&gt;46,000 Lines of Angular, Gone in a Weekend&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/vibe-coding-without-a-landlord" rel="noopener noreferrer"&gt;Vibe Coding Without a Landlord&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/magic-cloud-digitalocean-one-copy-paste" rel="noopener noreferrer"&gt;Magic Cloud + DigitalOcean: One Copy-Paste&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hyperlambda.dev/blog/magic-now-supports-mcp-server-integration-for-ai-agents" rel="noopener noreferrer"&gt;Magic Now Supports MCP Server Integration for AI Agents&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;em&gt;Originally published at &lt;a href="https://hyperlambda.dev/blog/from-module-to-github-repository-in-one-click" rel="noopener noreferrer"&gt;hyperlambda.dev&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>git</category>
      <category>opensource</category>
      <category>webdev</category>
      <category>ai</category>
    </item>
    <item>
      <title>Why Claude Is 10x Cheaper When It Builds on Magic Cloud</title>
      <dc:creator>Thomas Hansen</dc:creator>
      <pubDate>Thu, 06 Aug 2026 07:05:32 +0000</pubDate>
      <link>https://dev.to/polterguy/why-claude-is-10x-cheaper-when-it-builds-on-magic-cloud-4n5</link>
      <guid>https://dev.to/polterguy/why-claude-is-10x-cheaper-when-it-builds-on-magic-cloud-4n5</guid>
      <description>&lt;p&gt;Everyone optimizes the wrong variable.&lt;/p&gt;

&lt;p&gt;Cheaper models.&lt;br&gt;
Shorter prompts.&lt;br&gt;
Compressed context.&lt;/p&gt;

&lt;p&gt;That all helps a little.&lt;/p&gt;

&lt;p&gt;But look at Anthropic's rate card instead, and one asymmetry jumps out: output tokens cost 5x input tokens on every current model. Claude Fable 5 is $10 per million tokens in, and &lt;strong&gt;$50 per million tokens out&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;Which means the most expensive thing your AI agent does is write code as output.&lt;/p&gt;

&lt;p&gt;Magic is architected so it doesn't.&lt;/p&gt;

&lt;p&gt;And rather than argue this in the abstract, we let Claude build a complete full-stack app on our &lt;a href="https://hyperlambda.dev" rel="noopener noreferrer"&gt;hyperlambda.dev&lt;/a&gt; cloudlet — while measuring everything.&lt;/p&gt;

&lt;h2&gt;
  
  
  The rate card, straight from Anthropic
&lt;/h2&gt;

&lt;p&gt;These are Anthropic's official API prices, per million tokens, fetched from their pricing documentation on August 6, 2026:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Model&lt;/th&gt;
&lt;th&gt;Input&lt;/th&gt;
&lt;th&gt;Output&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Claude Fable 5&lt;/td&gt;
&lt;td&gt;$10&lt;/td&gt;
&lt;td&gt;$50&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Claude Opus 5 / 4.8&lt;/td&gt;
&lt;td&gt;$5&lt;/td&gt;
&lt;td&gt;$25&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Claude Sonnet 5 (intro, through Aug 31)&lt;/td&gt;
&lt;td&gt;$2&lt;/td&gt;
&lt;td&gt;$10&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Claude Sonnet 4.6 / Sonnet 5 (from Sep 1)&lt;/td&gt;
&lt;td&gt;$3&lt;/td&gt;
&lt;td&gt;$15&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Claude Haiku 4.5&lt;/td&gt;
&lt;td&gt;$1&lt;/td&gt;
&lt;td&gt;$5&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Two things are worth staring at.&lt;/p&gt;

&lt;p&gt;First, the output multiple is universal. Every tier charges 5x more for what the model writes than for what it reads.&lt;/p&gt;

&lt;p&gt;Second, Anthropic's newer tokenizer — used by Claude 4.7 and later — produces roughly 30% more tokens for the same text. Round-tripping source code through a model's context literally got more expensive this year.&lt;/p&gt;

&lt;p&gt;Prompt caching and the Batch API can discount those rates. But a discount on waste is still waste. The interesting question is why the tokens are being spent at all.&lt;/p&gt;

&lt;h2&gt;
  
  
  Where a coding agent's tokens actually go
&lt;/h2&gt;

&lt;p&gt;A conventional coding agent building a backend runs a loop.&lt;/p&gt;

&lt;p&gt;Read files. That is input.&lt;br&gt;
Write code. That is output, at 5x.&lt;br&gt;
Read the error. Input again.&lt;br&gt;
Rewrite. Output again.&lt;br&gt;
Re-read to verify. Input again.&lt;/p&gt;

&lt;p&gt;Every debug iteration compounds, and the compounding happens at the most expensive rate on the card. The model is not reasoning in most of those moments. It is acting as a very costly transport layer for source code.&lt;/p&gt;

&lt;p&gt;I have written before about &lt;a href="https://hyperlambda.dev/blog/how-hyperlambda-can-cut-ai-agent-costs-by-75-to-90-percent" rel="noopener noreferrer"&gt;how Hyperlambda changes these economics&lt;/a&gt; and &lt;a href="https://hyperlambda.dev/blog/how-magic-cuts-backend-build-cost-by-80-percent-in-agentic-workflows" rel="noopener noreferrer"&gt;measured roughly 80 percent savings on a Fable-priced build&lt;/a&gt;. This article is about the mechanism underneath those numbers — and a fresh build with its own receipts.&lt;/p&gt;

&lt;h2&gt;
  
  
  What we built to prove it
&lt;/h2&gt;

&lt;p&gt;We asked Claude to build &lt;strong&gt;Token Ledger&lt;/strong&gt;: an LLM spend tracker.&lt;/p&gt;

&lt;p&gt;Yes, that is deliberately meta. Claude built a token-cost dashboard while its own token cost was being metered.&lt;/p&gt;

&lt;p&gt;The deliverable: a SQLite database with three linked tables — providers, models, and a usage log — seeded with Anthropic's actual rate card from the table above. Fifteen HTTP endpoints, every one of them role-secured. Two aggregation endpoints feeding charts. And a designed, dark, authenticated dashboard.&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%2Fnjtj6p6gm2rznc8d8hka.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%2Fnjtj6p6gm2rznc8d8hka.png" alt="Token Ledger dashboard — KPI cards, spend by model, spend by day, recent usage table" width="800" height="645"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Look at the dashboard's own numbers for a moment. The second KPI card reads "output share of spend: 37%" — on a realistic mixed workload, over a third of the bill is output tokens. And the spend-by-model chart shows Fable 5 dwarfing everything else, because at $50 per million output tokens, it does.&lt;/p&gt;

&lt;p&gt;The app is arguing the article's thesis from inside the screenshot.&lt;/p&gt;

&lt;h2&gt;
  
  
  The build ledger
&lt;/h2&gt;

&lt;p&gt;Wall-clock time was measured with timestamps, not estimated.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;What&lt;/th&gt;
&lt;th&gt;Number&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Live secured backend — database, schema, seed data, 15 endpoints&lt;/td&gt;
&lt;td&gt;222 seconds&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Complete working app, including the hand-written frontend&lt;/td&gt;
&lt;td&gt;431 seconds&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Backend lines of code generated&lt;/td&gt;
&lt;td&gt;669&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Backend lines of code hand-written&lt;/td&gt;
&lt;td&gt;0&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Claude output tokens spent on backend code&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;0&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;The last row is the entire article.&lt;/p&gt;

&lt;p&gt;The backend was produced by twelve calls to Magic's CRUD generator and three calls to its SQL endpoint generator. Each call is a compact declarative argument — a table name, a column list, a role restriction, an SQL statement. Around a hundred tokens each, roughly 1,500 tokens of arguments in total.&lt;/p&gt;

&lt;p&gt;Not one of the 669 generated lines passed through Claude's output stream at $50 per million tokens. The platform wrote them, server-side, using the same battle-tested generators the Magic dashboard uses.&lt;/p&gt;

&lt;p&gt;Honest scope on the numbers: the 222 seconds include reading the platform's guides and setting up the design tokens. Screenshots and end-to-end verification came after the 431-second mark and included two pauses waiting for human tool approval, so they are excluded from the build figures.&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%2Ffin4gjhfuelei5qhmvxy.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%2Ffin4gjhfuelei5qhmvxy.png" alt="Token Ledger login — role-secured entry to the dashboard" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;That login screen is not decoration. Every endpoint behind it is gated by Magic's built-in RBAC — no hand-rolled JWT handling anywhere, because there is no hand-written backend anywhere.&lt;/p&gt;

&lt;h2&gt;
  
  
  The five mechanisms
&lt;/h2&gt;

&lt;p&gt;Why does this architecture starve the token meter? Five reasons, each visible in the build above.&lt;/p&gt;

&lt;h3&gt;
  
  
  1. Declarative calls replace emitted code
&lt;/h3&gt;

&lt;p&gt;One CRUD-generator call is roughly a hundred output tokens of arguments. It produces a complete endpoint — paging, sorting, filtering, validation, auth — of sixty to a hundred and twenty lines. Streaming the equivalent as source code is thousands of output tokens, usually across multiple attempts. In this build, 1,500 tokens of arguments bought 669 lines of backend.&lt;/p&gt;

&lt;h3&gt;
  
  
  2. Code generation happens server-side
&lt;/h3&gt;

&lt;p&gt;When something bespoke is needed, Magic's Hyperlambda Generator takes a plain-English prompt and writes the file on the server. The code never enters Claude's output stream or its input stream. Claude pays for a sentence, not a source file. And here is the stronger version of that point: this particular build needed &lt;strong&gt;zero&lt;/strong&gt; generator calls. The declarative tools covered the entire backend.&lt;/p&gt;

&lt;h3&gt;
  
  
  3. Code never round-trips through context
&lt;/h3&gt;

&lt;p&gt;Magic's operating rules forbid the agent from reading generated Hyperlambda back. Verification goes through live HTTP invocation and the OpenAPI spec. A conventional coding agent re-reads its files constantly — every read is input tokens, every edit is output tokens. On Magic, that loop is not discouraged. It is structurally impossible.&lt;/p&gt;

&lt;h3&gt;
  
  
  4. No debug spirals
&lt;/h3&gt;

&lt;p&gt;The generators are deterministic. There is no generate, error, paste-the-stacktrace, regenerate cycle — the invisible multiplier on every agent bill. This build's complete bug ledger: one entry, a headless-browser viewport quirk while taking &lt;em&gt;screenshots&lt;/em&gt;. Zero bugs in 669 generated backend lines.&lt;/p&gt;

&lt;h3&gt;
  
  
  5. One-call grounding
&lt;/h3&gt;

&lt;p&gt;At session start, one call returns who the agent is, what backend it is on, and its full operating instructions. One more call returns the exact list of capabilities that exist on the instance. Compare that with an agent grepping directories and reading files to discover what a codebase can do — all of it billed as input, none of it producing anything.&lt;/p&gt;

&lt;h2&gt;
  
  
  The accounting: same app, two architectures
&lt;/h2&gt;

&lt;p&gt;Take the same deliverable — the Token Ledger backend, fifteen secured endpoints — and price both paths at Anthropic's current rates.&lt;/p&gt;

&lt;p&gt;The Magic column is this build. The coding-agent column is a calibrated estimate for the same result via a conventional file-editing agent — scaffold, routes, auth, validation, and the customary debug loops — consistent with the roughly 140,000-versus-25,000-token gap &lt;a href="https://hyperlambda.dev/blog/how-magic-cuts-backend-build-cost-by-80-percent-in-agentic-workflows" rel="noopener noreferrer"&gt;measured in the July benchmark&lt;/a&gt;, with the backend-code share broken out.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;&lt;/th&gt;
&lt;th&gt;Claude on Magic (measured shape)&lt;/th&gt;
&lt;th&gt;Claude with generic tooling (estimate)&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Output tokens spent on backend code&lt;/td&gt;
&lt;td&gt;0&lt;/td&gt;
&lt;td&gt;~30,000&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Total output tokens, backend slice&lt;/td&gt;
&lt;td&gt;~2,000&lt;/td&gt;
&lt;td&gt;~35,000&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Total input tokens, backend slice&lt;/td&gt;
&lt;td&gt;~30,000&lt;/td&gt;
&lt;td&gt;~180,000&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Cost at Fable 5 ($10 / $50)&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;≈ $0.40&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;≈ $3.55&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Cost at Opus 5 ($5 / $25)&lt;/td&gt;
&lt;td&gt;≈ $0.20&lt;/td&gt;
&lt;td&gt;≈ $1.78&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Cost at Sonnet 4.6 ($3 / $15)&lt;/td&gt;
&lt;td&gt;≈ $0.12&lt;/td&gt;
&lt;td&gt;≈ $1.07&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Call it roughly 9x on this app, and the estimate columns are labeled as exactly that — estimates. The ratio is not a constant of nature. It is a consequence of one design decision: source code, the most expensive thing a model can emit, never enters the token stream.&lt;/p&gt;

&lt;p&gt;And notice what happens as the app grows. A CRUD-generator argument is about a hundred tokens whether the table has three columns or thirty. Hand-written code is not. The gap widens with size.&lt;/p&gt;

&lt;h2&gt;
  
  
  Where 10x holds — and where it is 5x
&lt;/h2&gt;

&lt;p&gt;Now the honest fine print.&lt;/p&gt;

&lt;p&gt;The July benchmark measured roughly 80 percent — 5x — across a full session, because a real session also contains reasoning, planning, schema decisions, and verification, and those do not compress. The frontend in this build was hand-written by the agent, at normal output rates, and took as long as the entire backend.&lt;/p&gt;

&lt;p&gt;The 10x figure belongs to the code-emission slice of the work: the backend, the endpoints, the auth, the data layer. On backend-heavy agentic workloads that slice dominates, and the blended number climbs toward it. On reasoning-heavy work, expect the 5x, not the 10x.&lt;/p&gt;

&lt;p&gt;Both numbers are worth having. Neither requires exaggeration.&lt;/p&gt;

&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;The standard advice for cutting Claude costs is to pick a smaller model, cache your prompts, and batch your jobs. All fine. All discounts on the same architecture.&lt;/p&gt;

&lt;p&gt;Magic changes the architecture. The agent stops being a code emitter paying $50 per million tokens for the privilege, and becomes an operator of a platform that already knows how to build backends — declaratively, server-side, with security enforced by the runtime instead of regenerated per project.&lt;/p&gt;

&lt;p&gt;We measured it: a live, role-secured, fifteen-endpoint backend in 222 seconds, 669 lines generated, zero lines through the token meter.&lt;/p&gt;

&lt;p&gt;Claude is a great engineer. Stop paying it by the line.&lt;/p&gt;

&lt;p&gt;Magic is MIT-licensed and open source — the repository is at &lt;a href="https://github.com/polterguy/magic" rel="noopener noreferrer"&gt;github.com/polterguy/magic&lt;/a&gt;, with documentation at &lt;a href="https://docs.ainiro.io" rel="noopener noreferrer"&gt;docs.ainiro.io&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Originally published at &lt;a href="https://hyperlambda.dev/blog/why-claude-is-10x-cheaper-when-it-builds-on-magic-cloud" rel="noopener noreferrer"&gt;hyperlambda.dev&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>ai</category>
      <category>claude</category>
      <category>lowcode</category>
      <category>backend</category>
    </item>
    <item>
      <title>Break my AI Sandbox and make $100 - Psst, nobody's done it yet!</title>
      <dc:creator>Thomas Hansen</dc:creator>
      <pubDate>Sat, 01 Aug 2026 10:10:45 +0000</pubDate>
      <link>https://dev.to/polterguy/break-my-ai-sandbox-and-make-100-psst-nobodys-done-it-yet-2b9n</link>
      <guid>https://dev.to/polterguy/break-my-ai-sandbox-and-make-100-psst-nobodys-done-it-yet-2b9n</guid>
      <description>&lt;p&gt;I have a standing offer: find a verified security bug in Magic's backend — the C# code or the Hyperlambda runtime — and I'll pay you $100.&lt;/p&gt;

&lt;p&gt;Nobody has collected.&lt;/p&gt;

&lt;p&gt;$100 is obviously not the point. Companies pay 100 times that for bounties on software with a fraction of the attack surface. The point is that I'm willing to put money on the architecture, publicly, permanently — because the architecture is the product.&lt;/p&gt;

&lt;h2&gt;
  
  
  The runtime is the security boundary
&lt;/h2&gt;

&lt;p&gt;Most AI coding tools work like this: the model generates free-form code, and you &lt;em&gt;hope&lt;/em&gt; it generated something safe. The model is the security boundary. Which means every prompt injection, every hallucination, every "ignore previous instructions" is a potential breach.&lt;/p&gt;

&lt;p&gt;Hyperlambda inverts this. The AI generates code, but the &lt;em&gt;runtime&lt;/em&gt; decides what executes:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Hyperlambda is not free-form code. It's a declarative structure that parses into an AST, and the runtime validates that AST before anything runs.&lt;/li&gt;
&lt;li&gt;Slots are whitelisted. If a slot isn't on the whitelist for the current context, it doesn't execute. Period. The AI can hallucinate whatever it wants — the runtime says no.&lt;/li&gt;
&lt;li&gt;RBAC is enforced at &lt;em&gt;execution time&lt;/em&gt;, not generation time. It doesn't matter what code was generated or by whom. If your JWT doesn't carry the role, the invocation is refused.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;If the AI writes something it shouldn't run, the runtime says no. That single sentence is the difference between a demo and something a regulated company can ship.&lt;/p&gt;

&lt;h2&gt;
  
  
  Receipts
&lt;/h2&gt;

&lt;p&gt;I don't expect you to take my word for it. In April I let Claude Code — one of the strongest code-analysis agents available — loose on the entire Magic codebase with explicit instructions to break it.&lt;/p&gt;

&lt;p&gt;It found real issues. All hardening, none sandbox escapes:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;No cap on request body size, allowing a memory-exhaustion DoS. Fixed.&lt;/li&gt;
&lt;li&gt;Missing timeouts that left the server exposed to Slowloris-style slow-drip attacks. Fixed.&lt;/li&gt;
&lt;li&gt;An edge case in path resolution that needed an explicit traversal guard. Fixed.&lt;/li&gt;
&lt;li&gt;A debug statement leaking information to the console. Removed.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;And here's what it &lt;em&gt;couldn't&lt;/em&gt; do, after crawling roughly 9,000 commits accumulated over some 7 years:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;No SQL injection. Every database access goes through parameterized ADO.NET.&lt;/li&gt;
&lt;li&gt;No password extraction. BCrypt with per-user salts.&lt;/li&gt;
&lt;li&gt;No secrets leakage. AES-GCM for storage.&lt;/li&gt;
&lt;li&gt;No auth bypass. Standard JWT, correctly implemented.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;No sandbox escape.&lt;/strong&gt; Every attempt to execute something outside the whitelisted slots was refused by the runtime.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The full write-up is here: &lt;a href="https://hyperlambda.dev/blog/claude-code-tried-to-break-magic-cloud-and-mostly-ended-up-confirming-its-security" rel="noopener noreferrer"&gt;Claude Code tried to break Magic Cloud, and mostly ended up confirming its security&lt;/a&gt;.&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%2Fou4in3lslsgm8p3bhrmi.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%2Fou4in3lslsgm8p3bhrmi.png" alt="The Hyperlambda playground" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Why free-form codegen can't make this offer
&lt;/h2&gt;

&lt;p&gt;Think about what it would take for an AI agent platform built on free-form code generation to make the same offer.&lt;/p&gt;

&lt;p&gt;They'd be paying out daily. When the model is the boundary, one clever prompt is a breach. The industry's answer so far has been layers of prompt-level guardrails — instructions asking the model to please behave. That's not security. That's etiquette.&lt;/p&gt;

&lt;p&gt;When the runtime is the boundary, the model's behavior becomes almost irrelevant to your security posture. The model can be jailbroken, poisoned, or just plain wrong — and the blast radius is a refused invocation and a log entry.&lt;/p&gt;

&lt;p&gt;This is why I can put a standing bounty on it. The security claim isn't "our AI is well-behaved." The claim is "the runtime refuses everything that isn't explicitly allowed." That's a falsifiable, testable claim — so go test it.&lt;/p&gt;

&lt;h2&gt;
  
  
  How to collect
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;Go to &lt;a href="https://playground.hyperlambda.dev" rel="noopener noreferrer"&gt;playground.hyperlambda.dev&lt;/a&gt; and hammer it. Or self-host — the whole thing is MIT licensed, so you can read every line of the code you're attacking.&lt;/li&gt;
&lt;li&gt;Find a verified bug in the backend C# or Hyperlambda code. Sandbox escape, RBAC bypass, executing a non-whitelisted slot — anything that breaks the security model.&lt;/li&gt;
&lt;li&gt;Send it to me. I verify it, I fix it, I pay you $100, and I'll publicly credit you for the find.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Prompt-level shenanigans against the AI itself don't count — making a chatbot say something silly is not a runtime breach. The claim under test is the runtime.&lt;/p&gt;

&lt;h2&gt;
  
  
  If you're evaluating AI agent platforms
&lt;/h2&gt;

&lt;p&gt;Ask every vendor you're talking to one question: &lt;em&gt;what happens when the AI generates something it shouldn't?&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;If the answer involves the words "the model is trained to" or "our system prompt instructs" — you're buying etiquette, not security. If the answer is a deterministic runtime mechanism you can read the source code of, you're buying engineering.&lt;/p&gt;

&lt;p&gt;Magic has been running in production since 2020. It's MIT licensed. The code is at &lt;a href="https://github.com/polterguy/magic" rel="noopener noreferrer"&gt;github.com/polterguy/magic&lt;/a&gt;, and the docs are at &lt;a href="https://docs.ainiro.io" rel="noopener noreferrer"&gt;docs.ainiro.io&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Break it and make $100. Psst — nobody's done it yet.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Originally published at &lt;a href="https://hyperlambda.dev/blog/break-my-ai-sandbox-and-make-100-psst-nobodys-done-it-yet" rel="noopener noreferrer"&gt;hyperlambda.dev&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>ai</category>
      <category>security</category>
      <category>opensource</category>
      <category>dotnet</category>
    </item>
    <item>
      <title>Turn Your Legacy SQL Server Database into a Modern Full Stack App in Minutes</title>
      <dc:creator>Thomas Hansen</dc:creator>
      <pubDate>Fri, 31 Jul 2026 20:42:35 +0000</pubDate>
      <link>https://dev.to/polterguy/turn-your-legacy-sql-server-database-into-a-modern-full-stack-app-in-minutes-dff</link>
      <guid>https://dev.to/polterguy/turn-your-legacy-sql-server-database-into-a-modern-full-stack-app-in-minutes-dff</guid>
      <description>&lt;p&gt;The app in the screenshots below took 7 minutes to build.&lt;/p&gt;

&lt;p&gt;Not a mockup. A login screen backed by JWT authentication, a client manager reading and writing through a role-secured CRUD API, and an Emails tab that dispatches real messages over SMTP. The backend was produced by wrapping a database in generated CRUD endpoints, plus one English sentence handed to the Hyperlambda Generator for the send-email endpoint.&lt;/p&gt;

&lt;p&gt;I have published the receipts for builds like this before, so this article is not another ledger.&lt;/p&gt;

&lt;p&gt;It is about the part of those 7 minutes that usually gets lost.&lt;/p&gt;

&lt;h2&gt;
  
  
  The database was the boring part
&lt;/h2&gt;

&lt;p&gt;Nothing in the build depended on the database being new.&lt;/p&gt;

&lt;p&gt;The CRUD generator does not care where a schema came from. It reads metadata — tables, columns, types, keys — and every Microsoft SQL Server database on earth exposes exactly that. The database in this demo was created seconds before the endpoints were. Yours carries twenty years of history, three generations of developers, and foreign keys that encode how your business actually works.&lt;/p&gt;

&lt;p&gt;Same metadata. Same generator. Same 7 minutes.&lt;/p&gt;

&lt;p&gt;That is the entire point. The demos always run on fresh databases because demos need reproducibility — but the machinery only ever sees the schema, and your ERP on SQL Server has a better schema than any demo. The hard part of a full stack app — modelling the business correctly — is the part you finished years ago.&lt;/p&gt;

&lt;h2&gt;
  
  
  What got built
&lt;/h2&gt;

&lt;p&gt;The front door. JWT authentication against the platform's built-in auth — no auth library, no password hashing code, no session plumbing anywhere in the app.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F1wtogq0y3nf3edi6zpw7.webp" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F1wtogq0y3nf3edi6zpw7.webp" alt="The login screen — JWT authentication handled by the platform, zero auth code in the application" width="800" height="495"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The client manager. Search, add, edit, delete, and per-client notes — every operation travelling through generated CRUD endpoints, each one gated on a role before any logic runs.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fues7ht7wxkmuioyg2mae.webp" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fues7ht7wxkmuioyg2mae.webp" alt="The client manager — search, status badges and per-client notes over generated CRUD endpoints" width="800" height="494"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;And the one endpoint that is not a table projection: composing an email to a client, dispatched through the platform's SMTP integration. That endpoint was described in a single English sentence and generated in seconds — the application never saw a mail-provider credential, because there is none in the application.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fnhf7119skgmcsch2cvnl.webp" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fnhf7119skgmcsch2cvnl.webp" alt="The Emails tab — a generated endpoint looks up the client and dispatches through platform SMTP" width="800" height="494"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  The recipe
&lt;/h2&gt;

&lt;p&gt;Four moves.&lt;/p&gt;

&lt;p&gt;Connect the database. Magic speaks to SQL Server through the standard .NET data provider — it is one more client, nothing installed inside the database, no schema changes.&lt;/p&gt;

&lt;p&gt;Wrap the tables. The CRUD generator reads the schema and emits endpoints — read, create, update, delete, count — with authentication and role-based access control already wired in.&lt;/p&gt;

&lt;p&gt;Describe what CRUD cannot do. "Look up this client's email address and send them a message" is one sentence, and the Hyperlambda Generator turns it into a working, role-gated endpoint.&lt;/p&gt;

&lt;p&gt;Serve the frontend. The same system that serves the API serves static files, so the app's HTML, CSS and JavaScript went live the moment they were written. One host, no CORS, no separate deployment.&lt;/p&gt;

&lt;p&gt;The full walkthrough — scoped database users, read-only starts, connecting an agent over MCP — is its own article: &lt;a href="https://hyperlambda.dev/blog/create-an-ai-agent-from-your-sql-server-or-mysql-database-step-by-step" rel="noopener noreferrer"&gt;Create an AI Agent From Your SQL Server or MySQL Database, Step by Step&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  No agent required
&lt;/h2&gt;

&lt;p&gt;This build ran through an AI agent over MCP, but the CRUD wrap does not need one. The dashboard's Backend Generator does the same thing point-and-click: pick the database, tick the tables, choose which roles may call what, and click Generate.&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%2Fsdhzs9il7h0x3nl9ybua.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%2Fsdhzs9il7h0x3nl9ybua.png" alt="The Backend Generator — pick a database, tick tables, choose roles, and generate the CRUD API from the dashboard" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Same generated endpoints, same enforcement, no conversation required. The agent is a convenience, not a dependency.&lt;/p&gt;

&lt;h2&gt;
  
  
  "But my database is legacy"
&lt;/h2&gt;

&lt;p&gt;Legacy means load-bearing, not obsolete — I have made that argument at length in &lt;a href="https://hyperlambda.dev/blog/supabase-for-sql-server-and-mysql-magic-brings-the-supabase-experience-to-legacy-databases-on-premise" rel="noopener noreferrer"&gt;Supabase for SQL Server and MySQL&lt;/a&gt;, so here is the short version.&lt;/p&gt;

&lt;p&gt;You connect through a scoped database user, so the platform can never do more than the credentials the DBA granted. You can start read-only, which turns "what if something writes the wrong thing" into a non-question for day one. And the whole stack runs in two containers you place yourself — same rack, same VLAN, same firewall the auditors already approved. The database does not change, and the data does not leave.&lt;/p&gt;

&lt;h2&gt;
  
  
  The fine print
&lt;/h2&gt;

&lt;p&gt;Seven minutes was measured for this schema, at this size. Your 200-table ERP will take longer — but the added time goes into decisions, not code: which tables deserve exposure, which operations each table gets, which roles may call them. Those are judgment calls a DBA is already equipped to make, and they were never the expensive part.&lt;/p&gt;

&lt;p&gt;The frontend is where human taste still spends its time. Generated backends are uniform; good interfaces are not.&lt;/p&gt;

&lt;p&gt;And writes deserve the same respect they have always deserved. Start read-only, prove the surface, then grant writes table by table. The speed changes nothing about the discipline.&lt;/p&gt;

&lt;h2&gt;
  
  
  The question worth asking
&lt;/h2&gt;

&lt;p&gt;The question is no longer whether your organisation can afford to modernise the systems built on SQL Server. It is whether wrapping one of them in a secured API and a working app is still a project at all — or just an afternoon.&lt;/p&gt;

&lt;p&gt;Magic is MIT-licensed and open source at &lt;a href="https://github.com/polterguy/magic" rel="noopener noreferrer"&gt;github.com/polterguy/magic&lt;/a&gt;, with documentation at &lt;a href="https://docs.ainiro.io" rel="noopener noreferrer"&gt;docs.ainiro.io&lt;/a&gt;.&lt;/p&gt;

</description>
      <category>ai</category>
      <category>sqlserver</category>
      <category>dotnet</category>
      <category>lowcode</category>
    </item>
    <item>
      <title>46,000 Lines of Angular, Gone in a Weekend</title>
      <dc:creator>Thomas Hansen</dc:creator>
      <pubDate>Mon, 27 Jul 2026 07:14:31 +0000</pubDate>
      <link>https://dev.to/polterguy/46000-lines-of-angular-gone-in-a-weekend-2nal</link>
      <guid>https://dev.to/polterguy/46000-lines-of-angular-gone-in-a-weekend-2nal</guid>
      <description>&lt;p&gt;I replaced the entire Magic Cloud dashboard this week. Forty-six thousand lines of Angular — HTML, TypeScript and CSS — gone, and in its place a React application of fifteen and a half thousand lines that does more than the thing it replaced.&lt;/p&gt;

&lt;p&gt;Twenty hours of coding. Thirty hours in total, counting my own reviewing, testing and swearing.&lt;/p&gt;

&lt;p&gt;I know exactly what that job costs when you do it by hand, because I have already done it by hand. In 2021 I rewrote this same dashboard the traditional way. A senior developer worked on it for a month and a half. Then I picked it up and worked on it for months more. Call it a three-month job for two experienced developers who knew the domain cold.&lt;/p&gt;

&lt;p&gt;That comparison is the only reason this article is worth writing. Anyone can claim an AI wrote a lot of code quickly. Very few people have the same application, built twice, by the same author, with the same requirements — where the only variable that changed is the tooling.&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%2Fn3l7uxktp24ybspfna8l.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%2Fn3l7uxktp24ybspfna8l.png" alt="The new Magic Cloud dashboard, showing KPI cards, the MCP agent banner and the Chatbot Wizard" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  The ledger
&lt;/h2&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;&lt;/th&gt;
&lt;th&gt;Then&lt;/th&gt;
&lt;th&gt;Now&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Framework&lt;/td&gt;
&lt;td&gt;Angular&lt;/td&gt;
&lt;td&gt;React 18 + Vite + TypeScript&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Lines of code&lt;/td&gt;
&lt;td&gt;~46,000&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;15,497&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Files&lt;/td&gt;
&lt;td&gt;many hundreds&lt;/td&gt;
&lt;td&gt;47&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Runtime dependencies&lt;/td&gt;
&lt;td&gt;the Angular universe&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;7&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Production build&lt;/td&gt;
&lt;td&gt;tens of MB&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;856 KB&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Build time&lt;/td&gt;
&lt;td&gt;minutes&lt;/td&gt;
&lt;td&gt;~1 second&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Time to write&lt;/td&gt;
&lt;td&gt;~3 months, two people&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;30 hours, one person supervising&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;A word on that line-count comparison, because it is the kind of number people rightly poke at. Angular splits a single component across a &lt;code&gt;.ts&lt;/code&gt; file, an &lt;code&gt;.html&lt;/code&gt; template and an &lt;code&gt;.scss&lt;/code&gt; stylesheet. React folds all three into one &lt;code&gt;.tsx&lt;/code&gt;. Counting the old TypeScript against the new TypeScript would flatter me dishonestly, so both sides count everything: markup, logic and styling. Forty-six thousand against fifteen and a half.&lt;/p&gt;

&lt;p&gt;The dependency line matters more than it looks. The whole application runs on React, React-DOM, React Router, CodeMirror, SignalR, &lt;code&gt;marked&lt;/code&gt; and DOMPurify. That is the entire third-party surface. There is no state management library, no component library, no CSS framework, no build plugin zoo. When your dependency list fits in one sentence, upgrades stop being events.&lt;/p&gt;

&lt;h2&gt;
  
  
  How it actually ran
&lt;/h2&gt;

&lt;p&gt;I drove Claude — Fable for the bulk of the work, Opus for the parts that needed more thinking. The model wrote essentially all of the code. My job was to babysit: sanity-check what came back, test it in a browser, catch the things that were confidently wrong, and decide what to build next.&lt;/p&gt;

&lt;p&gt;The loop that made it work was not "describe the feature and hope." It was: screenshot the old Angular screen, build the new one, screenshot the new one, compare them, fix the gap. Verification happened against rendered pages, not against source code. That distinction matters, because a model reading old Angular source will faithfully reproduce old Angular mistakes. A model looking at what the screen actually does will build what the screen actually does.&lt;/p&gt;

&lt;p&gt;Below is what came out of that loop, screen by screen — because the interesting claim is not that thirty hours produced &lt;em&gt;code&lt;/em&gt;, it is that thirty hours produced &lt;em&gt;this much working software&lt;/em&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Login
&lt;/h2&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%2Fc18yybx3aa2lvp0rgfee.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%2Fc18yybx3aa2lvp0rgfee.png" alt="The Magic login screen with backend selector, magnetic link and Google sign-in" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The dashboard talks to any Magic backend, so the first thing it needs is which one. The backend selector remembers every cloudlet you have ever signed into and keeps a separate JWT for each, so switching between them does not mean signing in again.&lt;/p&gt;

&lt;p&gt;Underneath the password field are two things the Angular version never had. &lt;strong&gt;Magnetic link&lt;/strong&gt; sends a temporary sign-in link to your email — it doubles as passwordless login, and it only appears if the backend actually has SMTP configured, because offering it otherwise is a dead end. &lt;strong&gt;Continue with Google&lt;/strong&gt; signs you in over OIDC against whatever providers the backend has registered. Both were built during this port, not ported into it.&lt;/p&gt;

&lt;h2&gt;
  
  
  Dashboard
&lt;/h2&gt;

&lt;p&gt;The landing screen answers "what is this cloudlet, and is anything wrong with it" in one glance: version, endpoint count, users, tasks, log items.&lt;/p&gt;

&lt;p&gt;Two panels below that are new. The first announces that &lt;strong&gt;your cloudlet is an AI agent&lt;/strong&gt; — with the MCP plugin installed, the URL shown there hands any MCP-capable agent your endpoints as callable tools. Claude, or anything else speaking the protocol, can discover and invoke them directly.&lt;/p&gt;

&lt;p&gt;The second is the &lt;strong&gt;Chatbot Wizard&lt;/strong&gt;, which runs the other direction: give it a website, pick a model and a persona, and the backend crawls the site, turns what it finds into training data, and gives you an embeddable chatbot grounded in your own content. The crawl takes minutes and reports progress over a SignalR channel, so the feedback window opens &lt;em&gt;before&lt;/em&gt; the job starts — a socket that connects late misses the first messages. You can close the window; the crawl carries on.&lt;/p&gt;

&lt;h2&gt;
  
  
  Hyper IDE
&lt;/h2&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%2Fy4gyvqeifietyxqeejq9.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%2Fy4gyvqeifietyxqeejq9.png" alt="Hyper IDE with a Hyperlambda file open, a dirty tab marker, and the slot autocomplete popup showing" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The file manager and code editor for everything on your server, and the component that absorbed the most work.&lt;/p&gt;

&lt;p&gt;The tree browses the whole backend file system. Files open as &lt;strong&gt;tabs&lt;/strong&gt;, several at once, and each tab tracks whether it is dirty — a dot appears on the tab and beside the path in the header the moment you change something, and navigating away asks before discarding it. The editor runs a Hyperlambda mode ported from the old dashboard, so slot invocations are coloured correctly, and &lt;strong&gt;Ctrl+Space completes against the backend's actual vocabulary&lt;/strong&gt; — the list of slots is fetched from the server you are connected to, and cached per backend, because two cloudlets with different plugins know different slots. That is the popup in the screenshot above, listing the &lt;code&gt;log.*&lt;/code&gt; slots this particular cloudlet knows about.&lt;/p&gt;

&lt;p&gt;Executing a file is smarter than it was. If the file is a real HTTP endpoint — it ends in &lt;code&gt;.get.hl&lt;/code&gt;, &lt;code&gt;.post.hl&lt;/code&gt; and friends, and lives under &lt;code&gt;/modules/&lt;/code&gt; or &lt;code&gt;/system/&lt;/code&gt; — the IDE invokes it as an endpoint, with arguments, and shows you the status code and response headers. Only files that are not endpoints get evaluated directly. You can upload and download files, preview HTML, XML, images, JavaScript and CSS straight from &lt;code&gt;/etc/www/&lt;/code&gt;, and press F1 on any selection to ask the AI what it does.&lt;/p&gt;

&lt;h2&gt;
  
  
  Playground
&lt;/h2&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%2F6t19orvr900t3aradjg0.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%2F6t19orvr900t3aradjg0.png" alt="The Hyperlambda Playground with a data.read example and its result pane" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Hyperlambda, executed on your server, without saving anything first. Input on the left, result on the right, F5 to run. It is the scratchpad you reach for when you want to know what a slot actually returns, and it saves snippets when the scratch turns out to be worth keeping.&lt;/p&gt;

&lt;h2&gt;
  
  
  SQL Studio
&lt;/h2&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%2Fv8edktw394ihvetbktuy.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%2Fv8edktw394ihvetbktuy.png" alt="SQL Studio with a query written against the chinook database" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Two tabs over the same three selectors: database type, connection string, database.&lt;/p&gt;

&lt;p&gt;The &lt;strong&gt;SQL&lt;/strong&gt; tab is a query editor with syntax colouring, Ctrl+Space completion over your real tables and columns, saved snippets, &lt;code&gt;.sql&lt;/code&gt; import, CSV export of results, and a Safe mode toggle that caps what a careless query can do. Selecting part of the text executes only the selection.&lt;/p&gt;

&lt;p&gt;The &lt;strong&gt;Designer&lt;/strong&gt; tab is the one I am quietest about and proudest of. It renders every table in the database as a card — primary keys, column types, nullability, and the foreign keys spelled out underneath — and lets you add tables, add columns and wire up relations without writing DDL. It will also hand you the DDL for a single table or the whole database if you would rather write it yourself.&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%2Faxumu6rdhk27fpq2rqvf.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%2Faxumu6rdhk27fpq2rqvf.png" alt="The SQL Studio Designer tab rendering chinook tables as schema cards with foreign keys" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Databases
&lt;/h2&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%2F9s05kbp1hmn30e308nes.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%2F9s05kbp1hmn30e308nes.png" alt="The Databases screen listing SQLite databases with table counts" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Create SQLite databases, back them up, restore them from an uploaded backup, delete the ones you no longer need — and, on the second tab, connect to external MySQL, PostgreSQL and SQL Server instances. Everything else in the dashboard then treats those exactly like a local database.&lt;/p&gt;

&lt;h2&gt;
  
  
  Generator
&lt;/h2&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%2F2w0appui4pdnq6dbm3qf.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%2F2w0appui4pdnq6dbm3qf.png" alt="The Generator screen with chinook tables selected and CRUD options" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Point it at a database, tick the tables, and it writes you a complete CRUD backend: POST, GET, PUT and DELETE per table, with paging, sorting, aggregates, distinct and search endpoints if you want them. You choose which roles may call what, whether writes are logged, how long GET responses may be cached, and whether existing files may be overwritten. The second tab wraps a custom SQL statement in an endpoint of its own.&lt;/p&gt;

&lt;p&gt;This is the part that turns a schema into a secured API in seconds, and it is why the backend is rarely where the time goes.&lt;/p&gt;

&lt;h2&gt;
  
  
  Endpoints
&lt;/h2&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%2Fiynm5x308yn6yxywlahh.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%2Fiynm5x308yn6yxywlahh.png" alt="The Endpoints screen with modules expanded showing HTTP verb badges" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Every endpoint on the backend, grouped by module, with its HTTP verb. Open one and you get a form built from its actual arguments — fill them in, invoke it, and see the status code, the response headers and the body rendered according to its content type.&lt;/p&gt;

&lt;p&gt;It handles files in both directions now, which it did not before: endpoints that accept &lt;code&gt;multipart/form-data&lt;/code&gt; get a proper file picker with image thumbnails inline, and endpoints that return files offer them as downloads. Each module will also hand you its OpenAPI specification, which is how you point an external tool — or an agent — at a subset of your API.&lt;/p&gt;

&lt;h2&gt;
  
  
  Users and roles
&lt;/h2&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%2F1t8ynapnt41vwmcjaext.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%2F1t8ynapnt41vwmcjaext.png" alt="The Users and roles screen listing users with their roles" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Who may reach your backend, and what they may do. Create users, assign roles, change passwords, lock accounts. Roles are the same objects the Generator gates endpoints with and the same ones inside the JWT, so this screen is the authorisation surface for the entire platform in one table.&lt;/p&gt;

&lt;h2&gt;
  
  
  Task Manager
&lt;/h2&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%2F9e9s9d90o5ep4t6idixq.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%2F9e9s9d90o5ep4t6idixq.png" alt="The Task Manager listing scheduled Hyperlambda tasks" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Hyperlambda that runs on a schedule or on demand — backups, cleanup jobs, crawls, alerts. Tasks can repeat on an interval, fire once at a fixed date, or follow a custom repetition pattern, and you can execute any of them immediately to see what happens. Executing asks first, because a task named &lt;code&gt;delete-old-log-items&lt;/code&gt; means it.&lt;/p&gt;

&lt;h2&gt;
  
  
  Machine Learning
&lt;/h2&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%2Fhmoamj1a6gwo0no8fpis.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%2Fhmoamj1a6gwo0no8fpis.png" alt="The Machine Learning screen listing models with import, vectorise and embed actions" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The largest single screen in the application, at two thousand lines. Models define which LLM answers, at what temperature, with what system message and what threshold. Training data is the content those models answer from — crawled from a site, uploaded as files, or written by hand. Vectorising turns it into embeddings; embedding hands you the snippet that drops the finished chatbot onto a web page. A history tab shows what people actually asked it.&lt;/p&gt;

&lt;h2&gt;
  
  
  Plugins
&lt;/h2&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%2Ffwm5jiqxhfbkmi4pv2cx.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%2Ffwm5jiqxhfbkmi4pv2cx.png" alt="The Plugins screen showing available Bazar modules" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The Bazar: MCP, OAuth, OpenAI, Ollama, HuggingFace, Shopify, HubSpot, NetSuite, scraping, charts, and a couple of dozen more. One click installs a module into your cloudlet, endpoints and all. You can also install your own from a ZIP file.&lt;/p&gt;

&lt;h2&gt;
  
  
  Profile
&lt;/h2&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%2F33razafuptqnwwr9eomz.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%2F33razafuptqnwwr9eomz.png" alt="The Profile screen with details, password change and access token generation" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Your name, your email, your password — and &lt;strong&gt;access tokens&lt;/strong&gt;, which is the part that matters operationally. Generate a long-lived JWT for a service account, a CI pipeline or an integration, scoped to the roles you pick and expiring on a date you choose.&lt;/p&gt;

&lt;h2&gt;
  
  
  Log
&lt;/h2&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%2Feq9bs6yumty8jrqli6ik.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%2Feq9bs6yumty8jrqli6ik.png" alt="The Log screen listing backend log entries by type and time" width="800" height="500"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;What your backend has been doing, newest first, filterable, with severity on every row. It is where you go when something did not work, and the generated CRUD endpoints write to it automatically when you ask them to log writes.&lt;/p&gt;

&lt;h2&gt;
  
  
  What got better, not just moved
&lt;/h2&gt;

&lt;p&gt;If this had been a straight translation I would not have bothered writing about it. The features that did not exist in the Angular version, all built inside those same thirty hours:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;OIDC login&lt;/strong&gt; — sign in with Google or any registered provider&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;File upload and download through the Endpoints screen&lt;/strong&gt;, with inline image previews&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Dirty-file tracking&lt;/strong&gt; across Hyper IDE, SQL Studio and the Playground&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Multiple files open at once&lt;/strong&gt;, as tabs&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Multi-backend support&lt;/strong&gt; with a separate JWT per cloudlet and shareable &lt;code&gt;?backend=&lt;/code&gt; links&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Magnetic-link login&lt;/strong&gt; for passwordless sign-in&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;The MCP agent banner&lt;/strong&gt; and the &lt;strong&gt;Chatbot Wizard&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Previewing&lt;/strong&gt; HTML, XML, images, JavaScript and CSS from &lt;code&gt;/etc/www/&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;An AI support agent on F1&lt;/strong&gt;, answering from the Hyperlambda and Magic documentation&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  The bug ledger
&lt;/h2&gt;

&lt;p&gt;Two rules make this kind of build survivable: the model writes, and a human reviews everything before it lands. Here is what the review caught.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;React's StrictMode caused three separate bugs.&lt;/strong&gt; It deliberately runs effects twice in development, which broke an image preview (the object URL was revoked before the image loaded), killed a SignalR connection (started and stopped in the same tick), and made two stacked dialogs land on the same z-index. All three were the same root cause wearing different hats, and all three were found by looking at the screen, not the code.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;The model invented a slot that does not exist.&lt;/strong&gt; It used &lt;code&gt;date.add&lt;/code&gt; for date arithmetic. There is no such slot. The fix was &lt;code&gt;math.add&lt;/code&gt; with a &lt;code&gt;time&lt;/code&gt; node — the pattern already used elsewhere in the codebase.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;It invented a role, too.&lt;/strong&gt; It gated the dashboard on an &lt;code&gt;admin&lt;/code&gt; role. The backend has 159 endpoints and every one of them checks &lt;code&gt;root&lt;/code&gt;. Caught during review, renamed everywhere.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;A mail endpoint was built with the wrong node shape&lt;/strong&gt;, which produced a runtime error rather than an email. &lt;strong&gt;A magnetic link took three attempts&lt;/strong&gt; to redirect correctly, because the token was being stripped from the URL before a second render could read it. &lt;strong&gt;An expired token walked straight into the dashboard&lt;/strong&gt;, because expiry was being checked without asking the server whether the token was still valid.&lt;/p&gt;

&lt;p&gt;And two mistakes the model made about its own work, which I include because they are the most instructive of the lot. It told me one screen had no confirmation dialog before running a destructive task — it had searched the code in a way that could not have found the guard, which was sitting six lines above what it read. And it told me a screenshot I had pushed did not exist, when the file was recoverable the whole time. Both were confidently wrong, and both were wrong in the same direction: &lt;em&gt;reporting an absence after looking in the wrong place.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Nothing on this list shipped. But the list is the honest cost of the method, and anyone telling you their AI build had no such list is not counting.&lt;/p&gt;

&lt;h2&gt;
  
  
  What this actually demonstrates
&lt;/h2&gt;

&lt;p&gt;It would be easy to read this as "AI writes code fast." That is not the finding, and it is not what changed.&lt;/p&gt;

&lt;p&gt;The expensive part of the 2021 rewrite was never typing. It was reading the old implementation to work out what a screen did in the edge cases, holding forty-odd screens' worth of behaviour in your head, and checking parity one control at a time. That is the part that compressed. The model does not get bored on screen thirty-one, and it does not skip the tedious parts of the Machine Learning page because the Dashboard was more fun.&lt;/p&gt;

&lt;p&gt;What did not change is who is responsible. I reviewed everything. I found the invented slot, the invented role, and the token that should not have been trusted. The ratio moved; the accountability did not. Thirty hours with a competent reviewer is not the same thing as thirty hours unattended, and I would not claim otherwise.&lt;/p&gt;

&lt;p&gt;Three months to thirty hours, on the same application, by the same person. That is the number I would want to see from someone else before I believed any of this, so it is the number I am publishing.&lt;/p&gt;

&lt;p&gt;Magic is MIT-licensed and open source — the repository is at &lt;a href="https://github.com/polterguy/magic" rel="noopener noreferrer"&gt;github.com/polterguy/magic&lt;/a&gt;, with documentation at &lt;a href="https://docs.ainiro.io" rel="noopener noreferrer"&gt;docs.ainiro.io&lt;/a&gt;.&lt;/p&gt;

</description>
      <category>ai</category>
      <category>react</category>
      <category>angular</category>
      <category>webdev</category>
    </item>
  </channel>
</rss>
