Back to Blog

Defining Capabilities for Copilot Agents in TypeSpec - What They Do and How to Pick the Right Ones

September 11, 20268 min readMichael Ridland

When people picture a Microsoft 365 Copilot agent, they usually picture the clever part: the instructions, the personality, the knowledge it draws on. What they miss is that an agent is mostly defined by what it can reach and what it can do. An agent with brilliant instructions and no access to anything useful is a chatbot with opinions. The bit that connects it to the real world, the documents, the search index, the actions it can take, is the capabilities layer, and getting it right matters more than most of the wordsmithing people obsess over.

If you are building agents in TypeSpec, capabilities are how you declare what your agent is allowed to touch. Microsoft's documentation on capabilities in TypeSpec has the syntax and the current list. I want to talk about what these actually do in practice, how we decide which to switch on for a client, and where teams get themselves into trouble.

What capabilities really are

A capability is a grant. Each one you add to an agent extends its reach in a specific direction. One lets it search and use content from SharePoint and OneDrive. Another connects it to specific web content. Another gives it access to a particular data source or lets it perform an action rather than just answer. Without capabilities, your agent knows only what is in its instructions and whatever general knowledge the model has. That is fine for a narrow question-and-answer bot and useless for anything that needs to know about your business.

The mental model I find helpful is to think of the agent as a new hire on their first day. The instructions are their job description. The capabilities are their access badges and system logins. A new hire with a great job description and no login to anything cannot do the job. And a new hire you hand the master key to on day one is a risk you did not need to take. Capabilities are the access decisions, and like access decisions in any organisation, the right answer is the least that gets the job done.

Doing it in TypeSpec, and why we bother

You can declare capabilities in a raw JSON manifest. We do it in TypeSpec on client builds, for the same reason we do most agent definition in TypeSpec: it is typed, it compiles, and it lives in source control where you can diff and review it. A capability is a security-relevant decision. Which of them your agent has should be something a second engineer can read in a pull request and question, not something buried in a hand-edited JSON blob that nobody has looked at since it was pasted in.

When you are running one agent, this feels like overkill. When you are running a fleet across a tenant, and a security reviewer asks "which of these agents can read finance's SharePoint", you want that answer to come from a clean, version-controlled definition, not from opening manifests one by one and squinting. This discipline is a standard part of how our Microsoft AI agent framework consultants work, because the alternative falls apart the moment you have more than a handful of agents to look after.

Picking the right capabilities

Here is the opinionated part, the bit the docs will not tell you because it depends on judgement.

Start from what the agent needs to do, not from what is available. The list of capabilities is a menu, and the temptation is to switch on a few extra "just in case". Resist it. Every capability you add is more surface area, more access to reason about, and more ways for the agent to do something you did not intend. Turn on what the job requires and nothing else. An agent that answers HR policy questions needs access to the HR policy library. It does not need to browse the open web, and giving it that access buys you nothing but risk.

Match the capability to the actual data source. A capability that lets an agent search your internal content is only as good as the content it points at. We see teams switch on a search capability, point it at a sprawling SharePoint with ten years of duplicated, outdated documents, and then wonder why the agent gives inconsistent answers. The capability worked perfectly. The data was the problem. Before you grant access to a source, be honest about whether that source is any good, because the agent will faithfully surface whatever is there, including the wrong version of a policy from 2021.

Be very deliberate about action capabilities. There is a meaningful line between an agent that reads and answers, and an agent that does something: creates a record, sends something, changes a system of record. The moment your agent can take an action, the stakes change entirely. A wrong answer is annoying. A wrong action is a real problem, because now the mistake is written into a system. We are conservative here, and we push clients to be conservative too. Read capabilities are relatively low risk. Write and action capabilities need proper thought about what happens when the agent gets it wrong, because it will, eventually.

The gotchas

A few things bite people, and they are rarely in the tutorial.

Capabilities interact with the permissions the user already has. This is a subtle one people miss. Just because you gave an agent a search capability does not mean it can show a user content that user is not allowed to see. The platform respects the underlying permissions, which is exactly what you want, but it means an agent can behave differently for different users depending on their access. Someone tests the agent, it works beautifully, a colleague with narrower permissions tries the same thing and gets a thinner answer, and everyone is confused. Test with realistic user permissions, not just your own admin-level access, or you will ship something that works only for you.

More capabilities can make routing worse, not better. An agent that reaches into everything becomes harder for the Copilot orchestrator to reason about and harder for users to understand. A focused agent with a tight set of capabilities and a clear scope tends to behave more predictably than a sprawling one that can do a bit of everything. Broad is not the same as capable.

Scope creep is real. An agent starts life doing one thing, then someone asks for "just one more" data source, then another, and eighteen months later you have an agent with a grab-bag of capabilities nobody can quite justify and a scope that has drifted from its original purpose. Review the capability set periodically and prune it. What made sense at launch may not make sense now, and unused access is pure risk with no upside. This kind of ongoing hygiene is a big part of what our Microsoft AI consultants do once an agent is in production, because agents are not set-and-forget.

The honest assessment

What is good: the capabilities model gives you real, declarative control over what an agent can reach, and doing it in TypeSpec means those decisions are legible and reviewable. Compared with the early days of agent building, where access felt vague and hard to pin down, this is a solid improvement. You can look at an agent and know what it can touch, which is the starting point for trusting it.

What is still rough: the interaction between capabilities, user permissions, and the data behind each source is genuinely fiddly, and the failure modes are quiet. An over-scoped agent does not throw an error. It just carries more risk and behaves less predictably than it should, and you might not notice until a security review or an embarrassing incident. The platform gives you the controls, but it does not make the judgement for you, and the judgement is where the value is.

The thing I would stress is that capabilities are a security and design decision dressed up as a configuration step. Treat them that way. The question is never "what can we switch on" but "what does this agent actually need, and what is the smallest set of access that does the job". Get that right and the agent is both more trustworthy and easier to reason about. Get it wrong and you have built something powerful that nobody can quite vouch for.

If you are building Copilot agents and want the access model set up so it holds up to scrutiny rather than needing a rework after a security review, that is the kind of work our AI agent builders do day to day. Have a look at our services or get in touch and we will give you a straight assessment of what your agents should and should not be reaching for.

Microsoft's capabilities documentation has the current list and the TypeSpec syntax. The decision about which ones belong on your agent is the part worth getting right early.