<?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>Forem: Bas Steins</title>
    <description>The latest articles on Forem by Bas Steins (@bascodes).</description>
    <link>https://forem.com/bascodes</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.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F374182%2Fdefaf96f-5c49-4599-ba57-c2d1cbff1b6f.jpg</url>
      <title>Forem: Bas Steins</title>
      <link>https://forem.com/bascodes</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://forem.com/feed/bascodes"/>
    <language>en</language>
    <item>
      <title>Stelvio's Anniversary: Ship Python to AWS</title>
      <dc:creator>Bas Steins</dc:creator>
      <pubDate>Wed, 04 Feb 2026 12:06:04 +0000</pubDate>
      <link>https://forem.com/bascodes/stelvios-anniversary-ship-python-to-aws-3l55</link>
      <guid>https://forem.com/bascodes/stelvios-anniversary-ship-python-to-aws-3l55</guid>
      <description>&lt;p&gt;Last weekend, we released our anniversary release of &lt;a href="https://github.com/stelviodev/stelvio" rel="noopener noreferrer"&gt;Stelvio&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Stelvio is an open source framework that allows you to create and deploy infrastructure to the Cloud, AWS in particular.&lt;/p&gt;

&lt;p&gt;We support a wide variety of serverless services, including:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Compute: &lt;a href="https://stelvio.dev/components/aws/lambda/" rel="noopener noreferrer"&gt;Functions&lt;/a&gt; are a first class citizen in Stelvio&lt;/li&gt;
&lt;li&gt;Storage: &lt;a href="https://stelvio.dev/components/aws/s3/" rel="noopener noreferrer"&gt;S3 Buckets&lt;/a&gt; are fully integrated, including their notifications&lt;/li&gt;
&lt;li&gt;Database: &lt;a href="https://stelvio.dev/components/aws/dynamo-db/" rel="noopener noreferrer"&gt;DynamoDB&lt;/a&gt; is a noSQL database fully supported by Stelvio&lt;/li&gt;
&lt;li&gt;Schedules: &lt;a href="https://stelvio.dev/components/aws/cron/" rel="noopener noreferrer"&gt;Cron&lt;/a&gt; components let you execute code periodically&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://stelvio.dev/components/aws/topics/" rel="noopener noreferrer"&gt;Topics&lt;/a&gt; and &lt;a href="https://stelvio.dev/components/aws/queues/" rel="noopener noreferrer"&gt;Queues&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;A &lt;a href="https://stelvio.dev/components/aws/cloudfront-router/" rel="noopener noreferrer"&gt;Router&lt;/a&gt; component that unifies resources under the same domain&lt;/li&gt;
&lt;li&gt;a &lt;a href="https://stelvio.dev/concepts/dns/" rel="noopener noreferrer"&gt;configuration option&lt;/a&gt; to customize DNS using Route53 or Cloudfront.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;In addition, we support&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;A live mode: You deploy your stack to AWS as normal but you can run lambda function code locally using a bridgte between your computer and the AWS infrastructure&lt;/li&gt;
&lt;li&gt;Automatic set of permissions: When you &lt;code&gt;link&lt;/code&gt; components, sensible defaults are created for IAM permissions and these are securely linked between your components.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Give it a try:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://stelvio.dev" rel="noopener noreferrer"&gt;Docs and Quickstart&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/codespaces/new?hide_repo_select=true&amp;amp;ref=main&amp;amp;repo=1084563664" rel="noopener noreferrer"&gt;Live coding in Codespaces&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/stelviodev/stelvio" rel="noopener noreferrer"&gt;GitHub Repo&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Watch our intro video:&lt;/p&gt;

&lt;p&gt;

  &lt;iframe src="https://www.youtube.com/embed/L9ZdFHR9BiI"&gt;
  &lt;/iframe&gt;


&lt;/p&gt;

&lt;p&gt;And our celebration podcast:&lt;/p&gt;

&lt;p&gt;

  &lt;iframe src="https://www.youtube.com/embed/PNfxAgYiA94"&gt;
  &lt;/iframe&gt;


&lt;/p&gt;

</description>
      <category>python</category>
      <category>asw</category>
      <category>infrastructure</category>
    </item>
    <item>
      <title>My Year in Review: 2025</title>
      <dc:creator>Bas Steins</dc:creator>
      <pubDate>Wed, 31 Dec 2025 11:34:34 +0000</pubDate>
      <link>https://forem.com/bascodes/my-year-in-review-2025-18i6</link>
      <guid>https://forem.com/bascodes/my-year-in-review-2025-18i6</guid>
      <description>&lt;h1&gt;
  
  
  What happened in 2025
&lt;/h1&gt;

&lt;p&gt;I somehow managed to miss publishing a 2024 review. No grand reason. But here we are.&lt;/p&gt;

&lt;h2&gt;
  
  
  ☕ Community
&lt;/h2&gt;

&lt;p&gt;At the beginning of the year, I joined the &lt;a href="https://bas.surf/torc" rel="noopener noreferrer"&gt;torc.dev community&lt;/a&gt;. That decision set the tone for a lot of what followed.&lt;/p&gt;

&lt;p&gt;Over the summer, I started a podcast: &lt;a href="https://bas.fm" rel="noopener noreferrer"&gt;&lt;strong&gt;bas.fm&lt;/strong&gt;&lt;/a&gt; — conversations with people in tech. No growth hacks, no "content strategy", just honest discussions with people I find interesting. By the end of the year, 26 episodes were out in the world. That alone still surprises me a bit.&lt;/p&gt;

&lt;p&gt;I also attended Commit Your Code Conference in Texas, which was a refreshing reminder that flying across an ocean to talk to people in real life still beats any Discord server or Slack workspace. On top of that, I went to several local meetups — smaller, less polished, but often more meaningful.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Key takeaway:&lt;/strong&gt;&lt;br&gt;&lt;br&gt;
2026 (and probably the years ahead) will be about personal connections more than ever.&lt;/p&gt;

&lt;p&gt;We barely finished processing "the virus" years when AI slop arrived and flooded our timelines. Genuine connections to real people feel scarce — and therefore valuable.&lt;/p&gt;

&lt;h2&gt;
  
  
  ⛰️ Stelvio
&lt;/h2&gt;

&lt;p&gt;In spring, I joined Michal Martinka to work on &lt;a href="https://github.com/stelviodev/stelvio" rel="noopener noreferrer"&gt;&lt;strong&gt;Stelvio&lt;/strong&gt;&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Stelvio is a Python framework for defining AWS serverless infrastructure in pure Python. No YAML, no DSLs pretending not to be programming languages.&lt;/p&gt;

&lt;p&gt;Over time, we made solid progress and are aiming to move the project from alpha to beta early next year. One of the features I’m particularly excited about is the ability to run Lambda functions locally while they’re still part of real AWS infrastructure — no emulator required.&lt;/p&gt;

&lt;p&gt;A lot of the work wasn’t just writing code. It was pair programming sessions, long discussions, trade-off analysis, and occasionally realizing that AWS has &lt;em&gt;opinions&lt;/em&gt; you only discover once you trip over them.&lt;/p&gt;

&lt;p&gt;For me, Stelvio has been a great way to stay involved in open source while also digging deeper into the less glamorous, more intricate parts of AWS. The parts that don’t fit neatly into blog posts or conference talks, but matter a lot in practice.&lt;/p&gt;

&lt;h2&gt;
  
  
  ⚕️ Health
&lt;/h2&gt;

&lt;p&gt;The growing attention around Bryan Johnson's "Don't Die" initiative—where he spends millions each year biohacking his age, complete with monthly colonoscopies—has made any talk of "biohacking" feel a bit cringe these days.&lt;/p&gt;

&lt;p&gt;Still, I stuck with my supplement and workout routines. Winter made that harder than I’d like to admit, but nothing derailed completely.&lt;/p&gt;

&lt;p&gt;It’s now been three years since I last saw a doctor for anything other than routine bloodwork. I feel fitter, stronger, and more energetic than I did ten years ago, which is still the only metric I really trust.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Key takeaway:&lt;/strong&gt;&lt;br&gt;&lt;br&gt;
"Physical health is the foundation for everything that follows." I wrote that in my 2022 retro, and it still holds.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Tools used:&lt;/strong&gt; whole foods, gym, supplements. I’ll probably write a separate post about the exact protocols at some point.&lt;/p&gt;

&lt;h2&gt;
  
  
  🌠 The Future
&lt;/h2&gt;

&lt;p&gt;Work on Stelvio will continue, and I'm planning to focus more on sharing knowledge about AWS, especially tailored for Python developers. I'll keep going with the podcast, get fully back on track with my workout plan, and make a conscious effort to take more time off—just to do nothing.&lt;/p&gt;

&lt;h2&gt;
  
  
  🔮 Predictions
&lt;/h2&gt;

&lt;p&gt;Some thoughts that will almost certainly age badly:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Europe will continue to underperform economically compared to the US.&lt;/li&gt;
&lt;li&gt;AI and robotics will peak in late 2026. We already have powerful LLMs and humanoid robots making strides, but we'll likely hit a wall next year.&lt;/li&gt;
&lt;li&gt;Expectations around AI will keep bouncing between hype and disappointment, especially when it comes to "general" intelligence.&lt;/li&gt;
&lt;li&gt;On the brighter side, AI will get much better at structured tasks, like coding and accounting.&lt;/li&gt;
&lt;li&gt;Attention spans will keep decreasing, and some form of AI-induced brain rot feels inevitable.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Bigger picture&lt;/strong&gt;: Society and economies in the EU and US will shift significantly. The value of traditional knowledge and university degrees might decline further. Chinese EVs will become mainstream. Europe will face mounting financial troubles with welfare budgets. The US will continue grappling with de-dollarization trends. Asset and precious metal prices will rise, opening the door to potential financial bubbles. Overall, it feels like the cards are being reshuffled—populist movements rising in Europe, globalization hitting the West harder, non-Western economies gaining ground, job insecurity growing, and longstanding values like traditional education coming under real pressure.&lt;/p&gt;

&lt;p&gt;None of this is new. It just feels more visible now.&lt;/p&gt;

</description>
      <category>community</category>
      <category>devjournal</category>
    </item>
    <item>
      <title>Agent Mode With Third-Party Models in Copilot</title>
      <dc:creator>Bas Steins</dc:creator>
      <pubDate>Tue, 15 Jul 2025 14:28:58 +0000</pubDate>
      <link>https://forem.com/bascodes/agent-mode-with-third-party-models-in-copilot-317k</link>
      <guid>https://forem.com/bascodes/agent-mode-with-third-party-models-in-copilot-317k</guid>
      <description>&lt;h1&gt;
  
  
  How to Use Third Party Models in GitHub Copilot Agent Mode
&lt;/h1&gt;

&lt;p&gt;&lt;a href="https://github.com/features/copilot" rel="noopener noreferrer"&gt;GitHub Copilot&lt;/a&gt; has become an indispensable coding assistant for millions of developers. While it's incredibly powerful out of the box, many developers wonder: "Can I use other AI models like Claude, GPT-4, or Grok with Copilot's advanced Agent Mode?"&lt;/p&gt;

&lt;p&gt;The answer is yes – but it requires a clever workaround.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Problem: Tool Support Limitations
&lt;/h2&gt;

&lt;p&gt;&lt;a href="https://openrouter.ai/" rel="noopener noreferrer"&gt;OpenRouter&lt;/a&gt; is fantastic for accessing various AI models from OpenAI, Anthropic, and others on a pay-per-use basis. It's perfect for testing different models without committing to expensive subscriptions. You can use powerful models like:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://openrouter.ai/x-ai/grok-4" rel="noopener noreferrer"&gt;Grok&lt;/a&gt; - X.AI's conversational model&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://openrouter.ai/moonshotai/kimi-k2" rel="noopener noreferrer"&gt;Kimi K-2&lt;/a&gt; - Moonshot AI's capable model&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;However, there's a critical limitation: &lt;strong&gt;GitHub Copilot's Agent Mode requires models to support function calling (tools), but OpenRouter's API doesn't announce tool support for its models.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;This means that even though models like Claude and GPT-4 natively support function calling, Copilot won't enable Agent Mode when using them through OpenRouter.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Solution: A Proxy Chain
&lt;/h2&gt;

&lt;p&gt;The solution is elegant: create a local proxy chain that preserves tool calling capabilities while routing requests through OpenRouter.&lt;/p&gt;

&lt;p&gt;Here's the architecture:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;VSCode Copilot → oai2ollama (port 11434) → LiteLLM (port 4000) → OpenRouter → AI Models
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The magic happens in three stages:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;VSCode Copilot&lt;/strong&gt; sends requests to what it thinks is a local Ollama server&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;oai2ollama&lt;/strong&gt; translates Ollama API calls to OpenAI format&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;LiteLLM&lt;/strong&gt; proxies OpenAI-compatible requests to OpenRouter&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;OpenRouter&lt;/strong&gt; routes to the actual AI model providers&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Throughout this chain, tool/function calling capabilities are preserved, enabling full Agent Mode functionality.&lt;/p&gt;

&lt;h2&gt;
  
  
  Setting Up the Proxy: Step-by-Step Guide
&lt;/h2&gt;

&lt;p&gt;I've created an open-source project called &lt;a href="https://github.com/bascodes/copilot-ollama" rel="noopener noreferrer"&gt;copilot-ollama&lt;/a&gt; that handles all the complex proxy setup automatically.&lt;/p&gt;

&lt;h3&gt;
  
  
  Prerequisites
&lt;/h3&gt;

&lt;p&gt;Before we start, make sure you have:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://docs.astral.sh/uv/" rel="noopener noreferrer"&gt;uv&lt;/a&gt; package manager installed&lt;/li&gt;
&lt;li&gt;An OpenRouter API key (&lt;a href="https://openrouter.ai/keys" rel="noopener noreferrer"&gt;get one here&lt;/a&gt;)&lt;/li&gt;
&lt;li&gt;VSCode with the GitHub Copilot extension&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Installation
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Clone the repository:&lt;/strong&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;   git clone https://github.com/bascodes/copilot-ollama.git
   &lt;span class="nb"&gt;cd &lt;/span&gt;copilot-ollama
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Set your OpenRouter API key:&lt;/strong&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;   &lt;span class="nb"&gt;export &lt;/span&gt;&lt;span class="nv"&gt;OPENROUTER_API_KEY&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;your_openrouter_api_key_here
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Start the proxy servers:&lt;/strong&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;   ./run.sh
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This single command starts both proxy servers and handles all the configuration.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Configure VSCode:&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Open VSCode settings&lt;/li&gt;
&lt;li&gt;Set &lt;code&gt;github.copilot.chat.byok.ollamaEndpoint&lt;/code&gt; to &lt;code&gt;http://localhost:11434&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;Click "Manage Models" → Select "Ollama"&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Start coding!&lt;/strong&gt; 🎉&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Your OpenRouter models are now available in Copilot Agent Mode with full tool calling support.&lt;/p&gt;

&lt;h2&gt;
  
  
  Customizing Available Models
&lt;/h2&gt;

&lt;p&gt;The proxy comes with sensible defaults, but you can easily customize which models are available by editing the &lt;code&gt;config.yaml&lt;/code&gt; file:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;model_list&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;model_name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;claude-3-sonnet&lt;/span&gt;  &lt;span class="c1"&gt;# Name that appears in VSCode&lt;/span&gt;
    &lt;span class="na"&gt;litellm_params&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="na"&gt;model&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;openrouter/anthropic/claude-3-sonnet&lt;/span&gt;  &lt;span class="c1"&gt;# Actual OpenRouter model&lt;/span&gt;

  &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;model_name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;gpt-4-turbo&lt;/span&gt;
    &lt;span class="na"&gt;litellm_params&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="na"&gt;model&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;openrouter/openai/gpt-4-turbo&lt;/span&gt;

  &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;model_name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;kimi-k2&lt;/span&gt;
    &lt;span class="na"&gt;litellm_params&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="na"&gt;model&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;openrouter/moonshotai/kimi-k2&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Popular Models to Try
&lt;/h2&gt;

&lt;p&gt;Here are some excellent models to experiment with:&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;OpenRouter Path&lt;/th&gt;
&lt;th&gt;Best For&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Claude 3 Sonnet&lt;/td&gt;
&lt;td&gt;&lt;code&gt;openrouter/anthropic/claude-3-sonnet&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;Code generation and reasoning&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;GPT-4 Turbo&lt;/td&gt;
&lt;td&gt;&lt;code&gt;openrouter/openai/gpt-4-turbo&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;Latest OpenAI capabilities&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Mixtral 8x7B&lt;/td&gt;
&lt;td&gt;&lt;code&gt;openrouter/mistralai/mixtral-8x7b-instruct&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;Fast open-source model&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Llama 3 70B&lt;/td&gt;
&lt;td&gt;&lt;code&gt;openrouter/meta-llama/llama-3-70b-instruct&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;Meta's powerful open model&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;h2&gt;
  
  
  Why This Matters
&lt;/h2&gt;

&lt;p&gt;This solution opens up exciting possibilities:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Cost Control&lt;/strong&gt;: Pay per use instead of monthly subscriptions&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Model Diversity&lt;/strong&gt;: Access to cutting-edge models from multiple providers&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Full Agent Mode&lt;/strong&gt;: Complete tool calling and function support&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Local Control&lt;/strong&gt;: Everything runs locally, maintaining privacy&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Technical Details
&lt;/h2&gt;

&lt;p&gt;For those interested in the implementation details:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;The proxy uses &lt;a href="https://docs.litellm.ai/docs/simple_proxy" rel="noopener noreferrer"&gt;LiteLLM&lt;/a&gt; for OpenAI-compatible proxying&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/CNSeniorious000/oai2ollama" rel="noopener noreferrer"&gt;oai2ollama&lt;/a&gt; handles Ollama API compatibility&lt;/li&gt;
&lt;li&gt;Tool calling metadata is preserved throughout the proxy chain&lt;/li&gt;
&lt;li&gt;The solution works around VSCode's current limitation of only supporting Ollama endpoints for custom models&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Looking Forward
&lt;/h2&gt;

&lt;p&gt;There's an ongoing discussion about enabling custom API endpoints directly in Copilot: &lt;a href="https://github.com/microsoft/vscode-copilot-release/issues/7518" rel="noopener noreferrer"&gt;microsoft/vscode-copilot-release#7518&lt;/a&gt;. Once that's implemented, this workaround won't be necessary.&lt;/p&gt;

&lt;p&gt;However, until then, this proxy solution provides a robust way to unlock the full potential of GitHub Copilot with your favorite AI models.&lt;/p&gt;

&lt;p&gt;The restrictions of the Copilot API can be found in the &lt;a href="https://github.com/microsoft/vscode-copilot-chat/blob/132714b7b9ee6e05d2fe3c46c7dc738764473763/src/extension/conversation/vscode-node/languageModelAccess.ts#L162" rel="noopener noreferrer"&gt;VSCode Copilot source code&lt;/a&gt;, which is where I discovered the Ollama endpoint configuration option.&lt;/p&gt;

&lt;h2&gt;
  
  
  Get Started Today
&lt;/h2&gt;

&lt;p&gt;Ready to supercharge your coding experience? Check out the &lt;a href="https://github.com/bascodes/copilot-ollama" rel="noopener noreferrer"&gt;copilot-ollama repository&lt;/a&gt; and start experimenting with powerful AI models in GitHub Copilot's Agent Mode.&lt;/p&gt;

</description>
      <category>ai</category>
      <category>vscode</category>
      <category>vibecoding</category>
    </item>
    <item>
      <title>Vibe Coding a VSCode Extension</title>
      <dc:creator>Bas Steins</dc:creator>
      <pubDate>Fri, 11 Jul 2025 16:23:17 +0000</pubDate>
      <link>https://forem.com/bascodes/vibe-coding-a-vscode-extension-4mj6</link>
      <guid>https://forem.com/bascodes/vibe-coding-a-vscode-extension-4mj6</guid>
      <description>&lt;h1&gt;
  
  
  Building a VSCode Focus Extension: An AI-Assisted Coding Journey
&lt;/h1&gt;

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

&lt;p&gt;Recently, I stumbled upon a &lt;a href="https://x.com/willmcgugan/status/1943041592891421053" rel="noopener noreferrer"&gt;tweet&lt;/a&gt; by Will McGugan that caught my attention. The tweet showcased &lt;a href="https://ia.net/writer" rel="noopener noreferrer"&gt;iA Writer&lt;/a&gt;'s focus function—a clever feature that highlights the current "block" (or paragraph) while dimming everything else around it.&lt;/p&gt;

&lt;p&gt;Since I'd never tackled VSCode extension development before, this seemed like the perfect opportunity for some experimental "vibe coding." The concept was simple enough: create something similar for code editors, but instead of paragraphs, focus on code blocks and symbol hierarchies.&lt;/p&gt;

&lt;h2&gt;
  
  
  tl;dr
&lt;/h2&gt;

&lt;p&gt;I built a VSCode extension that dims code based on cursor location using AI assistance. Key takeaways: Used "meta-prompting" (AI helping write prompts for AI), spent ~$0.50 for 291 lines of code, discovered the &lt;code&gt;FoldingRangeProvider&lt;/code&gt; API, and learned that AI excels at boilerplate but struggles with integration challenges. The extension works by leveraging &lt;code&gt;DocumentSymbolProvider&lt;/code&gt; to create progressive dimming effects based on symbol hierarchy.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Meta-Prompt Approach
&lt;/h2&gt;

&lt;p&gt;Rather than diving straight into code, I decided to craft a comprehensive prompt first. Eventually, ChatGPT came up with this prompt:&lt;/p&gt;

&lt;p&gt;&amp;lt; BEGIN OF PROMPT &amp;gt;&lt;br&gt;
&lt;strong&gt;Prompt:&lt;/strong&gt;&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Build a Visual Studio Code extension named &lt;strong&gt;"VSCode Focus"&lt;/strong&gt; that enhances code readability by dynamically dimming unrelated code based on the cursor’s location in the document's symbol hierarchy. The extension should implement the following behavior:&lt;/p&gt;
&lt;/blockquote&gt;


&lt;h3&gt;
  
  
  🔍 &lt;strong&gt;Behavior:&lt;/strong&gt;
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;&lt;strong&gt;Symbol Hierarchy Detection&lt;/strong&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;ul&gt;
&lt;li&gt;Use the &lt;code&gt;DocumentSymbolProvider&lt;/code&gt; to retrieve the hierarchical structure of the open document.&lt;/li&gt;
&lt;li&gt;Parse the symbol tree to determine which symbols &lt;strong&gt;contain the current cursor position&lt;/strong&gt;.&lt;/li&gt;
&lt;li&gt;Identify the &lt;strong&gt;full path of nested symbols&lt;/strong&gt; from the outermost to the innermost level where the cursor resides.&lt;/li&gt;
&lt;/ul&gt;

&lt;ol&gt;
&lt;li&gt;&lt;strong&gt;Dynamic Opacity Calculation&lt;/strong&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;Apply a &lt;strong&gt;progressive dimming effect&lt;/strong&gt;:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Innermost symbol (cursor location):&lt;/strong&gt; 100% opacity (no dimming).&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Each parent level:&lt;/strong&gt; Reduce opacity by a configurable &lt;code&gt;opacityIncrement&lt;/code&gt;.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Code outside the symbol hierarchy:&lt;/strong&gt; Dimmed to a configurable &lt;code&gt;minimumOpacity&lt;/code&gt;.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;ol&gt;
&lt;li&gt;&lt;strong&gt;Optional Block Support&lt;/strong&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;ul&gt;
&lt;li&gt;If &lt;code&gt;vscode-focus.includeBlocks&lt;/code&gt; is &lt;code&gt;true&lt;/code&gt;, include blocks like &lt;code&gt;if&lt;/code&gt;, &lt;code&gt;while&lt;/code&gt;, &lt;code&gt;for&lt;/code&gt;, &lt;code&gt;switch&lt;/code&gt;, etc., in the hierarchy analysis using AST or custom parsing.&lt;/li&gt;
&lt;/ul&gt;

&lt;ol&gt;
&lt;li&gt;&lt;strong&gt;Live Updates&lt;/strong&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;ul&gt;
&lt;li&gt;Automatically update dimming effects as the cursor moves or the file content changes.&lt;/li&gt;
&lt;/ul&gt;


&lt;h3&gt;
  
  
  ⚙️ &lt;strong&gt;Configuration (via Settings UI):&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;Register the following settings under &lt;code&gt;vscode-focus&lt;/code&gt;:&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;"contributes"&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;"configuration"&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;"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;"VSCode Focus"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"properties"&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;"vscode-focus.enabled"&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;"boolean"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"default"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;true&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;"Enable/disable the focus highlighting effect."&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;"vscode-focus.minimumOpacity"&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;"number"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"default"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mf"&gt;0.1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"minimum"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mf"&gt;0.01&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"maximum"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mf"&gt;0.9&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;"Minimum opacity for the outermost dimmed code."&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;"vscode-focus.opacityIncrement"&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;"number"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"default"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mf"&gt;0.2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"minimum"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mf"&gt;0.05&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"maximum"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mf"&gt;0.5&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;"Opacity increment per hierarchy level."&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;"vscode-focus.includeBlocks"&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;"boolean"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"default"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;false&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;"Include control flow blocks like 'if', 'while', etc., in focus detection."&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;h3&gt;
  
  
  🎨 &lt;strong&gt;Implementation Notes:&lt;/strong&gt;
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Use the &lt;code&gt;TextEditorDecorationType&lt;/code&gt; API to apply dimming styles to ranges.&lt;/li&gt;
&lt;li&gt;Use debounce when handling cursor change or document edits for performance.&lt;/li&gt;
&lt;li&gt;Respect multiple cursors but apply dimming based on the &lt;strong&gt;first/main selection&lt;/strong&gt;.&lt;/li&gt;
&lt;li&gt;Provide a command &lt;code&gt;Toggle VSCode Focus&lt;/code&gt; to quickly enable/disable the effect.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&amp;lt; END OF PROMPT &amp;gt;&lt;/p&gt;

&lt;p&gt;As you can see, this prompt was itself generated by an LLM. After several iterations with ChatGPT (gpt-3.5), it produced this fairly comprehensive specification. I'm still debating whether to call this approach "vibe prompting" or "meta vibe coding"—but whatever the name, it felt like a natural way to bridge the gap between a vague idea and executable requirements.&lt;/p&gt;

&lt;h2&gt;
  
  
  From Vision to Specification
&lt;/h2&gt;

&lt;p&gt;The inputs I fed into ChatGPT were refreshingly simple: a screenshot from a similar extension and some ASCII art sketching out my vision. &lt;/p&gt;

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

&lt;p&gt;And this ASCII art that captured what I had in mind:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;// hierarchy 1 (inactive)
    LEVEL 1             60% DIM   = OPACITY 40%
    LEVEL 1             60% DIM   = OPACITY 40%

// hierarchy 2 (the active hierarchy)
    LEVEL 1             60% DIM   = OPACITY 40%
    LEVEL 2            40% DIM   = OPACITY 60%
        LEVEL 3        20% DIM   = OPACITY 80%
        LEVEL 3        20% DIM   = OPACITY 80%
            LEVEL 4    NO DIM    = OPACITY 100%  ← Cursor is here
            LEVEL 4    NO DIM    = OPACITY 100%

// hierarchy 3 (inactive)
    LEVEL 1             60% DIM   = OPACITY 40%
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The concept was straightforward: create a gradual dimming effect where the current code context (method, class, namespace) remains fully visible, while surrounding code fades progressively based on how far removed it is from the cursor's current location.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Development Experience
&lt;/h2&gt;

&lt;p&gt;Armed with this detailed prompt, I put it to work with both GitHub Copilot and Claude Sonnet 4. The results were... educational.&lt;/p&gt;

&lt;h3&gt;
  
  
  Getting Started: The Activation Struggle
&lt;/h3&gt;

&lt;p&gt;The initial setup was surprisingly smooth—both AI assistants generated reasonable starting code that followed the specification. However, getting the extension to actually activate proved trickier than expected. It took several "still not working" follow-up prompts before the code became truly functional. There's something humbling about watching an AI struggle with the same activation issues that trip up human developers.&lt;/p&gt;

&lt;h3&gt;
  
  
  The Mess Factor
&lt;/h3&gt;

&lt;p&gt;During development, Copilot developed some interesting habits. It generated numerous test files that weren't actually needed, then forgot to configure the TypeScript compiler to ignore them. This created a cascade of build errors that took time to untangle. Even more amusing was its tendency to create an "incredible amount of markdown files"—apparently its way of keeping notes on the development process. These digital breadcrumbs painted a picture of an AI trying to maintain context across a complex task.&lt;/p&gt;

&lt;h3&gt;
  
  
  The Dimming Logic
&lt;/h3&gt;

&lt;p&gt;Like an intern, the AI initially struggled with the core logic of applying the dimming effect. It got the logic right in of of the first prompts, but then applied the rendering logic from the inside (deepest symbol level) to the outside (outermost symbol level). While that sounds logical, the result was that the later applied dimming effects would override the earlier ones. And since symbols can nest deeply, this led to messed up visual results.&lt;/p&gt;

&lt;h3&gt;
  
  
  Technical Discoveries
&lt;/h3&gt;

&lt;p&gt;From an implementation standpoint, the AI made some smart architectural choices. As expected from the original prompt, it leveraged the &lt;code&gt;DocumentSymbolProvider&lt;/code&gt;—essentially tapping into the Language Server Protocol's understanding of code structure. This was the obvious foundation for any symbol-hierarchy-based dimming system.&lt;/p&gt;

&lt;p&gt;The more interesting development came when I pushed to extend the dimming beyond just symbols (classes, functions, etc.) to include logical blocks like &lt;code&gt;if&lt;/code&gt;, &lt;code&gt;for&lt;/code&gt;, and &lt;code&gt;switch&lt;/code&gt; statements. Copilot suggested investigating the &lt;code&gt;FoldingRangeProvider&lt;/code&gt;, which was completely new to me. This was genuinely insightful—the folding provider already understands code structure in a way that could complement symbol analysis. Unfortunately, despite the solid theoretical foundation, we never quite got this extended functionality working reliably.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Economics of AI-Assisted Development
&lt;/h2&gt;

&lt;p&gt;Running this experiment provided some interesting data points on the practical costs of AI-assisted coding.&lt;/p&gt;

&lt;p&gt;I kept everything within a single session, which meant that at some point the conversation history got compressed to manage context limits. According to the AI's own accounting, the entire project consumed roughly 60,000 input tokens and 20,000 output tokens—translating to about $0.50 in total costs.&lt;/p&gt;

&lt;p&gt;The final extension weighs in at 291 lines of code, which works out to approximately 0.17 cents per line. I'm not sure this metric means much in isolation, but it's an interesting data point for anyone thinking about the economics of AI-assisted development. Of course, this doesn't account for the value of learning, experimentation, or the time saved compared to building from scratch.&lt;/p&gt;

&lt;h2&gt;
  
  
  Reflections
&lt;/h2&gt;

&lt;p&gt;This experiment highlighted both the potential and limitations of current AI coding assistants. They excel at generating boilerplate, suggesting architectural patterns, and even discovering APIs you might not know about. But they still struggle with the integration challenges that often make or break real-world projects.&lt;/p&gt;

&lt;p&gt;The meta-prompting approach—using AI to help craft better specifications—feels like it has real potential. Starting with a well-structured prompt led to much better initial code than my usual approach of jumping straight into implementation details.&lt;/p&gt;

&lt;p&gt;Most importantly, this wasn't just about building a VSCode extension. It was about exploring a new way of working with AI tools, treating them as collaborative partners in both the design and implementation phases of software development.&lt;/p&gt;

</description>
      <category>vscode</category>
      <category>typescript</category>
      <category>vibecoding</category>
    </item>
    <item>
      <title>When the Internet Melted Down: Cloudflare’s Outage and the Magic of Durable Objects</title>
      <dc:creator>Bas Steins</dc:creator>
      <pubDate>Fri, 13 Jun 2025 14:30:52 +0000</pubDate>
      <link>https://forem.com/bascodes/when-the-internet-melted-down-cloudflares-outage-and-the-magic-of-durable-objects-1i9h</link>
      <guid>https://forem.com/bascodes/when-the-internet-melted-down-cloudflares-outage-and-the-magic-of-durable-objects-1i9h</guid>
      <description>&lt;p&gt;If you were online yesterday, June 12, 2025, you might have noticed things got a little… chaotic. Cloudflare, the superhero of internet infrastructure, hit a snag that left a colorful mess (pun intended—check out that awesome image above!) across the web. Let’s dive into what happened during this 148-minute outage, why it mattered, and take a deeper look at the fascinating tech behind it—Durable Objects.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Outage That Shook the Web
&lt;/h2&gt;

&lt;p&gt;Yesterday, Cloudflare’s lights flickered, and it wasn’t just a minor glitch. For 148 minutes (that’s 2 hours and 28 minutes, to be exact), services like Workers KV, WARP, Access, and even parts of the Cloudflare Dashboard went dark. This wasn’t a small hiccup—Cloudflare handles over 25 million HTTP requests per second and boasts a network spanning 330 cities across 125 countries. When it stumbles, the internet feels it.&lt;/p&gt;

&lt;p&gt;The culprit? A failure in the underlying storage infrastructure for Workers KV, a key component for many Cloudflare services. Workers KV is designed as a “coreless” service, meaning it should run independently across Cloudflare’s global data centers with no single point of failure. However, it relies on a central data store for a “source of truth.” When that store—tied to Google Cloud—went down, it triggered a cascading effect. Yep, Google Cloud’s outage yesterday amplified the chaos, impacting not just Cloudflare but the countless websites and apps depending on it for CDN and web firewall services.&lt;/p&gt;

&lt;p&gt;Cloudflare’s CTO, Dane Knecht, owned up to it, promising a detailed postmortem (which they’ve already started drafting—kudos for transparency!). The outage wasn’t just a tech fail; it sparked a bigger debate about relying on hyperscalers, a point DHH hammered home in his own X posts about returning to bare metal.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why This Matters
&lt;/h2&gt;

&lt;p&gt;With Cloudflare powering a huge chunk of the internet, this outage had real-world impacts. Teams worldwide scrambled as their websites lagged or went offline. The dependency on third-party providers like Google Cloud raised eyebrows—why would a company with 330 data centers lean on someone else’s infrastructure? Bas speculates it’s a trade-off: Cloudflare’s all-in on its Workers platform and Durable Objects, but building a fully independent distributed file system might stretch their engineering resources thin. Fair point! This incident is a wake-up call to balance convenience with resilience, especially when the internet’s original DARPA design aimed to survive nuclear strikes.&lt;/p&gt;

&lt;h2&gt;
  
  
  Diving into Durable Objects: The Tech Behind the Scenes
&lt;/h2&gt;

&lt;p&gt;  &lt;iframe src="https://www.youtube.com/embed/C5-741uQPVU"&gt;
  &lt;/iframe&gt;
&lt;/p&gt;

&lt;p&gt;Now, let’s geek out a bit! The YouTube video gives us a great starting point to unpack Durable Objects, the innovative tech at the heart of this outage. These are Cloudflare’s secret sauce for building stateful serverless applications, and they’re pretty cool once you get under the hood.&lt;/p&gt;

&lt;h3&gt;
  
  
  What Are Durable Objects?
&lt;/h3&gt;

&lt;p&gt;Durable Objects are a compute-with-storage building block in Cloudflare’s serverless ecosystem. Unlike traditional serverless functions that are stateless (they forget everything after each run), Durable Objects let you keep state—think of them as persistent JavaScript objects that stick around and can be accessed anywhere in Cloudflare’s network. They run on V8 isolates, the same engine powering Google Chrome, with each isolate acting like a browser tab—isolated but capable of holding data.&lt;/p&gt;

&lt;h3&gt;
  
  
  How Do They Work?
&lt;/h3&gt;

&lt;p&gt;Here’s the magic: when you define a Durable Object in your code, it looks like a regular JavaScript class. But Cloudflare handles the heavy lifting—spinning it up, persisting its state, and syncing it across their global network. Each Durable Object is tied to a specific location, and synchronization ensures consistency. This is where things get interesting (and a bit tricky). The persistence and syncing rely on underlying storage, which, in this case, looped back to Google Cloud. When that link broke, the whole chain faltered.&lt;/p&gt;

&lt;h3&gt;
  
  
  Durable Objects vs. D1
&lt;/h3&gt;

&lt;p&gt;Cloudflare also offers D1, a serverless SQLite database built on Durable Objects. D1 is great for relational data but isn’t colocated with your application code, which can add latency. Durable Objects, on the other hand, give you low-level control with embedded SQLite, perfect for distributed systems. The trade-off? You might need to build custom database tools, unlike D1’s out-of-the-box features. It’s a choose-your-own-adventure scenario based on your app’s needs!&lt;/p&gt;

&lt;h3&gt;
  
  
  The Zero Cold Start Promise
&lt;/h3&gt;

&lt;p&gt;One perk of Durable Objects is their near-zero cold start times. Since they load during the TLS handshake, your code is ready to roll almost instantly—unlike some serverless platforms (cough, AWS Lambda, cough) where cold starts can slow things down. However, if a Durable Object isn’t busy, it might get evicted from memory, making in-memory caching less useful unless it’s handling heavy traffic.&lt;/p&gt;

&lt;h2&gt;
  
  
  Lessons Learned and Looking Ahead
&lt;/h2&gt;

&lt;p&gt;Cloudflare’s response was solid—frequent status updates and a commitment to fix the root cause. Their postmortem will likely dive into decoupling from upstream dependencies like Google Cloud, a move that could bolster resilience. For developers, this is a nudge to weigh the pros and cons of third-party services. Want scalability and zero cold starts? Great! Just don’t put all your eggs in one basket.&lt;/p&gt;

&lt;p&gt;As for Durable Objects, they’re a game-changer for stateful serverless apps, especially with AI agents and distributed systems. But this outage highlights the need for redundancy in their storage layer. Maybe we’ll see Cloudflare roll out a homegrown solution—fingers crossed!&lt;/p&gt;

&lt;h2&gt;
  
  
  Wrap-Up
&lt;/h2&gt;

&lt;p&gt;Yesterday’s Cloudflare outage was a messy but educational moment for the internet. It showcased the power and pitfalls of modern infrastructure, with Durable Objects playing a starring role. Whether you’re a developer or just a curious soul, it’s a reminder to build with resilience in mind. Got thoughts? Drop them below—I’d love to chat! And hey, if you need more details, I can always dig deeper with a search. Until next time, keep exploring the tech frontier!&lt;/p&gt;

</description>
      <category>cloudcomputing</category>
    </item>
    <item>
      <title>This Week In Python</title>
      <dc:creator>Bas Steins</dc:creator>
      <pubDate>Fri, 13 Jun 2025 13:44:07 +0000</pubDate>
      <link>https://forem.com/bascodes/this-week-in-python-59o2</link>
      <guid>https://forem.com/bascodes/this-week-in-python-59o2</guid>
      <description>&lt;p&gt;&lt;strong&gt;Fri, June 13, 2025&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;This Week in Python is a concise reading list about what happened in the past week in the Python universe.&lt;/p&gt;

&lt;h2&gt;
  
  
  Python Articles
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://sergiolema.dev/2025/06/09/publish-a-python-wheel-to-gcp-artifact-registry-with-poetry/" rel="noopener noreferrer"&gt;Publish a Python Wheel to GCP Artifact Registry with Poetry&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://bui.app/the-missing-manual-for-signals-state-management-for-python-developers/" rel="noopener noreferrer"&gt;The Missing Manual for Signals: State Management for Python Developers&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://utcc.utoronto.ca/~cks/space/blog/python/ArgparseAndNestedGroups" rel="noopener noreferrer"&gt;Python argparse has a limitation on argument groups that makes me sad&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://astoeffelbauer.quarto.pub/blog/posts/modern-python/" rel="noopener noreferrer"&gt;Writing Modern Python Code&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://tonybaloney.github.io/posts/python-match-statement.html" rel="noopener noreferrer"&gt;Using the Python match statement&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Projects
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://github.com/fail2ban/fail2ban" rel="noopener noreferrer"&gt;fail2ban&lt;/a&gt; – Daemon to ban hosts that cause multiple authentication errors&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/autoscrape-labs/pydoll" rel="noopener noreferrer"&gt;pydoll&lt;/a&gt; – library for automating chromium-based browsers without a WebDriver&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/hejhdiss/pcl" rel="noopener noreferrer"&gt;pcl&lt;/a&gt; – minimal proof-of-concept compiler and runner for PCL files, which combine embedded C and Python code into a single source file&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/paiml/depyler" rel="noopener noreferrer"&gt;depyler&lt;/a&gt; – Compiles Python to Rust&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/getmoto/moto" rel="noopener noreferrer"&gt;moto&lt;/a&gt; – library that allows you to easily mock out tests based on AWS infrastructure&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>python</category>
      <category>thisweekinpython</category>
    </item>
    <item>
      <title>This Week In Python</title>
      <dc:creator>Bas Steins</dc:creator>
      <pubDate>Fri, 06 Jun 2025 17:21:35 +0000</pubDate>
      <link>https://forem.com/bascodes/this-week-in-python-1ij0</link>
      <guid>https://forem.com/bascodes/this-week-in-python-1ij0</guid>
      <description>&lt;p&gt;&lt;strong&gt;Fri, June 06, 2025&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;This Week in Python is a concise reading list about what happened in the past week in the Python universe.&lt;/p&gt;

&lt;h2&gt;
  
  
  Python Articles
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://blog.pamelafox.org/2025/06/teaching-python-with-codespaces.html" rel="noopener noreferrer"&gt;Teaching Python with Codespaces&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://fromscratchcode.com/blog/how-local-variables-work-in-python-bytecode/" rel="noopener noreferrer"&gt;How local variables work in Python bytecode&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.stephendiehl.com/posts/smt_and_mcp_solvers/" rel="noopener noreferrer"&gt;Interfacing MCP with Combinatorial, Convex, and SMT Solvers&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://lwn.net/Articles/1020576/" rel="noopener noreferrer"&gt;Recent disruptive changes from Setuptools&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://hugovk.dev/blog/2025/peps-and-co/" rel="noopener noreferrer"&gt;PEPs &amp;amp; Co.&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Projects
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://github.com/wey-gu/py-pglite" rel="noopener noreferrer"&gt;py-pglite&lt;/a&gt; – Test your app with Postgres just as lite as SQLite – by @wey_gu&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/deepankarm/pyleak" rel="noopener noreferrer"&gt;pyleak&lt;/a&gt; – Detect leaked asyncio tasks, threads, and event loop blocking in Python – by @_deepankarm_&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/patrick-kidger/patdb" rel="noopener noreferrer"&gt;patdb&lt;/a&gt; – A snappy + easy + pretty TUI debugger for Python – by @PatrickKidger&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/intellectronica/ez-mcp" rel="noopener noreferrer"&gt;ez-mcp&lt;/a&gt; – The easiest path to getting an MCP server going – by @intellectronica&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/duriantaco/skylos" rel="noopener noreferrer"&gt;skylos&lt;/a&gt; – static analysis tool for Python codebases&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>python</category>
      <category>thisweekinpython</category>
    </item>
    <item>
      <title>This Week In Python</title>
      <dc:creator>Bas Steins</dc:creator>
      <pubDate>Fri, 23 May 2025 15:22:07 +0000</pubDate>
      <link>https://forem.com/bascodes/this-week-in-python-jla</link>
      <guid>https://forem.com/bascodes/this-week-in-python-jla</guid>
      <description>&lt;p&gt;&lt;strong&gt;Fri, May 23, 2025&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;This Week in Python is a concise reading list about what happened in the past week in the Python universe.&lt;/p&gt;

&lt;h2&gt;
  
  
  Python Articles
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://www.pgrs.net/2025/05/22/visualizing-financial-data-with-duckdb-and-plotly/" rel="noopener noreferrer"&gt;Visualizing Financial Data with DuckDB And Plotly&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://pythonspeed.com/articles/pydantic-json-memory/" rel="noopener noreferrer"&gt;Loading Pydantic models from JSON without running out of memory&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://lwn.net/SubscriberLink/1020576/fcef31015579a9b1/" rel="noopener noreferrer"&gt;Recent disruptive changes from Setuptools&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://farlow.dev/2025/05/19/pokemon-on-github-profile" rel="noopener noreferrer"&gt;Running Pokemon Red on my GitHub Profile&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.llamaindex.ai/blog/python-tooling-at-scale-llamaindex-s-monorepo-overhaul" rel="noopener noreferrer"&gt;Python Tooling at Scale: LlamaIndex’s Monorepo Overhaul&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Projects
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://github.com/bytedance/deer-flow" rel="noopener noreferrer"&gt;deer-flow&lt;/a&gt; –  community-driven Deep Research framework&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/tuananh/hyper-mcp" rel="noopener noreferrer"&gt;hyper-mcp&lt;/a&gt; – fast, secure MCP server&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/kscalelabs/ksim-gym" rel="noopener noreferrer"&gt;ksim-gym&lt;/a&gt; – Making robots useful&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/ionelmc/pytest-benchmark" rel="noopener noreferrer"&gt;pytest-benchmark&lt;/a&gt; – pytest fixture for benchmarking code&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/lambda-science/modern-python-boilerplate" rel="noopener noreferrer"&gt;modern-python-boilerplate&lt;/a&gt; – python boilerplate for package developement – by @corentinm_py&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>python</category>
      <category>thisweekinpython</category>
    </item>
    <item>
      <title>This Week In Python</title>
      <dc:creator>Bas Steins</dc:creator>
      <pubDate>Fri, 16 May 2025 13:20:02 +0000</pubDate>
      <link>https://forem.com/bascodes/this-week-in-python-1ch5</link>
      <guid>https://forem.com/bascodes/this-week-in-python-1ch5</guid>
      <description>&lt;p&gt;&lt;strong&gt;Fri, May 16, 2025&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;This Week in Python is a concise reading list about what happened in the past week in the Python universe.&lt;/p&gt;

&lt;h2&gt;
  
  
  Python Articles
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://engineering.fb.com/2025/05/15/developer-tools/introducing-pyrefly-a-new-type-checker-and-ide-experience-for-python/" rel="noopener noreferrer"&gt;Introducing Pyrefly: A new type checker and IDE experience for Python&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://blog.est.im/2025/stdout-04" rel="noopener noreferrer"&gt;A single Python function for both async/sync&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://snarky.ca/unravelling-t-strings/" rel="noopener noreferrer"&gt;Unravelling t-strings&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://dynomight.net/numpy/" rel="noopener noreferrer"&gt;I don't like NumPy&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.mistys-internet.website/blog/blog/2025/05/13/the-database-row-that-didnt-exist/" rel="noopener noreferrer"&gt;The Database Row That Did and Didn't Exist&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Projects
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://github.com/cofob/autogenlib" rel="noopener noreferrer"&gt;autogenlib&lt;/a&gt; – Python library that automatically generates code on-the-fly using OpenAI's API&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/buiapp/reaktiv" rel="noopener noreferrer"&gt;reaktiv&lt;/a&gt; – Reactive Computation Graphs State Management for Python&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/NolanTrem/toller" rel="noopener noreferrer"&gt;toller&lt;/a&gt; – Lightweight Python library to make your async calls to microservices, etc. more robust and reliable&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/PaulleDemon/PyUIBuilder" rel="noopener noreferrer"&gt;PyUIBuilder&lt;/a&gt; – GUI builder for Tkinter, CustomTkinter, Kivy and PySide&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/D4Vinci/Scrapling" rel="noopener noreferrer"&gt;Scrapling&lt;/a&gt; – An undetectable, powerful, flexible, high-performance Python library to make Web Scraping Easy and Effortless&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>python</category>
      <category>thisweekinpython</category>
    </item>
    <item>
      <title>This Week In Python</title>
      <dc:creator>Bas Steins</dc:creator>
      <pubDate>Fri, 09 May 2025 14:32:46 +0000</pubDate>
      <link>https://forem.com/bascodes/this-week-in-python-3ckj</link>
      <guid>https://forem.com/bascodes/this-week-in-python-3ckj</guid>
      <description>&lt;p&gt;&lt;strong&gt;Fri, May 09, 2025&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;This Week in Python is a concise reading list about what happened in the past week in the Python universe.&lt;/p&gt;

&lt;h2&gt;
  
  
  Python Articles
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://akselmo.dev/posts/kate-python-lsp/" rel="noopener noreferrer"&gt;Kate and Python language server&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://judoscale.com/blog/scaling-python-task-queues" rel="noopener noreferrer"&gt;Scaling Python Task Queues Effectively&lt;/a&gt; &lt;/li&gt;
&lt;li&gt;
&lt;a href="https://www.phoronix.com/news/Python-3.14-Beta-1" rel="noopener noreferrer"&gt;Python 3.14 Reaches Beta With New Tail-Call Interpreter For Better Performance&lt;/a&gt; &lt;/li&gt;
&lt;li&gt;&lt;a href="https://blog.trailofbits.com/2025/05/01/making-pypis-test-suite-81-faster/" rel="noopener noreferrer"&gt;Making PyPI's test suite 81% faster&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://technicalwriting.dev/ml/gn.html" rel="noopener noreferrer"&gt;Automating code deletion with Gemini (and a little Python)&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Projects
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://github.com/astral-sh/ty" rel="noopener noreferrer"&gt;ty&lt;/a&gt; – extremely fast Python type checker and language server, written in Rust &lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/ernestofgonzalez/epub-utils" rel="noopener noreferrer"&gt;epub-utils&lt;/a&gt; – Python library and CLI tool for inspecting ePub from the terminal&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/ivanbelenky/us-routing" rel="noopener noreferrer"&gt;us-routing&lt;/a&gt; – us cached road graph, freeways, primary and secondary roads&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/leontrolski/tkintergalactic" rel="noopener noreferrer"&gt;tkintergalactic&lt;/a&gt; – Modern declarative (React-like) Tcl/Tk interface for Python&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/anonyxbiz/Blazeio" rel="noopener noreferrer"&gt;Blazeio&lt;/a&gt; – ultra-fast asynchronous web framework crafted for high-performance backend applications. Built on Python's asyncio&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>python</category>
      <category>thisweekinpython</category>
    </item>
    <item>
      <title>This Week In Python</title>
      <dc:creator>Bas Steins</dc:creator>
      <pubDate>Fri, 25 Apr 2025 18:16:54 +0000</pubDate>
      <link>https://forem.com/bascodes/this-week-in-python-873</link>
      <guid>https://forem.com/bascodes/this-week-in-python-873</guid>
      <description>&lt;p&gt;&lt;strong&gt;Fri, April 25, 2025&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;This Week in Python is a concise reading list about what happened in the past week in the Python universe.&lt;/p&gt;

&lt;h2&gt;
  
  
  Python Articles
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://davepeck.org/2025/04/11/pythons-new-t-strings/" rel="noopener noreferrer"&gt;Python's new t-strings&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://blog.edward-li.com/tech/advanced-python-features/" rel="noopener noreferrer"&gt;14 Advanced Python Features&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://ashishb.net/programming/python-in-production-2/" rel="noopener noreferrer"&gt;How to run Python in production&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://bitfieldconsulting.com/posts/go-vs-python" rel="noopener noreferrer"&gt;Go vs Python&lt;/a&gt; &lt;/li&gt;
&lt;li&gt;&lt;a href="https://log.schemescape.com/posts/diy/irc-server-in-python.html" rel="noopener noreferrer"&gt;Minimal IRC server from scratch in Python&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Projects
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://github.com/more-itertools/more-itertools" rel="noopener noreferrer"&gt;more-itertools&lt;/a&gt; – More routines for operating on iterables, beyond itertools&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/autokitteh/autokitteh" rel="noopener noreferrer"&gt;autokitteh&lt;/a&gt; – Durable workflow automation in just a few lines of code&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/hxu296/tariff" rel="noopener noreferrer"&gt;tariff&lt;/a&gt; – The GREATEST, most TREMENDOUS Python package that makes importing great again&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/Salaah01/django-action-triggers" rel="noopener noreferrer"&gt;django-action-triggers&lt;/a&gt; – Django library for asynchronously triggering actions in response to database changes&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/PrajwalVandana/maestro-cli" rel="noopener noreferrer"&gt;maestro-cli&lt;/a&gt; – command-line tool to play songs (or any audio, really) in the terminal&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>python</category>
      <category>thisweekinpython</category>
    </item>
    <item>
      <title>Cloudflare Dev Week 2025: Revolutionary Serverless</title>
      <dc:creator>Bas Steins</dc:creator>
      <pubDate>Sat, 12 Apr 2025 11:47:15 +0000</pubDate>
      <link>https://forem.com/bascodes/cloudflare-dev-week-2025-revolutionary-serverless-28c2</link>
      <guid>https://forem.com/bascodes/cloudflare-dev-week-2025-revolutionary-serverless-28c2</guid>
      <description>&lt;p&gt;Clouflare is an interesting case for cloud-native (for lack of a better word) software developers. They're still primarily known for their CDN only, and it seems that they slept through the whole serverless development thing that Azure, Google, and AWS is pushing. &lt;/p&gt;

&lt;p&gt;Nothing could be further from the truth. With workers, durable objects, serverless KV-stores and SQLite databses, you could build almost everything imagineable on their platform.&lt;/p&gt;

&lt;p&gt;This year, however, they're really doubling down on the developer experience. &lt;/p&gt;

&lt;p&gt;Here are the most impressive announcements Cloudflare made during their &lt;a href="https://blog.cloudflare.com/welcome-to-developer-week-2025/" rel="noopener noreferrer"&gt;Developer Week 2025&lt;/a&gt; event:&lt;/p&gt;

&lt;h3&gt;
  
  
  Full-Stack In A Single Worker
&lt;/h3&gt;

&lt;p&gt;With the support of static assets in Workers, you can now deploy a full-stack application in a single worker. Basically, this is an effort to merge Workers and Pages into a single product.&lt;/p&gt;

&lt;p&gt;Additionally, Workers now support popular frameworks such as React Router v7 (Remix), Astro, Hono, Vue.js, Nuxt, and SvelteKit, with upcoming support for Next.js, Angular, and SolidJS (SolidStart) expected in Q2 2025.&lt;/p&gt;

&lt;p&gt;The &lt;a href="https://blog.cloudflare.com/introducing-the-cloudflare-vite-plugin/" rel="noopener noreferrer"&gt;Vite plugin&lt;/a&gt;, which runs Vite’s development server within the Workers runtime, offering benefits like Hot Module Replacement alongside access to Workers-specific features.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://blog.cloudflare.com/full-stack-development-on-cloudflare-workers/" rel="noopener noreferrer"&gt;Blog Post&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  MySQL Support for Hyperdrive
&lt;/h3&gt;

&lt;p&gt;In another exciting development, Cloudflare now offers native MySQL support directly on the Workers platform. Thanks to Hyperdrive—a tool for managing stateful database connections in a stateless environment—developers can build globally distributed applications with direct MySQL connectivity, regardless of database hosting location. This breakthrough simplifies scaling, as Hyperdrive efficiently pools and caches connections, thereby reducing latency while optimizing performance for region-specific SQL databases. Moreover, improved Node.js compatibility means popular MySQL drivers like &lt;code&gt;mysql&lt;/code&gt; and &lt;code&gt;mysql2&lt;/code&gt; now work seamlessly, making it easier than ever for developers to migrate or extend their existing applications.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://blog.cloudflare.com/building-global-mysql-apps-with-cloudflare-workers-and-hyperdrive/" rel="noopener noreferrer"&gt;Blog Post&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Read Replicas for D1
&lt;/h3&gt;

&lt;p&gt;Improving database performance further, Cloudflare’s beta release of read replicas for D1—its managed SQLite database—targets enhanced scalability. By creating read-only copies of the primary database, the platform can offload read queries across multiple nodes. The direct result? Lower latency and higher throughput for applications that require the best possible performance for read-heavy workloads.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://blog.cloudflare.com/d1-read-replication-beta/" rel="noopener noreferrer"&gt;Blog Post&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Workflows
&lt;/h3&gt;

&lt;p&gt;Cloudflare is also expanding into the realm of orchestration with the general availability of its Workflows platform. This powerful feature allows developers to build and manage multi-step, durable processes that can handle complex scenarios like retries, delays, and error management. Seamlessly integrated with Workers, Workflows provide state management and offer a visual interface for designing and monitoring processes, making it easier to build resilient applications without the overhead of external orchestration tools.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://blog.cloudflare.com/workflows-ga-production-ready-durable-execution/" rel="noopener noreferrer"&gt;Blog Post&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Containers
&lt;/h3&gt;

&lt;p&gt;Perhaps the most game-changing announcement was the upcoming open beta for Cloudflare’s container platform—expected in June 2025. This new service enables developers to run containerized applications globally with minimal overhead. Imagine being able to run CLI tools, full Linux environments, or even port existing applications from other cloud providers without a complete rearchitecting effort. This initiative could usher Cloudflare into a broader range of use cases, firmly positioning them as a serious competitor in the serverless space.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://blog.cloudflare.com/cloudflare-containers-coming-2025/" rel="noopener noreferrer"&gt;Blog Post&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Secrets Store
&lt;/h3&gt;

&lt;p&gt;Managing sensitive data just got a whole lot easier. The beta release of Secrets Store offers a centralized, secure solution for handling API keys, tokens, and other credentials. With built-in role-based access control (RBAC), audit logging, and seamless integration via Wrangler, managing secrets becomes a breeze. This new offering is a nod to best practices in security and compliance, ensuring that development teams can focus on building great applications without worrying about secret management pitfalls.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://blog.cloudflare.com/secrets-store-beta/" rel="noopener noreferrer"&gt;Blog Post&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  AI
&lt;/h3&gt;

&lt;p&gt;Additionally, Cloudflare has upgraded its Agents SDK to better support AI agents using the Model Context Protocol (MCP). This update streamlines remote transport, authentication, and tool discovery, enabling AI agents to securely and efficiently interact with multiple MCP servers. By integrating with authentication providers like Stytch, Auth0, and WorkOS, Cloudflare ensures robust security while providing the scalability needed for complex AI workflows. With Durable Objects available in its free tier, Cloudflare now offers scalable, stateful storage solutions essential for modern AI applications.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://blog.cloudflare.com/building-ai-agents-with-mcp-authn-authz-and-durable-objects/" rel="noopener noreferrer"&gt;Blog Post&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  0.email
&lt;/h3&gt;

&lt;p&gt;In a surprising yet timely move, the one-day-old launch of 0.email—a complete email service running entirely on Cloudflare’s infrastructure—demonstrates just how far the platform has come. This project is a testament to Cloudflare’s commitment to challenging conventional service paradigms and pushing the limits of what’s possible at the edge.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://x.com/cmdhaus/status/1910746521542459620" rel="noopener noreferrer"&gt;Tweet&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Summary
&lt;/h2&gt;

&lt;p&gt;Cloudflare Developer Week 2025 could mark a turning point for the company, shifting its image from a niche CDN provider to a formidable player in the serverless landscape. By stripping away the heavy-handed legacy of traditional enterprise cloud offerings, Cloudflare has focused on delivering a modern, hassle-free platform that champions developer experience above all else. With robust support for full-stack deployment, advanced database integrations, powerful orchestration tools, and even containerization, Cloudflare is poised to disrupt the serverless space. For developers tired of the complexities and overhead of traditional microservices architectures and Kubernetes, Cloudflare's streamlined, developer-first approach is a breath of fresh air and the future of software development.&lt;/p&gt;

</description>
      <category>cloud</category>
      <category>webdev</category>
      <category>cloudflare</category>
    </item>
  </channel>
</rss>
