Skip to main content

Posts

Let your agents cleanup after they leave your desk

If you are let multiple agents work in parallel on your code base, you need a way to start an agent session with code isolation. The typical way to do this is by creating separate Git worktrees for each agent. avoids that parallel agents overwrite each other’s files. But the sessions pile up, and so do the worktrees. Each one is a full checkout on your disk. Until recently I did the cleanup work myself, but now VSCode has a worktree cleanup feature to deal with this. Why do we need this? Before this feature, you had two options: do it by hand or ignore it. By hand meant something like this: git worktree list git worktree remove <path> git worktree prune That works. But it doesn’t tell you which worktree belongs to which agent session, whether the session is still relevant, or how much space you’ll get back. Archive, done or delete? Cleanup builds on how VS Code already finishes sessions. There are three actions: Close a chat tab: hides the conversation, noth...
Recent posts

Track used skills, agents and MCP servers with the Copilot usage metrics API

As part of our AI adoption journey, we wanted to know which custom skills, agents and MCP servers were actually in use. So, we built a small tool that scanned our repositories for SKILL.md files, .agent.md files and MCP configuration. It worked, but it answered the wrong question. It told us what existed , not what developers used . The Copilot usage metrics API now closes that gap. What changed? In September the API got CLI customization metrics. The catch: every customer-defined skill, agent and MCP server was grouped under other , and slash commands under custom . Useful for trends, useless for “is our new skill being used?”. Since October 22, the totals_by_skill , totals_by_custom_agent , totals_by_mcp , totals_by_slash_cmd and totals_by_plugin arrays show the configured name of your own items. Each list also holds up to 25 entries per record, up from five. Remark: names are reported from Copilot CLI, the Copilot app, clients built on the Copilot SDK (like VS Code ...

Strongly typed IDs in .NET with Vogen

What does this method signature tell you? public Task<Order> GetOrder(Guid customerId, Guid orderId) Nothing that stops you from calling it like this: await repository.GetOrder(orderId, customerId); It compiles, it runs, and it returns nothing (or worse, the wrong thing). Every ID is a Guid , so the compiler can’t help you. This problem is called primitive obsession. We don't take real advantage of our type system but use any of the built-in primitives instead. The solution The obvious fix is a small wrapper type per ID. A readonly struct or a record does the job, but you end up writing the same boilerplate for every ID: equality, ToString , JSON serialization, a type converter for route binding, an EF Core value converter, Luckily someone already did all the hard work for us and created Vogen. Vogen is a source generator that does all the hard work. Add the package: dotnet add package Vogen And declare your ID: using Vogen; [ValueObject<Guid>]...

Generating architecture diagrams with the Archify skill

Keeping architecture diagrams up to date has always been a lot of work. They are outdated the moment your diagram is saved. Thanks to AI, keeping those diagrams up-to-date became a lot easier. I originally did this just by asking the AI to create and update mermaid diagrams, but recently I started experimenting with Archify . You describe a system in plain words (or point your agent at a codebase), and you get back an interactive HTML diagram. What is Archify? Archify is an agent skill and some tooling around it. It works with Claude Code, Codex, Cursor, OpenCode and GitHub Copilot. What makes it different, is that the agent doesn’t draw the diagram directly. It authors typed JSON that describes the system. Archify then renders that JSON and validates it. The output is a single, self-contained HTML file. Installing the skill For Claude Code: npx -y skills@latest add https://archify.si --skill archify --agent claude-code --global --copy --yes For GitHub Copilot: npx ...

DSC 3.0: running your own PowerShell with getScript, testScript and setScript

Sooner or later you hit a setting that no DSC resource manages. A hosts file entry, a certificate with specific properties, some tweak that only exists as a PowerShell snippet on a wiki page. You know the PowerShell to fix it, but there is no resource to wrap it in. One way is to reach for Microsoft.DSC.Transitional/RunCommandOnSet . It runs a command during the set operation, and that is all it does. There is no test, so DSC cannot tell you whether the machine is in the desired state. But it is a good fit as a temporary transitional resource while migrating DSCv3 resources. There is another option: Microsoft.DSC.Transitional/PowerShellScript . It lets you bring your own getScript , testScript and setScript . Note: If you are new to DSC 3.0 check out my blog series about it: Getting started with DSC 3.0 – Part 1: What is DSC and what changed? Getting started with DSC 3.0 – Part 2: Managing a Windows service end to end Getting started with DSC 3.0 – Part 3: Capturin...

Letting GitHub Copilot drive your desktop with computer use

I'm a big fan of the Automations feature in the GitHub Copilot app. It allows me to focus on the most important stuff and I can schedule and delegate a lot of work in the background. Most of the time, these automations can interact with an API, a CLI or an MCP server. But what if you want to interact with a desktop application that only exists as a GUI, a legacy tool nobody wants to touch, a screen you have to click through by hand every week. That is the gap GitHub is trying to close with the recently introduced 'computer use' feature in the GitHub Copilot app and Copilot CLI. What is computer use? Computer use lets Copilot interact with desktop applications on your behalf. It reads the application content through the accessibility tree of your operating system and takes screenshots when it needs visual context. Then it can click controls, enter and edit text, press keys, scroll and drag. Some facts up front: It is in public preview since October 1, 2026 ...

SQL Server Full-Text Search: when a stop word broke our search

One of our users complained that the search functionality was broken. Searches that should have returned results came back empty. The cause turned out to be a single word: 'both'. If you are new to Full-Text Search, start with my previous post. It explains the building blocks I use below. The problem The search in our application is built on SQL Server Full-Text Search. The terms a user types are combined into a CONTAINS query. A simplified version looks like this: SELECT ProductId, Name FROM dbo.Products WHERE CONTAINS(Description, '"bike" AND "both"'); This returned no rows, even though we knew there were products matching both terms. Searching for "bike" alone worked fine. Looking for the cause The cause is simple:  Stop words Stop words are words that are not indexed because they are considered too common to be useful. SQL Server ships with a system stoplist per language, and 'both' is on the English one: S...