I have watched security teams drown in vulnerability data. Thousands of findings pour in from scanners, and the response is usually one of two extremes: treat everything as critical (and burn out the engineering team) or file it all into a backlog (and actually fix nothing). Neither works.
A good triage workflow is the bridge between detection and remediation. It decides what gets fixed, in what order, by whom, and by when. Get this right, and your vulnerability management program actually functions. Get it wrong, and you are just generating reports nobody reads.
Why Most Triage Processes Fail
The typical failure mode looks like this: the security team runs a scan, exports a spreadsheet of 2,000 findings, emails it to engineering, and asks them to "prioritize and fix." Engineering looks at the spreadsheet, sees no clear prioritization, no ownership mapping, and no timeline, so they do nothing. Three months later, the auditor asks for remediation evidence, and everyone panics.
The root causes are usually:
- No contextual prioritization. CVSS alone does not tell you what matters.
- No ownership mapping. Findings are not routed to the team that can fix them.
- No SLAs. Without timelines, everything has the same priority: none.
- Too much noise. When 80% of findings are informational or false positives, people stop looking.
The Triage Framework
Stage 1: Intake and Deduplication
Before anyone looks at a finding, clean up the data. Scanners produce duplicates across tools, scans, and time periods.
Deduplicate by:
- Same CVE affecting the same component in the same project.
- Same finding from different scanners (Dependabot and Snyk often report the same CVE).
- Findings that are already tracked in your existing backlog.
This alone typically reduces volume by 30-50%.
Stage 2: Contextual Scoring
CVSS tells you the theoretical severity. You need practical severity. Enrich each finding with:
Exploitability: Is there a public exploit? Is it being actively exploited in the wild? Check CISA KEV (Known Exploited Vulnerabilities) and EPSS (Exploit Prediction Scoring System).
Reachability: Is the vulnerable code path actually executed in your application? A critical vulnerability in a function you never call is less urgent than a high vulnerability in your authentication middleware.
Environment exposure: Is the affected component in a public-facing service? Internal tool? Air-gapped system? A remote code execution vulnerability in an internet-facing API is fundamentally different from the same vulnerability in an internal batch processor.
Data sensitivity: What data does the affected service handle? PII, financial data, and healthcare records elevate priority.
Build a composite score:
| Factor | Weight | Scale | |--------|--------|-------| | CVSS base score | 25% | 0-10 | | EPSS probability | 25% | 0-1 (scaled to 0-10) | | Reachability | 20% | Binary: 0 or 10 | | Environment exposure | 15% | Internal=2, Staging=5, Production=8, Public=10 | | Data sensitivity | 15% | None=0, Internal=3, Confidential=7, Regulated=10 |
The composite score drives your SLA tier, not the raw CVSS.
Stage 3: Ownership Assignment
Every finding needs an owner. Not "the security team." Not "engineering." A specific team or individual who has the authority and knowledge to fix it.
Map ownership through:
- Repository CODEOWNERS files that link dependency files to teams.
- Service catalogs (Backstage, OpsLevel, etc.) that map services to owning teams.
- Dependency manifests - if the vulnerable dependency is
react, it goes to frontend. If it ispg, it goes to the backend team that owns the database layer.
Automate this mapping. Manual routing does not scale past a dozen repositories.
Stage 4: SLA Assignment
Tie SLAs to your composite severity tiers:
| Tier | Composite Score | Remediation SLA | |------|----------------|-----------------| | Critical | 8.0-10.0 | 48 hours | | High | 6.0-7.9 | 7 days | | Medium | 4.0-5.9 | 30 days | | Low | 2.0-3.9 | 90 days | | Informational | 0-1.9 | Accept or next quarter |
SLAs should be realistic. Setting a 24-hour SLA for everything critical sounds good on paper but guarantees SLA breaches, which erodes trust in the entire program.
Stage 5: Disposition
Not every finding needs a code fix. Valid dispositions include:
- Fix - Upgrade, patch, or refactor.
- Mitigate - Apply compensating controls (WAF rule, network segmentation) when a fix is not immediately available.
- Accept - Document the risk, get sign-off from a risk owner, and set a review date.
- False Positive - Mark as such with justification. Feed this back to improve scanner configuration.
- Not Applicable - The component is present but not deployed, or the vulnerable function is not reachable.
Every disposition needs a justification. "Accepted" without a reason is the same as "ignored."
Stage 6: Tracking and Escalation
Track remediation in the same system your developers already use. If your engineering team lives in Jira, vulnerability tickets go in Jira. If they use Linear, use Linear. Do not create a separate tracking system that nobody checks.
Escalation triggers:
- SLA approaching (75% of time elapsed) - notify the assigned team.
- SLA breached - notify the team lead and security manager.
- SLA breached by 2x - escalate to engineering director.
Automated escalation removes the awkward "hey, can you fix this?" conversations and replaces them with process.
Operationalizing the Workflow
Daily Standup Integration
For critical and high findings, integrate vulnerability status into existing daily standups. Not as a separate meeting. Not as a separate report. As a standard agenda item: "Do we have any open critical or high vulnerabilities approaching SLA?"
Weekly Review
Hold a 30-minute weekly triage meeting between security and engineering leads. Review:
- New findings from the past week.
- Approaching SLA breaches.
- Findings needing disposition decisions (accept, mitigate).
- False positive patterns that need scanner tuning.
Monthly Metrics
Report on:
- Mean time to triage (time from detection to ownership assignment).
- Mean time to remediate (time from detection to deployed fix).
- SLA compliance rate by tier.
- Volume trends (are findings increasing or decreasing over time?).
- Top 5 recurring vulnerability types (these suggest systemic issues worth investing in prevention).
Common Anti-Patterns
The spreadsheet handoff. Exporting findings to Excel and emailing them to engineering is not a workflow. It is a dead end.
Treating all criticals the same. A CVSS 9.8 in a test environment is not the same as a CVSS 9.8 in your payment processing system.
Triaging at the CVE level instead of the instance level. The same CVE in different contexts can have different priorities.
No feedback loop. If developers report false positives and nothing changes in the scanner configuration, they stop reporting.
How Safeguard.sh Helps
Safeguard.sh provides built-in vulnerability triage with contextual scoring that goes beyond raw CVSS. It maps findings to project owners, enforces remediation SLAs through policy gates, and gives both security and engineering teams a shared view of what needs fixing and when. The platform tracks disposition decisions, automates escalation, and provides the metrics you need to demonstrate program effectiveness. Instead of building a triage workflow from scratch with custom tooling, Safeguard.sh gives you a proven framework that works out of the box.