Automated role-based task routing for security teams diagram concept
the shed // AGENTIC AI BRIEFING

Security teams drown in findings from a dozen scanners with no consistent way to get each one to the right specialist. Here’s how role-based agent routing fixes that without a human triage queue.

Security teams do not have a shortage of findings. They have a shortage of routing. See the pattern in action, tap through the tabs below:




triage-crew // routing.yaml

Every scanner speaks a different language, and nobody's translating. A SAST tool flags a SQL injection risk. A cloud posture scanner flags a public bucket. An IAM auditor flags a stale service account with admin rights. Each finding needs a different specialist, but they all land in the same queue.

Right now, a human reads each one and decides where it goes. That step is slow, inconsistent between people, and stalls completely outside business hours, right when a real exposure is most likely to sit unnoticed.

# triage-crew.yaml

agents:
  - name: triage_agent
    role: "Finding Triage Specialist"
    goal: "Classify each incoming finding by domain and
           route it to the correct specialist agent"
    tools: [read_finding, classify_domain, route_to_agent]
    allowed_domains: [iam, network, appsec, cloud_posture]

  - name: iam_agent
    role: "IAM Specialist"
    goal: "Investigate and remediate identity and access findings"
    tools: [iam_policy_lookup, service_account_audit, open_ticket]
    scope: "identity-and-access-only"

  - name: cloud_posture_agent
    role: "Cloud Posture Specialist"
    goal: "Investigate cloud resource exposure findings
           against IaC history"
    tools: [bucket_policy_history, iac_diff_lookup, open_ticket]
    scope: "cloud-resources-only"

routing:
  default_severity_gate: "human_review_above_medium"
  unmatched_finding: "escalate_to_human_queue"

# live routing session, 2:14am

$ triage-agent run --source cloud-posture-scanner --finding FND-88213

[triage_agent] reading finding FND-88213 ...
[triage_agent] resource_type=storage_bucket keywords=[public-read, exposed]
[triage_agent] classified_domain=cloud_posture confidence=0.94
[triage_agent] routing -> cloud_posture_agent

[cloud_posture_agent] fetching bucket policy history for bucket=reports-prod-7f2
[cloud_posture_agent] cross-checking terraform state ...
[cloud_posture_agent] no matching intentional change found
[cloud_posture_agent] severity=high, human_review_required=true
[cloud_posture_agent] paging on-call: cloud-team-secondary
[cloud_posture_agent] ticket opened SEC-4471, context attached
[cloud_posture_agent] time-to-page: 3m12s

Getting started this week:

1. Map your current finding sources (scanners, pentest reports, manual review) and note what domain each belongs to.
2. Write a role, goal, and tool scope for each specialist agent before writing any routing logic.
3. Start with three roles max: identity, network, application. Split further only once you see real misroutes.
4. Set a severity gate so agents route and page, but a human approves anything above your threshold.
5. Log every routing decision somewhere your compliance team can query later.

The Triage Bottleneck Nobody Budgeted For

A single sprint can produce results from a SAST scanner, a cloud posture tool, an IAM access reviewer, a dependency scanner, and whatever the last pentest turned up. Every finding needs a specialist: an IAM person for a stale service account, a network person for an open security group, an AppSec person for an injection flaw, a cloud engineer for a public storage bucket.

Most teams solve this with a shared queue and a human dispatcher. A senior engineer, or whoever is on call, reads each finding and decides what kind of problem it is before forwarding it. That step does not scale. It is inconsistent between people, stalls overnight and on weekends, and burns your most senior engineer's time on classification work that does not need their seniority.

How It's Built: Give Every Agent a Job Description

The fix is not a smarter agent that tries to do everything. It is the opposite: narrow, role-defined agents that each own one domain, plus a triage agent whose only job is reading a finding and deciding who owns it.

This is the core idea behind CrewAI's role-based design pattern: every agent gets a role, a goal, and a set of tools scoped to that role. A Triage Agent does not fix anything, it classifies. An IAM Agent only has tools for identity systems. A Network Agent only touches firewall rules and security groups. An AppSec Agent only opens tickets against application repos.

That separation matters more than raw classification accuracy. When an agent's tool access is scoped to its role, a routing mistake cannot turn into a change made by the wrong system. The Network Agent physically cannot touch an IAM policy, even if the Triage Agent misclassifies a finding. It is least-privilege applied to agents, not just people.

Walking Through a Real Finding

Say a cloud posture scanner flags a storage bucket with public read access at 2am. Right now that finding sits in a shared queue until someone with cloud context wakes up, opens it, and works out if it is a false positive or a real exposure.

With role-based routing, the Triage Agent picks up the finding, checks it against a small set of classification signals (resource type, service, keywords in the description), and hands it to the Cloud Posture Agent with the original scanner output attached. That agent has tools to check bucket policy history, cross-reference your infrastructure-as-code repo to see if the change was intentional, and either close it as expected behavior or open a ticket with severity and owning team pre-filled.

A human still makes the actual security call on anything above a defined severity threshold. What changes is that the right human gets paged, with the right context, in minutes instead of whenever the queue gets read.

What Actually Changes

  • Findings reach the right specialist in minutes, not whenever someone gets to the shared queue.
  • Triage is consistent. The same category of finding goes to the same agent every time, day or night.
  • Senior engineers stop spending mornings re-reading tickets that were routed to the wrong team.
  • Every routing decision leaves an audit trail, which matters when a SOC 2 auditor asks how you handle findings.
  • On-call rotations get paged for their actual domain instead of whoever happened to be reading the queue.

Where This Breaks

Role boundaries need to be genuinely distinct, or agents will end up fighting over ownership. A finding can easily be both an IAM issue and a cloud issue at once, so build an explicit shared-ownership path for those rather than pretending the split is always clean.

Do not let the Triage Agent auto-close anything above low severity. It should stay a router, not a judge, especially early on while you are still tuning its classification logic.

FAQ

How is this different from a rules engine that routes findings by keyword?

A rules engine gets harder to maintain as your finding sources grow, since every new scanner needs its own hand-written rules. A triage agent works from a role description and each specialist agent's stated scope, so adding a new specialist is closer to writing a job description than writing new routing logic.

Do I need CrewAI specifically to build this?

No. CrewAI is one convenient way to define agent roles and hand off between them, but the underlying pattern, a router plus narrow specialist agents with scoped tool access, works with other agent frameworks too. The framework is implementation detail.

What's the biggest mistake teams make rolling this out?

Starting with too many roles. Begin with two or three broad specialists, such as identity, network, and application, and split further only once you see where misroutes actually happen.

For teams who want this routing layer built and tuned against their own scanner stack, tha-shed's DevOps & Cybersecurity coaching covers agentic workflow design for security teams end to end.