<?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: Matheus Guimaraes</title>
    <description>The latest articles on DEV Community by Matheus Guimaraes (@techwithmatheus).</description>
    <link>https://dev.to/techwithmatheus</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%2F990373%2Fc3282166-8fbe-4de0-ae95-edb54e59fc04.png</url>
      <title>DEV Community: Matheus Guimaraes</title>
      <link>https://dev.to/techwithmatheus</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/techwithmatheus"/>
    <language>en</language>
    <item>
      <title>AI in Games: Are We Drawing the Line in the Wrong Place?</title>
      <dc:creator>Matheus Guimaraes</dc:creator>
      <pubDate>Wed, 02 Sep 2026 14:10:01 +0000</pubDate>
      <link>https://dev.to/techwithmatheus/ai-in-games-are-we-drawing-the-line-in-the-wrong-place-706</link>
      <guid>https://dev.to/techwithmatheus/ai-in-games-are-we-drawing-the-line-in-the-wrong-place-706</guid>
      <description>&lt;p&gt;The games industry is going through an uncomfortable transition. Studios see the productivity gains AI may offer, while many players see almost any use of it as inherently bad. As a lifelong gamer who started his career as a game developer, I see that divide from both sides.&lt;/p&gt;

&lt;p&gt;I understand the reaction. People are worried about artists losing work, creative jobs being devalued and models being trained on work without permission. Those concerns certainly deserve careful consideration, but I also think the conversation has become far too binary with outright rejection often treated as the only acceptable position.&lt;/p&gt;

&lt;h2&gt;
  
  
  When any use becomes unacceptable
&lt;/h2&gt;

&lt;p&gt;The example that crystallised this for me was &lt;em&gt;Clair Obscur: Expedition 33&lt;/em&gt;. The &lt;a href="https://uk.pcmag.com/ai/162208/clair-obscur-expedition-33-stripped-of-a-game-of-the-year-award-because-of-ai" rel="noopener noreferrer"&gt;Indie Game Awards withdrew its Game of the Year and Debut Game awards&lt;/a&gt; after it emerged that generative AI had been used during production. The material appears to have been placeholder artwork that accidentally shipped and was later patched out.&lt;/p&gt;

&lt;p&gt;There is a disclosure issue. The awards had a clear rule, and the submission reportedly stated that no generative AI had been used so, ok, I understand it from the perspective of enforcing that rule.&lt;/p&gt;

&lt;p&gt;What I disagree with is the rule itself. Declaring a game ineligible because generative AI touched any part of production, regardless of how it was used, feels very extreme and, dare I say, very naive and counterproductive to me. It turns “AI was involved” into the entire judgement and ignores context, scale and impact.&lt;/p&gt;

&lt;h2&gt;
  
  
  We have seen this pattern before
&lt;/h2&gt;

&lt;p&gt;When Disney blended computer-generated environments with hand-drawn characters in &lt;em&gt;Beauty and the Beast&lt;/em&gt;, audiences marvelled. CGI transformed visual effects, and computer animation became an art form of its own. We did not judge those works by how many people might have recreated every frame by hand. In fact, &lt;em&gt;Toy Story&lt;/em&gt;, released in 1995 as the first fully computer-animated feature film, continues to be celebrated today.&lt;/p&gt;

&lt;p&gt;To me, AI is just another step in that long history of automation. Game development already depends on IDEs, automated testing, procedural generation, motion capture, physics engines and infrastructure that scales itself. All allow teams to do more. If replacing manual effort is the line we object to, where does that line begin?&lt;/p&gt;

&lt;p&gt;That is not to say that every use of AI is ethical, of course. Replacing an actor’s performance without consent is not the same as generating an environmental texture. Eliminating a creative team is not the same as helping one automate repetitive work. Training data, consent, attribution, disclosure and the treatment of workers matter.&lt;/p&gt;

&lt;p&gt;That is why I find blanket rejection, at the very least, unhelpful. It removes the nuance needed to tell responsible use from exploitative use.&lt;/p&gt;

&lt;h2&gt;
  
  
  Judge the outcome, and ask better questions
&lt;/h2&gt;

&lt;p&gt;As a gamer, I care most about the game: Is it good? Is it original? Does it move me?&lt;/p&gt;

&lt;p&gt;If we want to examine how it was made then we should go deeper than just “AI was used.” What was it used for? Did it replace credited work? Was source material used with permission? Did the studio mislead anyone? Did the tool help creators realise their vision, or flatten it?&lt;/p&gt;

&lt;p&gt;I know this is a topic that probably deserves a whole post in itself, but I also feel similarly about AI-generated art.&lt;/p&gt;

&lt;p&gt;Art communicates, provokes or makes us feel.&lt;/p&gt;

&lt;p&gt;The creation process can affect how we value a work. I personally struggle to appreciate works created by simply throwing paint at a canvas, for example, but my reaction to that process does not necessarily mean the result isn’t art. Similarly, I do not believe that using a prompt automatically prevents the result from being art, any more than using a camera, graphics tablet, image editor, particle system or CGI package does.&lt;/p&gt;

&lt;p&gt;My bet is that AI will become another ordinary part of how games are made and the current backlash is just a transitional state of mind while society works out the boundaries of a disruptive technology and adjusts to a new world.&lt;/p&gt;

&lt;p&gt;We should absolutely shape those boundaries, but I hope we shape them around consent, transparency and harm, not fear of the technology itself.&lt;/p&gt;

&lt;p&gt;Of course, that's just my perspective, not a universal answer. Where would you draw the line? Which uses of AI in game development do you consider acceptable, and which do you not? I would genuinely like to hear how players and developers see it.&lt;/p&gt;

</description>
      <category>ai</category>
      <category>gamedev</category>
      <category>ethics</category>
      <category>discuss</category>
    </item>
    <item>
      <title>Why Can't We Just Use Claude for Everything? Agent Creation vs. Agent Engineering</title>
      <dc:creator>Matheus Guimaraes</dc:creator>
      <pubDate>Tue, 18 Aug 2026 16:36:11 +0000</pubDate>
      <link>https://dev.to/aws/why-cant-we-just-use-claude-for-everything-agent-creation-vs-agent-engineering-5aaa</link>
      <guid>https://dev.to/aws/why-cant-we-just-use-claude-for-everything-agent-creation-vs-agent-engineering-5aaa</guid>
      <description>&lt;p&gt;Recently, I was talking to a friend who, much like the rest of the world, has started using AI extensively at work to create agents even though she's not a software developer or from a technical background.&lt;/p&gt;

&lt;p&gt;She has been experimenting with Claude a lot, building useful workflows for herself and her team, and getting increasingly excited about what these systems can do.&lt;/p&gt;

&lt;p&gt;At some point, our conversation moved onto the work I've been doing around agentic systems: agent architectures, context engineering, memory, orchestration, sub-agents and frameworks such as Strands Agents.&lt;/p&gt;

&lt;p&gt;And her reaction was:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Why do you need all of that? I'm already creating agents.&lt;/strong&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;"Great question", I thought to myself.&lt;/p&gt;

&lt;p&gt;And what made it particularly interesting was that I'd heard almost the same question from the opposite direction.&lt;/p&gt;

&lt;p&gt;After giving a talk about agentic architecture and building harnesses with Strands Agents SDK, a junior developer came up to me and asked:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;What's the point of all of this? Why can't we just use Claude for everything?&lt;/strong&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Two people approaching the subject from completely different directions had arrived at the same question.&lt;/p&gt;

&lt;p&gt;And I think that question exposes something important about where we are with agents today. We are using the same word &lt;strong&gt;"agent"&lt;/strong&gt; to describe two very different activities with very different use cases.&lt;/p&gt;

&lt;p&gt;The way I see it, there is a big difference between &lt;strong&gt;creating agents&lt;/strong&gt; and &lt;strong&gt;engineering agents&lt;/strong&gt;.&lt;/p&gt;




&lt;h2&gt;
  
  
  Agent Creation vs. Agent Engineering
&lt;/h2&gt;

&lt;p&gt;Applications such as Claude, ChatGPT, Amazon Quick and others increasingly allow people to create surprisingly sophisticated agentic workflows without building the underlying infrastructure themselves.&lt;/p&gt;

&lt;p&gt;There is still a learning curve, though. You need to provide instructions and give the system knowledge and context in a way that produces results that are within expectation (and, hopefully, without hallucinations!). You may also need to learn about tools, set up integrations, schedule work or even create subagents so multiple pieces of functionality can work together.&lt;/p&gt;

&lt;p&gt;From the user's perspective, they have created an agent. And indeed they have! But when a software engineer looks at the same system... they see something different.&lt;/p&gt;

&lt;p&gt;They see an application providing a highly abstracted, opinionated agent runtime operating as a black box. You have little control over how execution happens, how context is assembled and maintained, how the system scales, or even where memory lives, among other architectural concerns.&lt;/p&gt;

&lt;p&gt;As an application user, you are creating an agent &lt;strong&gt;inside somebody else's agentic architecture&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;And that's not a problem. In fact, this could be exactly what you need!&lt;/p&gt;

&lt;p&gt;Developers and software architects make trade-offs between abstraction and control all the time. We don't choose the lowest-level technology simply because it gives us the most control; we use abstractions because they remove decisions we don't want to make and complexity we don't need to own.&lt;/p&gt;

&lt;p&gt;The same principle applies here. If Claude gives you everything you need to create an agent, why &lt;em&gt;wouldn't&lt;/em&gt; you use it?&lt;/p&gt;

&lt;p&gt;As usual with system design, the important thing is understanding the trade-offs. The abstraction works because somebody else has made a set of architectural decisions for you. If those decisions suit your requirements, then awesome. If they don't, you may need to take ownership of some of them yourself.&lt;/p&gt;

&lt;p&gt;That's where I find the distinction between &lt;strong&gt;Agent Creation&lt;/strong&gt; and &lt;strong&gt;Agent Engineering&lt;/strong&gt; useful.&lt;/p&gt;

&lt;p&gt;For me, three things make that distinction particularly clear.&lt;/p&gt;




&lt;h2&gt;
  
  
  Is the agent a feature or a component?
&lt;/h2&gt;

&lt;p&gt;This is perhaps my favourite way of thinking about the distinction.&lt;/p&gt;

&lt;p&gt;Let's say I create an agent in Claude to research holidays for me. It knows my preferences, researches destinations, compares options and perhaps uses tools to build an itinerary. It could be incredibly sophisticated... but Claude is still the application. I go to Claude, interact through Claude's interface and rely on Claude's infrastructure to make everything work.&lt;/p&gt;

&lt;p&gt;My agent is a &lt;strong&gt;feature of an application I'm using&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;Now imagine I want to offer that same experience through my own travel website. A customer comes to my application and asks for a holiday; somewhere behind the scenes an agent researches flights and hotels, applies their preferences, interacts with booking systems and returns the result.&lt;/p&gt;

&lt;p&gt;The capability sounds almost identical, but architecturally something fundamental has changed. The agent is now a &lt;strong&gt;component of a system I'm building&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;Suddenly I need to decide where it runs, how my application communicates with it, how it scales, how it authenticates against other systems, what happens when it fails, how it fits into traditional application flows, and how I observe what it's doing. The AI is no longer the destination; it's now part of the system I'm responsible for.&lt;/p&gt;

&lt;p&gt;That's very clearly Agent Engineering.&lt;/p&gt;

&lt;p&gt;The point is really about ownership. If an agent is a feature of Claude or another application, you're limited, quite deliberately, to what that application allows you to do. If your requirements fit inside those boundaries, great. When they don't... you need another abstraction.&lt;/p&gt;




&lt;h2&gt;
  
  
  Do you need control over the economics?
&lt;/h2&gt;

&lt;p&gt;Another reason you might choose to engineer the agent is cost.&lt;/p&gt;

&lt;p&gt;There is a lot of conversation right now about just how many tokens agentic systems can consume, particularly as we build long-running workflows with large context windows, tool calls and multiple agents.&lt;/p&gt;

&lt;p&gt;Moving from Agent Creation to Agent Engineering doesn't automatically make any of this cheaper, by the way. Engineering has its own cost, and it would be rather ironic to spend £100,000 in developer time to save £500 in tokens.&lt;/p&gt;

&lt;p&gt;What engineering gives you is &lt;strong&gt;control&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;If you own the harness around your agents, architectural decisions become available that simply aren't exposed when you're operating inside somebody else's application.&lt;/p&gt;

&lt;p&gt;You can decide that one task doesn't need the full conversation history, cache an expensive result, retrieve memory only when it's relevant, summarize context between steps, or route simpler tasks to cheaper models.&lt;/p&gt;

&lt;p&gt;You can start treating context and tokens as resources that you deliberately engineer.&lt;/p&gt;

&lt;p&gt;There's a much larger conversation here around context engineering, but that's a story for another post. For now, the important point is that &lt;strong&gt;the abstraction determines which levers are available to you&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;If you don't need those levers, there's little value in taking responsibility for them. If the economics of your system mean you do, Agent Engineering gives you that control.&lt;/p&gt;




&lt;h2&gt;
  
  
  Do you need to own where your data goes?
&lt;/h2&gt;

&lt;p&gt;Then there is a question that tends to become important very quickly in enterprise environments: where does everything actually live?&lt;/p&gt;

&lt;p&gt;When I create an agent inside an application, I'm accepting that application's architecture and its mechanisms for handling context, state, memory, integrations and data. Again, that may be completely acceptable.&lt;/p&gt;

&lt;p&gt;But what if particular data cannot leave a certain environment? What if I need to know exactly where long-term memory is persisted, control which model receives which information, maintain my own audit trail, or guarantee that certain data never crosses a particular boundary?&lt;/p&gt;

&lt;p&gt;Now the black box really matters.&lt;/p&gt;

&lt;p&gt;This is partly a compliance question, partly a data ownership question and, yes, partly a vendor lock-in question. The more behaviour, knowledge and state I build around one application's abstractions, the more dependent I become on that platform's capabilities and constraints.&lt;/p&gt;

&lt;p&gt;But vendor lock-in isn't, by itself, a reason to engineer everything from scratch. We accept varying degrees of lock-in throughout modern software architecture because managed abstractions can provide enormous value.&lt;/p&gt;

&lt;p&gt;The question is simply whether that trade-off is acceptable &lt;strong&gt;for the requirements in front of you&lt;/strong&gt;.&lt;/p&gt;




&lt;h2&gt;
  
  
  So... Can't We Just Use Claude For Everything?
&lt;/h2&gt;

&lt;p&gt;A useful spreadsheet can eventually become an application, but that doesn't mean the spreadsheet was a mistake. It may have been exactly the right abstraction for the problem at the time, and it may even have helped us understand the problem well enough to know what was worth engineering later.&lt;/p&gt;

&lt;p&gt;I think Agent Creation and Agent Engineering should be seen in much the same way: not as levels on a maturity ladder, and certainly not as a journey where every agent should eventually become an engineered one, but as different architectural choices about how much of the underlying system we need to own. We might happily create an agent inside Claude for one task while engineering another from the ground up, perhaps even within the same system.&lt;/p&gt;

&lt;p&gt;Sometimes an agent created inside Claude, ChatGPT, Amazon Quick or another application will remain there because it does everything we need. Sometimes our requirements will mean taking ownership of the architecture ourselves and we'll find ourselves reaching for Strands Agents SDK or another agent harness.&lt;/p&gt;

&lt;p&gt;And perhaps the next time someone asks me, &lt;em&gt;"Why can't we just use Claude for everything?"&lt;/em&gt;, my answer will simply be...&lt;/p&gt;

&lt;p&gt;You can! For as long as its decisions are compatible with yours.**&lt;/p&gt;

</description>
      <category>ai</category>
      <category>agents</category>
      <category>architecture</category>
      <category>programming</category>
    </item>
    <item>
      <title>Understanding Async Programming</title>
      <dc:creator>Matheus Guimaraes</dc:creator>
      <pubDate>Mon, 17 Aug 2026 16:01:25 +0000</pubDate>
      <link>https://dev.to/aws/understanding-async-programming-4mei</link>
      <guid>https://dev.to/aws/understanding-async-programming-4mei</guid>
      <description>&lt;p&gt;Async programming, short for asynchronous programming, is one of those concepts that might sound intimidating at first but becomes surprisingly intuitive once you understand the problem it is trying to solve.&lt;/p&gt;

&lt;p&gt;And that problem is mostly waiting.&lt;/p&gt;

&lt;p&gt;Modern applications spend a lot of time waiting for things to happen. They wait for APIs to respond, databases to return queries, files to be read or written, and data to travel across a network. Async programming gives us a way to avoid blocking while that happens, allowing other useful work to make progress instead.&lt;/p&gt;

&lt;p&gt;In this post, I’ll cover the basic concepts behind async programming rather than focusing on a particular language. The exact implementation differs between languages and runtimes, but the underlying ideas are largely the same. So if you’re new to async, or have used async and await without ever being completely sure what they’re doing, this is a good place to start.&lt;/p&gt;

&lt;h2&gt;
  
  
  What is Async Programming?
&lt;/h2&gt;

&lt;p&gt;At its core, async programming allows your program to start an operation that may take some time and avoid blocking while it waits for that operation to complete.&lt;/p&gt;

&lt;p&gt;This contrasts with synchronous programming, where execution waits for an operation to finish before continuing past that point.&lt;/p&gt;

&lt;p&gt;Imagine you’re making an API call, a very common task in modern applications. Your application sends a request across the network and then has to wait for a response. Even if that response takes only a fraction of a second, that's a long time in computer terms.&lt;/p&gt;

&lt;p&gt;The important thing is that your application isn't necessarily doing useful computation during all that time. A lot of it is simply waiting for something external to happen.&lt;/p&gt;

&lt;p&gt;This is where async programming shines. Rather than blocking an execution resource while waiting for the API call to complete, asynchronous execution can allow other work to make progress and then continue the original operation when its result becomes available.&lt;/p&gt;

&lt;h2&gt;
  
  
  Async Doesn't Necessarily Mean Faster
&lt;/h2&gt;

&lt;p&gt;One of the most common misconceptions about async programming is that it's about improving performance. A lot of people think that using async makes their code run faster. However...&lt;/p&gt;

&lt;p&gt;Async does not necessarily make the operation itself any faster.&lt;/p&gt;

&lt;p&gt;Your API call might take exactly the same amount of time to complete whether you call it synchronously or asynchronously. What async changes is what your application can do while it waits. Instead of being blocked by that wait, it can potentially make progress on other work.&lt;/p&gt;

&lt;h2&gt;
  
  
  When is Async Programming Useful?
&lt;/h2&gt;

&lt;p&gt;There are three main benefits to using async programming:&lt;/p&gt;

&lt;p&gt;Improved throughput: Because your application doesn't have to block on one operation before making progress on other work, it can often handle more work over the same period of time. This is particularly valuable in applications such as web servers that may be handling many requests concurrently.&lt;br&gt;
Better resource utilization: Waiting for I/O doesn't necessarily require a thread to sit blocked until the operation completes. With asynchronous I/O, execution resources can potentially be used for other work while the application waits for the database, network, filesystem or another external resource.&lt;br&gt;
Better responsiveness: Async programming can also help applications remain responsive while longer-running operations are taking place. In a user interface, for example, you generally don't want the entire application to freeze while it waits for a network request or file operation to complete.&lt;/p&gt;

&lt;p&gt;The common thread between all three is the same: making better use of time that would otherwise be spent waiting.&lt;/p&gt;
&lt;h2&gt;
  
  
  Sync vs. Async: When to Use Each
&lt;/h2&gt;

&lt;p&gt;Async programming sounds great, but that doesn't mean everything should be asynchronous.&lt;/p&gt;

&lt;p&gt;The distinction becomes clearer when we think about I/O-bound and CPU-bound work.&lt;/p&gt;

&lt;p&gt;I/O-bound operations spend a significant amount of their time waiting for something outside the CPU: network requests, database calls, file operations and similar tasks. These are often excellent candidates for async programming because there is useful time to reclaim while the application waits.&lt;/p&gt;

&lt;p&gt;CPU-bound operations are different. If you're performing a heavy calculation, for example, the CPU is actively doing the work rather than waiting for something else to happen. Making that code asynchronous doesn't suddenly make the computation faster.&lt;/p&gt;

&lt;p&gt;CPU-bound work may instead benefit from parallelism, where computation is divided so that multiple pieces of work can execute at the same time, potentially across multiple CPU cores.&lt;/p&gt;

&lt;p&gt;Async programming can also introduce additional complexity and some runtime overhead, so there's little benefit in making code asynchronous simply for the sake of it. It is most useful when your application would otherwise spend meaningful time blocked waiting for I/O.&lt;/p&gt;

&lt;p&gt;Async Isn't the Same as Parallelism&lt;/p&gt;

&lt;p&gt;The distinction between async and parallelism is an important one. Async is primarily about allowing other work to make progress while something is waiting. Parallelism is about performing multiple pieces of work at the same time.&lt;/p&gt;

&lt;p&gt;And async doesn't necessarily mean multithreaded either. Different languages and runtimes implement asynchronous execution in different ways, so you shouldn't assume that an async operation means another thread is somewhere doing the work.&lt;/p&gt;

&lt;p&gt;This is why async can provide concurrency without necessarily providing parallelism: multiple operations can make progress over the same period of time without their code actually executing at the exact same moment.&lt;/p&gt;
&lt;h2&gt;
  
  
  How Does Async Work in Code?
&lt;/h2&gt;

&lt;p&gt;The exact mechanics vary between programming languages, but many modern languages provide the familiar async and await keywords to make asynchronous code easier to write and reason about.&lt;/p&gt;

&lt;p&gt;At a conceptual level, async identifies code that participates in asynchronous execution, while await marks a point where that code depends on the result of an asynchronous operation.&lt;/p&gt;

&lt;p&gt;If that result is already available, execution may simply continue. If it isn't, the function can yield rather than blocking there, allowing other work to make progress. Once the awaited operation completes, execution can continue from that point.&lt;/p&gt;

&lt;p&gt;You can think of await as saying: "I need the result of this operation before I can continue from here, but there's no reason to block everything else while I'm waiting for it."&lt;/p&gt;

&lt;p&gt;The precise details of what happens underneath, whether that involves an event loop, tasks, promises, futures, state machines or something else, depend on the language and runtime. But you don't need to understand all of those implementation details to understand the basic async mental model.&lt;/p&gt;
&lt;h2&gt;
  
  
  Ready to Dive Deeper?
&lt;/h2&gt;

&lt;p&gt;If async still feels a little abstract, I also explain the same ideas visually in the companion video below. Sometimes seeing the synchronous and asynchronous flows side by side is what finally makes the concept click.&lt;/p&gt;

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

</description>
      <category>programming</category>
      <category>softwaredevelopment</category>
      <category>beginners</category>
      <category>webdev</category>
    </item>
    <item>
      <title>Running Kiro Crew in Docker on Windows</title>
      <dc:creator>Matheus Guimaraes</dc:creator>
      <pubDate>Wed, 12 Aug 2026 20:12:47 +0000</pubDate>
      <link>https://dev.to/aws/running-kiro-crew-in-docker-on-windows-19j6</link>
      <guid>https://dev.to/aws/running-kiro-crew-in-docker-on-windows-19j6</guid>
      <description>&lt;p&gt;I've been playing with &lt;a href="https://kiro.dev/docs/crew/installation/" rel="noopener noreferrer"&gt;Kiro Crew&lt;/a&gt; recently, and when I went to get it running on my Windows machine I had a decision to make.&lt;/p&gt;

&lt;p&gt;Kiro Crew doesn't currently have a Windows desktop app. You can still run it natively on Windows, but the documented route involves installing and running the Gateway from source.&lt;/p&gt;

&lt;p&gt;But then, while looking through the &lt;a href="https://github.com/kirodotdev/KiroCrew" rel="noopener noreferrer"&gt;Kiro Crew GitHub repository&lt;/a&gt;, I noticed another option that immediately caught my attention: &lt;strong&gt;there's an official Docker image!&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Docker is already a familiar part of the development workflow for many of us, and a container felt like a nice, clean way to get Kiro Crew running without installing it from source.&lt;/p&gt;

&lt;p&gt;So that's the route I took.&lt;/p&gt;

&lt;p&gt;It worked, but along the way I ran into an interesting security detail that made the setup slightly less straightforward than simply running a container.&lt;/p&gt;

&lt;p&gt;And, as it turns out, that's actually a good thing.&lt;/p&gt;

&lt;h2&gt;
  
  
  What we're going to do
&lt;/h2&gt;

&lt;p&gt;By the end of this post, we'll have Kiro Crew running in Docker on Windows, with its agent sandbox enabled and without giving the container more privileges than it actually needs.&lt;/p&gt;

&lt;p&gt;I'm using Docker Desktop with WSL 2, so you'll want to have those installed before following along.&lt;/p&gt;

&lt;p&gt;You can check your WSL installation with:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight powershell"&gt;&lt;code&gt;&lt;span class="n"&gt;wsl&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;--version&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;With that out of the way, let's get Kiro Crew running.&lt;/p&gt;

&lt;h2&gt;
  
  
  Starting with the official container image
&lt;/h2&gt;

&lt;p&gt;The Kiro Crew team publishes a public container image, so we don't need to build anything ourselves or even authenticate with a container registry. Nice and easy.&lt;/p&gt;

&lt;p&gt;Before doing anything else, I created a directory to keep the files for this setup together:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;mkdir &lt;/span&gt;kiro-crew
&lt;span class="nb"&gt;cd &lt;/span&gt;kiro-crew
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now, at first glance, running Kiro Crew looks like it should be as simple as starting the official image.&lt;/p&gt;

&lt;p&gt;And technically, the Gateway itself will run.&lt;/p&gt;

&lt;p&gt;But there's another security boundary inside that container that we need to understand before we can start it properly.&lt;/p&gt;

&lt;h2&gt;
  
  
  Wait... a sandbox inside a container?
&lt;/h2&gt;

&lt;p&gt;This was the interesting part for me.&lt;/p&gt;

&lt;p&gt;We're already putting Kiro Crew inside a Docker container, which gives us an isolation boundary between Kiro Crew and our Windows host.&lt;/p&gt;

&lt;p&gt;But Kiro Crew adds another boundary of its own.&lt;/p&gt;

&lt;p&gt;Agent commands aren't simply executed with access to everything available to the main Kiro Crew process. On Linux, Kiro Crew creates an internal user-namespace sandbox for those commands.&lt;/p&gt;

&lt;p&gt;Conceptually, our setup looks something like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Windows
└── Docker container
    └── Kiro Crew
        └── Agent sandbox
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Why sandbox an agent that's already inside a container?&lt;/p&gt;

&lt;p&gt;Because the two boundaries are protecting different things.&lt;/p&gt;

&lt;p&gt;The container isolates Kiro Crew from our host. The inner sandbox isolates &lt;strong&gt;agent commands from sensitive state available to Kiro Crew itself&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;For example, Kiro Crew's sandbox hides credential directories such as &lt;code&gt;~/.aws&lt;/code&gt; and &lt;code&gt;~/.ssh&lt;/code&gt; from agent subprocesses by bind-mounting empty directories over them. So if an agent-executed command tries to access one of those directories, it simply sees an empty directory rather than our AWS credentials or SSH keys.&lt;/p&gt;

&lt;p&gt;That means the Gateway can have the credentials it needs to do its job without automatically making those credentials readable by commands executed by an agent.&lt;/p&gt;

&lt;p&gt;That's a pretty important distinction when we're giving an AI agent the ability to execute commands.&lt;/p&gt;

&lt;h2&gt;
  
  
  Where Docker gets in the way
&lt;/h2&gt;

&lt;p&gt;There's one complication.&lt;/p&gt;

&lt;p&gt;To create that inner sandbox, Kiro Crew needs Linux system calls including:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;unshare(CLONE_NEWUSER)
unshare(CLONE_NEWNS)
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Docker's default seccomp security policy blocks those operations.&lt;/p&gt;

&lt;p&gt;So if the Kiro Crew container can't create its inner sandbox, it doesn't quietly shrug its shoulders and run agent commands without one.&lt;/p&gt;

&lt;p&gt;It &lt;strong&gt;fails closed&lt;/strong&gt;, meaning that when the security mechanism can't be established, access is denied rather than silently falling back to a less secure mode.&lt;/p&gt;

&lt;p&gt;The Gateway and dashboard can still run, but agent command execution remains disabled.&lt;/p&gt;

&lt;p&gt;I actually really like this design! What initially looks like an extra hurdle in getting the container running is Kiro Crew refusing to silently weaken its security model.&lt;/p&gt;

&lt;p&gt;So how do we fix it?&lt;/p&gt;

&lt;h2&gt;
  
  
  The tempting solution and the better solution
&lt;/h2&gt;

&lt;p&gt;There are a few ways we could approach this.&lt;/p&gt;

&lt;p&gt;One option is to simply tell Kiro Crew that we accept running agent commands without the inner sandbox. Kiro Crew provides an environment variable for exactly that:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;KIROCREW_ALLOW_UNSANDBOXED=1
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We could pass that into our container and Kiro Crew would allow agent execution, leaving Docker itself as our only isolation boundary.&lt;/p&gt;

&lt;p&gt;We could also reach for the rather large hammer:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;--privileged
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That would make the sandbox work, but it does so by granting the container extremely broad privileges and removing many of Docker's normal isolation restrictions.&lt;/p&gt;

&lt;p&gt;That's a much bigger security concession than we actually need.&lt;/p&gt;

&lt;p&gt;What we really want is much narrower:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Allow the operations Kiro Crew needs to create its sandbox while keeping the rest of Docker's security restrictions in place.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;And this is another nice detail about the Kiro Crew implementation: the team already provides a seccomp profile specifically for this!&lt;/p&gt;

&lt;p&gt;So we don't have to create one ourselves.&lt;/p&gt;

&lt;h2&gt;
  
  
  Downloading the Kiro Crew seccomp profile
&lt;/h2&gt;

&lt;p&gt;From the &lt;code&gt;kiro-crew&lt;/code&gt; directory we created earlier, download the &lt;a href="https://github.com/kirodotdev/KiroCrew/blob/main/docker/seccomp/kirocrew-seccomp.json" rel="noopener noreferrer"&gt;official Kiro Crew seccomp profile&lt;/a&gt;:&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://raw.githubusercontent.com/kirodotdev/KiroCrew/main/docker/seccomp/kirocrew-seccomp.json &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-o&lt;/span&gt; kirocrew-seccomp.json
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You should now have:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;kiro-crew/
└── kirocrew-seccomp.json
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Having trouble downloading it from WSL?&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;I happened to be dealing with a DNS issue in my WSL environment when I did this, so &lt;code&gt;curl&lt;/code&gt; couldn't resolve GitHub. If you happen to run into the same thing, there's nothing special about downloading the file through &lt;code&gt;curl&lt;/code&gt;: you can download &lt;code&gt;kirocrew-seccomp.json&lt;/code&gt; directly from the Kiro Crew GitHub repository in your browser and place it in this directory manually, which is what I did.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Now we can start the container using that profile.&lt;/p&gt;

&lt;h2&gt;
  
  
  Running Kiro Crew
&lt;/h2&gt;

&lt;p&gt;Run:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;docker run &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="nt"&gt;--name&lt;/span&gt; kirocrew &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-p&lt;/span&gt; 127.0.0.1:5476:5476 &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-v&lt;/span&gt; kirocrew-home:/home/kirocrew &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;--security-opt&lt;/span&gt; &lt;span class="nv"&gt;seccomp&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;kirocrew-seccomp.json &lt;span class="se"&gt;\&lt;/span&gt;
  ghcr.io/kirodotdev/kirocrew:stable
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;There are a couple of things worth noticing here.&lt;/p&gt;

&lt;p&gt;We're only publishing port &lt;code&gt;5476&lt;/code&gt; on the host's loopback interface, so the dashboard isn't being exposed to the rest of our network.&lt;/p&gt;

&lt;p&gt;We're also creating a named Docker volume:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;kirocrew-home
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Kiro Crew keeps its persistent state under &lt;code&gt;/home/kirocrew&lt;/code&gt;, including its configuration and Kiro CLI credentials. That means our state can survive replacing or upgrading the container.&lt;/p&gt;

&lt;p&gt;And, most importantly for what we've just discussed, we're passing the Kiro Crew seccomp profile with:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;--security-opt seccomp=kirocrew-seccomp.json
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The container can now create the inner namespace sandbox while Docker's other default security restrictions remain in place.&lt;/p&gt;

&lt;h2&gt;
  
  
  Let's open it
&lt;/h2&gt;

&lt;p&gt;At this point I did what I imagine most developers would do.&lt;/p&gt;

&lt;p&gt;I opened:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;http://localhost:5476
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And instead of the Kiro Crew dashboard, I was greeted by a message telling me I was missing a token.&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%2Fibs1dbiy2gnkertdm7o2.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%2Fibs1dbiy2gnkertdm7o2.png" alt="Kiro Crew dashboard showing that an access token is required" width="800" height="706"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Another security measure!&lt;/p&gt;

&lt;p&gt;Simply being able to reach port &lt;code&gt;5476&lt;/code&gt; isn't enough to get access to the dashboard. Kiro Crew also requires a bearer token, so someone who can reach the Gateway still needs to authenticate before they can use it.&lt;/p&gt;

&lt;p&gt;So, there's one more part of the setup we need to do.&lt;/p&gt;

&lt;p&gt;Actually, two.&lt;/p&gt;

&lt;h2&gt;
  
  
  Authenticating Kiro CLI
&lt;/h2&gt;

&lt;p&gt;Kiro Crew's agent runtime uses &lt;code&gt;kiro-cli&lt;/code&gt;, so first we need to authenticate the CLI running inside our container.&lt;/p&gt;

&lt;p&gt;We can do that without opening an interactive shell ourselves:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;docker &lt;span class="nb"&gt;exec&lt;/span&gt; &lt;span class="nt"&gt;-it&lt;/span&gt; kirocrew kiro-cli login
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Follow the authentication flow and log in with the identity you use for Kiro.&lt;/p&gt;

&lt;p&gt;Once authentication succeeds, those credentials are stored in the &lt;code&gt;kirocrew-home&lt;/code&gt; volume we created earlier, so they survive container upgrades.&lt;/p&gt;

&lt;p&gt;But that authenticates the agent runtime.&lt;/p&gt;

&lt;p&gt;We still need access to the dashboard.&lt;/p&gt;

&lt;h2&gt;
  
  
  Getting our dashboard token
&lt;/h2&gt;

&lt;p&gt;Every request to the Kiro Crew dashboard requires a token.&lt;/p&gt;

&lt;p&gt;We can mint a temporary login link from the running container:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;docker &lt;span class="nb"&gt;exec &lt;/span&gt;kirocrew kirocrew token &lt;span class="nt"&gt;--ttl&lt;/span&gt; 2h
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Kiro Crew will print a URL containing the token.&lt;/p&gt;

&lt;p&gt;It will look roughly like:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;http://localhost:5476/?token=...
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Open that URL in your browser and...&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%2Fugtlxga5vgxv3hj4i2f8.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%2Fugtlxga5vgxv3hj4i2f8.png" alt="Kiro Crew running successfully in Docker on Windows" width="800" height="469"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;We're in!&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;And with that, we have Kiro Crew running nicely inside Docker on Windows, without having to build it from source and without unnecessarily weakening either of its isolation boundaries.&lt;/p&gt;

&lt;p&gt;Now I just need someone to explain why the Solarized theme is green instead of yellow. 😄&lt;/p&gt;

&lt;h2&gt;
  
  
  References
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://kiro.dev/docs/crew/installation/" rel="noopener noreferrer"&gt;Kiro Crew installation documentation&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/kirodotdev/KiroCrew" rel="noopener noreferrer"&gt;Kiro Crew GitHub repository&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/kirodotdev/KiroCrew/blob/main/docs/guides/docker.md" rel="noopener noreferrer"&gt;Kiro Crew Docker guide&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>docker</category>
      <category>ai</category>
      <category>security</category>
      <category>devops</category>
    </item>
  </channel>
</rss>
