Tracking Pentest Findings in a Spreadsheet, and When to Stop
Track pentest findings in Excel or Google Sheets with a fixed ID, CVSS vector, owner, target date and retest result on every row, and know when to stop.
A pentest findings tracker in Excel or Google Sheets needs one row per finding with an ID that never changes, the severity and CVSS vector, the affected assets, a status from a defined list, a named owner, a target date, the latest retest result and a link to the evidence. It stays honest while one person owns it, IDs are never reused and history is added rather than overwritten, and it is time to stop when the firm and the client are both editing copies of it.
One set of findings, two trackers
A testing firm keeps a tracker to know which findings are open across its engagements, which are due a retest and what each retest found. The client receiving the findings keeps one to run remediation: who is fixing what, by when, and what was decided about the rest. Both start from the same report and need most of the same columns. The difference is ownership. The firm owns the ratings and the retest results, the client owns the people and the progress, and most of the trouble below comes from a sheet either side can change.
The columns that matter
| Column | What goes in it | Why |
|---|---|---|
| Finding ID | The engagement reference and a number, such as ACM-031-07 | Tickets, emails and retests all refer to it. Titles get reworded; the ID never changes. |
| Title | The title exactly as the report gives it | So anyone can find the finding in the document. |
| Reported | The date the client was told, and the report version | The remediation clock starts here. |
| Severity and CVSS | The rating, the score and the full vector string, which begins with its version | A score without its vector cannot be checked, and when a rating changes the vector shows what moved. |
| Affected assets | Every host, URL or component, or a tab with one row per finding and asset | Fixes land asset by asset. A finding on forty hosts is fixed when the fortieth is. |
| Status | One value from a defined list | Every count and filter depends on it. |
| Owner | A named person | A team or a distribution list is not an owner. |
| Target date | A date taken from the agreed remediation timeline | It turns a severity into a date somebody can be held to. |
| Retest result and date | The outcome of each retest, and when it was done | It separates fixes the client reported from fixes somebody verified. |
| Evidence | A link to the evidence in the report or your controlled store | The evidence itself never goes in the sheet. |
Target dates should come from a table agreed before testing, not negotiated finding by finding afterwards; vulnerability remediation timelines sets one out, with where each figure comes from. On the client's side, add a column for the ticket in their own system, so the sheet points at the work rather than replacing it.
Rules that keep a sheet honest
- One sheet, one owner. Decide whose copy is the record and who answers for it, and let it be the only copy. If both sides edit it, give each side its own columns: in Google Sheets, protect the ID, rating and retest columns so only the firm can edit them; in Excel, unlock the columns the client fills in and protect the rest of the sheet.
- IDs are never reused. A finding withdrawn in QA or after a dispute keeps its row and its ID, marked withdrawn with the reason. Never number by row, never renumber after a sort, and give anything found during a retest a new ID.
- Statuses are defined. Put the list and what each status means on a tab of its own, and make the column a dropdown.
- History is added, not overwritten. When a severity, status or target date changes, add a dated line to a change log tab with the old value, the new one, who changed it and why. Version history shows that a cell changed; only the log says why.
- The sheet is as sensitive as the report. Unfixed weaknesses listed against hostnames are exactly what an attacker would want. Share it with named people, never through a link anyone can open, and remove access when the engagement ends.
A status list that covers most engagements:
| Status | Means | Set by |
|---|---|---|
| Open | Reported, with no fix yet | The firm, at delivery |
| In progress | Somebody named is working on it | The client |
| Fix reported | The client says the fix is deployed to the tested environment | The client |
| Remediated | A retest found the weakness gone | The firm |
| Part remediated | A retest found some of it still present | The firm |
| Not remediated | A retest found it unchanged | The firm |
| Risk accepted | A named person decided not to fix it, with a date to revisit it | The client, recorded by the firm |
| Withdrawn | Removed after QA or a dispute, with the reason | The firm |
Separating fix reported from remediated is the point: a sheet that only says "fixed" cannot tell a claim from a verified result. Risk accepted is a status of its own rather than a kind of closed, for the reasons in when a client accepts the risk instead of fixing it.
What breaks as volume grows
A sheet like this holds up for one engagement and one contact. With several of each, it fails in four places.
Copies edited by both sides. The firm sends the sheet, the client adds columns and renames two statuses, the firm records a retest in its own copy in the meantime, and somebody merges the two by hand. Every merge is a chance to lose an update, and the one lost is usually the retest result.
The report and the sheet disagree. A finding withdrawn in QA stays in the sheet, or a severity lowered after the debrief changes in the report but not in the tracker the retest will start from. Two records of one engagement drift apart, for the reasons set out in Word and spreadsheets or a reporting platform.
Evidence does not travel. A link to the firm's file share means nothing to the client's engineer, and screenshots pasted into cells go wherever the sheet is forwarded. The developer fixing the finding needs the request and the response; the sheet gives them a title and a colour.
Retests and auditors ask for history. An auditor wants to know when a finding was reported, how it was rated then, when it was fixed and who verified it. A retest starts from the original finding, its evidence and the client's account of the fix, as how to run a retest properly sets out. A sheet with overwritten cells cannot answer either, and a weakness raised again next year under a new ID hides that it came back.
When to stop
The signals are about how the sheet is used, not how many rows it has. Stop when you merge copies more than once an engagement, when retest requests arrive as edited spreadsheets by email, when the client's engineers already work from a ticketing system and the sheet has become a copy of their tickets, or when somebody asks for a history you would have to rebuild from old versions.
What replaces it depends on your side. A client should move remediation into its own ticketing system, one ticket per finding carrying the finding ID, which is what what happens after a penetration test recommends on the day the report lands. A testing firm should move to a record that the report, the tracker and the client's view are all generated from, so nothing needs reconciling.
The spreadsheet does not disappear. It becomes an export: a dated, read-only snapshot for a board pack, an auditor or a client who wants to filter findings their own way. A snapshot that says when it was taken is useful. A copy that passes itself off as the record is where the trouble started.
Our free reporting tool and the Portal share the same reporting. Findings go out to Excel, PDF or Word for one finding, an engagement or every phase at once (one Excel file with a tab per phase), with the columns you choose, a summary tab of severity counts per phase and a figures tab linking every figure back to its finding. Change the sheet in Excel and bring it back, and you see what would change and what would be deleted before anything is. In the Portal, clients sign in to read their findings, ask for retests and comment on the engagement, and findings can be pushed to their Jira, ServiceNow and other trackers with their state read back, as retests and your client's issue tracker explains. Exporting findings to Excel, Word or PDF covers the exports.
Common Questions
- What columns should a pentest findings tracker have?
- One row per finding, with an ID that never changes, the title as the report gives it, the date and report version it was reported in, the severity with its CVSS score and full vector, the affected assets, a status from a defined list, a named owner, a target date from the agreed remediation timeline, the latest retest result and date, and a link to the evidence. Clients should add the ticket reference from their own system.
- Who should own a pentest remediation tracker, the client or the testing firm?
- Both have a part, so split the columns rather than sharing everything. The testing firm owns the ratings, CVSS vectors and retest results, because those are its findings. The client owns the owner, target date and progress columns, because the work is theirs. Keep one copy as the record, protect each side's columns, and send updates to whoever owns them rather than keeping a second copy that has to be merged later.
- How should pentest findings be numbered?
- Give each finding an ID made from the engagement reference and a sequence number, and never change or reuse it. A finding withdrawn in QA or after a dispute keeps its ID, with a withdrawn status and the reason. Do not use row numbers, which change when somebody sorts the sheet, and give anything new found during a retest a fresh ID rather than borrowing an old one.
- When should you stop tracking pentest findings in a spreadsheet?
- When you merge copies edited by both sides more than once an engagement, when retest requests arrive as edited sheets by email, when the client's engineers already work in a ticketing system, or when an auditor asks for a history you would have to rebuild from old versions. At that point the client should track remediation in its own tickets and the firm in a system that generates the report and the tracker from one record.
Keep Reading
Screenshots in Pentest Reports: Captions, Redaction and Size
Screenshots in a pentest report should each prove one point: cropped, redacted by removing the data, captioned with what they prove, numbered and kept small.
Markdown or Word for Pentest Reports: What Each Costs You
Markdown or Word for pentest reports: what each costs in writing, review, layout, version control and client edits, plus a third option and how to choose.
Stopping AI From Inventing Findings in Pentest Reports
How to stop AI inventing versions, CVEs, hosts and impact in pentest findings: draft only from captured evidence, keep values verbatim, and review every draft.
Setup guide
See the product set up, end to end
The whole setup in 10:01, with chapters you can jump to: registering, your own domain, your own database in any of three places, your own mail server, branding, the first sign-in, updating the database on Supabase Cloud, and moving the database if you change your mind.
- 0:00 · Registering, signing in, and the free trial
- 0:44 · Your name and your firm’s name
- 0:50 · Custom domain
- +6 more