Bug report templates for web apps, mobile, visual and performance bugs
One template does not fit every bug. These six each carry the fields their kind of bug cannot be fixed without, and there are versions for GitHub, team chat and customers too.
By the VeoRec team · · 11 min read
In short
Every bug report template needs the same core: title, environment, steps from a clean start, expected and actual results, frequency, severity and evidence. On top of that, each kind of bug needs a few fields of its own: device and orientation for mobile web, viewport and zoom for visual bugs, measured timings for performance, attempt counts and timestamps for intermittent bugs. Copy the one that fits below, and put it in your tracker so people never start from a blank box.
- Start every template with the same core fields, then add the three or four that this kind of bug needs.
- Visual bugs need viewport width, zoom and OS scaling; without them a layout bug often cannot be reproduced.
- Performance reports need a measured number, how it was measured, and the data size, not the word "slow".
- Intermittent bugs need attempt counts and exact timestamps so failures can be matched to logs.
- Make only four or five fields required. A template nobody finishes is worse than a short one people fill in.
- Review the template against your "cannot reproduce" tickets every few months and fix the field that keeps going missing.
A bug report template exists for one reason: so the person who found the bug writes down, in one go, everything the person fixing it will ask for. A good one turns "the dashboard is weird" into a ticket a developer can pick up cold. A bad one is a wall of fields people skip or fill with "N/A".
This post gives you a core bug report template, five variants for specific kinds of bugs (mobile web, visual, performance, intermittent, errors), and versions for a GitHub issue form, a team chat message and a customer email. Copy what you need. Each one is plain Markdown, so it pastes cleanly into Jira, Linear, GitHub, GitLab or a shared doc.
Start from the core fields every bug report needs
Every template below shares the same spine. If you only adopt one thing, adopt this order, because it matches the order a developer works in: find it, reproduce it, compare it, judge it.
| Field | What good looks like | Common miss |
|---|---|---|
| Summary | Where, what happens, under which condition | A mood ("broken", "weird") instead of a symptom |
| Environment | URL, build, browser and version, OS, account role | "Chrome" with no version; no account role |
| Steps | Numbered, from a stated starting point, one action each | Starting halfway through the flow |
| Expected / actual | Two separate lines, observations only | Merged into one sentence, or a diagnosis instead |
| Frequency | Every time, X of Y attempts, or once | Left blank, so nobody knows if a retry is enough |
| Severity | A level plus one sentence of reasoning | Everything marked critical |
| Evidence | Recording or screenshot, exact error text, failing request | A paraphrased error message |
If you want the reasoning behind each field, with a worked example, start with how to write a bug report. This post is the toolbox: the shapes, ready to paste.
Copy a bug report template for the bug in front of you
Pick the template by the kind of bug, not by the team that will fix it. A layout glitch on a phone is a mobile bug and a visual bug; use the visual one and add the device lines. Each template has a Copy button.
The general template covers most bugs. The other five keep the same core and add a handful of fields each. The reasons matter, because a field nobody understands gets skipped.
Mobile web: the device is part of the bug
On mobile, "Safari" can mean the browser app, or the in-app browser that opens when someone taps a link in an email or chat app, and they do not always behave the same. Ask for the exact device, the OS version and where the page was opened. Orientation and network belong here too: a checkout button that hides under the keyboard only in landscape is a real bug, and it is invisible to anyone testing in portrait.
The "Does it happen on desktop?" line is there to save a step. If the answer is yes, the developer can debug in a desktop browser, which is much faster than debugging on a phone.
Visual bugs: write down the viewport, zoom and scaling
Layout bugs depend on numbers the reporter rarely thinks about. A card grid that wraps at 1,280 pixels wide looks fine at 1,440. Browser zoom at 110% and Windows display scaling at 125% both change the effective width. Without those three values, the developer will open the page, see nothing wrong, and close the ticket.
The other field that matters is "What it should look like". Link the design file or a screenshot of a page where the same component looks right. "The spacing looks off" is an opinion; "the gap is 8 px here and 24 px in the design" is a bug. For visual bugs the evidence is usually a screenshot, so capture the browser, not a photo of your monitor, and annotate the part that is wrong.
Performance bugs: replace "slow" with a number
Nobody can fix "slow". They can fix "the Reports page takes 31 to 44 seconds across five loads for an account with 12,000 invoices, and took about 3 seconds last month". That sentence has a measurement, a method, a data size and a baseline, which are the four fields in the performance template.
Say how you measured. A stopwatch is fine if you say so. The Network and Performance panels in browser DevTools give better numbers and can export a profile the developer can open. Data size matters most of all: a page that is fast with 50 records and unusable with 12,000 is a different bug from a page that is slow for everyone.
Intermittent bugs: count attempts and keep timestamps
"Sometimes" is the least useful word in a bug report. "4 of 20 attempts" is useful, because the developer knows they need to try at least 20 times before calling it fixed. Timestamps are even more useful: with the exact time of each failure, someone can find those requests in the logs and compare them with the attempts that worked.
The field "What differed between failing and passing attempts" is where intermittent bugs get solved. Were you clicking faster? Was the tab in the background? Had the page been open for an hour? Even a hunch is worth writing down, labelled as a hunch. There is more on chasing these in writing steps to reproduce.
Errors and failed requests: copy, never paraphrase
An error message is evidence, and paraphrasing it destroys some of it. "Request failed: 422, ref 8f2c1a at 14:03 UTC" lets a developer find the exact failing request. "It said something about a failed request" does not. The template asks for the status code and response body from the browser's Network panel because they often contain the whole diagnosis.
See a filled-in bug report template
Templates are easier to use when you have seen one done well. The table shows the visual template filled in for a plausible bug on a pricing page. Notice how short each answer is: the template does the organising, so the reporter only has to supply facts.
| Field | Filled in |
|---|---|
| Summary | Pricing cards overlap the FAQ heading at 1,280 px wide in Chrome |
| Where | example.com/pricing, the three plan cards and the "Questions" heading below them |
| Viewport | 1,280 x 720 window, browser zoom 100%, Windows display scaling 125% |
| What it looks like now | Annotated screenshot: the bottom of the Pro card covers the top half of the heading |
| What it should look like | Link to the pricing frame in the design file; 48 px gap between cards and heading |
| Browsers checked | Chrome 129: overlaps. Firefox 131: overlaps. Safari 18 on a Mac at 1,280 px: fine |
| Content that triggers it | Only when the Pro card shows the yearly price note, which adds a third line |
The last row is the one that makes this report excellent, and it came from the template asking. The reporter would not have thought to mention the yearly price note on their own. Because the field was there, they toggled monthly and yearly, saw the overlap appear and disappear, and handed the developer the cause.
The intermittent template earns its keep in a similar way. Suppose a tester reports that saving a draft invoice "sometimes" shows a spinner that never stops. Filled in properly, the report says: 3 of 15 attempts failed; failures at 10:42, 10:51 and 11:07 UTC; all three failures happened when the tab had been in the background for more than a few minutes before clicking Save, and none of the twelve passing attempts did. Same browser, same account, same invoice.
That last observation came straight from the "What differed" field. The developer reads it, suspects an expired session token that the save request does not refresh, looks up the three timestamps in the logs, and finds three 401 responses the front end never handled. Without the timestamps and the background-tab note, that ticket would have sat in "cannot reproduce" for weeks.
Adjust the template to who is reporting
The same template does not suit every reporter, and pretending it does is how you end up with half-filled forms. Think about the four groups who report bugs in most product teams and what you can reasonably ask of each.
- Testers. Hold them to the full template for the kind of bug. Reporting is their job, and complete reports are the measure of it.
- Developers reporting to each other. They often skip the environment because they assume it is shared. Keep the environment field required, even for internal tickets.
- Support agents. They relay what customers say. Give them the core template plus a habit: try to reproduce it in a test account, and record it if they can. A support agent who sends a recording of the bug on a test account has done half the triage.
- Customers. Do not send them a form. Send the four plain questions from the customer reply above, and accept whatever comes back. A support agent can turn the answer into a proper report.
For support teams, this split matters most. The agent who records the bug with VeoRec in a test account and pastes the link into the ticket turns a vague customer email into something a developer can act on, without asking the customer for anything more.
Put the template where reports are written
A template in a wiki page gets used for a month. A template that appears in the box where people type gets used for years. Most trackers let you set a default description or a form for a ticket type; use it.
On GitHub, issue forms go further than a Markdown template. You write a YAML file in .github/ISSUE_TEMPLATE/, and GitHub shows a form with separate fields, dropdowns and required validations, then turns the answers into Markdown in the issue body. At the time of writing, GitHub describes issue forms as being in public preview. The form below asks for the core fields and makes the important ones required.
The chat version is for the bug you spot in passing and do not want to lose: six lines that still contain the core. The customer version asks for four things in plain language, because customers will not fill in a form with "Environment" in it, but they will tell you the page, what they clicked and roughly when.
Big open source projects use the same tactics. React's bug report template, for example, asks for the version, numbered steps, a link to a code example, and current versus expected behaviour, and warns that issues without reproduction steps or code examples may be closed as not actionable. That warning is blunt, but it works: it tells reporters up front which fields matter.
Keep the template short enough that people finish it
Every field you add lowers the chance that the others get filled in properly. Watch for these signs that a template is too long:
- Fields that are blank or "N/A" in most tickets.
- Reports that answer the steps field with "see above".
- People filing bugs in chat to avoid the form.
- The same information appearing in two fields.
- Testers keeping their own private template in a notes app because the official one asks for the wrong things.
A rule that works: make four or five fields required (steps, expected, actual, environment, frequency) and leave the rest optional with good placeholder text. Placeholders teach better than instructions. "Chrome 129, macOS 14, build 2026.10.1" shows the level of detail you want in a way that "Please provide environment details" never does.
Be wary of confirmation checkboxes such as "I have searched for duplicates" or "I am on the latest version". They are cheap to add and easy to tick without reading. One checkbox for the rule that matters most to your project is reasonable; five of them become a ritual. If duplicates are your real problem, a link to a pre-filtered search of open bugs in the form's intro text does more than a checkbox ever will.
Where you can, fill fields automatically. If your app shows a build number, a user ID or a request ID on error screens, make them easy to copy. Some teams add a "Copy debug info" button to the help menu that puts the version, browser and account ID on the clipboard. It is one of the cheapest ways to improve every bug report your product will ever receive.
Make the evidence field easy to fill
The evidence field is where templates most often fall short, because attaching things is fiddly. A screenshot needs to be saved, found and dragged in. A video needs to be small enough for the tracker: GitHub, for instance, limits uploaded videos to 10 MB on free plans and 100 MB on paid plans, which a few minutes of screen recording can pass.
A link avoids both problems. With VeoRec, the share link is already on your clipboard when you stop recording, the video uploaded while you recorded, and the developer does not need an account to watch it. They can also reply with a timestamped comment at the moment it breaks, which keeps the discussion attached to the evidence. Whatever you use, write the template so a link is an acceptable answer, and say what the recording should show. The guide to video bug reports covers what to show in the first ten seconds.
Fill the evidence field in one click Record the bug in the tab where it happens, with your voice and click highlights, and paste the link that is already copied when you stop. See the bug reporting recorder
Check your template against the tickets that went wrong
A template is never finished. Every few months, pull the last twenty tickets that were closed as "cannot reproduce" or that bounced back and forth before anyone started work. For each one, ask which field would have prevented the back and forth.
- Collect the tickets that stalled Filter for "cannot reproduce", "needs info", or tickets with more than five comments before work began.
- Find the first question the developer asked It is usually one of: which account, which browser, what exactly did you click, what did you expect.
- Count the answers If the same question shows up in several tickets, the template is missing that field or its placeholder is unclear.
- Change one thing Add or reword one field, or make one field required. Changing everything at once makes it impossible to see what helped.
- Remove a field nobody uses If a field is blank in most tickets and nobody missed it, delete it. The template gets shorter as it gets better.
This is also how you find out whether you need more variants. If half your stalled tickets are layout bugs on tablets, a dedicated visual template with viewport fields will pay for itself in a week.
What to do next
Copy the general template into your tracker today as the default description for bugs, and add the GitHub issue form if you work in a public repository. Then save the variants somewhere your testers can grab them, or turn them into separate ticket types if your tracker supports that.
If you run a QA function, pair the template with a shared definition of "ready for a developer", so reports that miss the core fields go back to the reporter before they reach the sprint. The QA to developer handoff checklist has one you can adapt.
Frequently asked questions
What is a bug report template?
It is a pre-filled outline for reporting a defect, with fields for the title, environment, steps to reproduce, expected and actual results, frequency, severity and evidence. It makes sure the reporter records what a developer will need, so the ticket can be worked on without follow-up questions.
What fields should be required in a bug report form?
Steps to reproduce, expected result, actual result, environment and frequency cover most needs. Make those required and leave severity, evidence and notes optional but well explained. More required fields usually means lower quality answers in all of them.
How do I add a bug report template to GitHub?
Create a file in the .github/ISSUE_TEMPLATE folder of your repository. A Markdown file gives reporters a pre-filled text body; a YAML file defines an issue form with separate fields, dropdowns and required validations. The YAML example in this post is a working starting point.
Should visual bugs use a different template?
Yes, or at least extra fields. Layout bugs depend on the browser window width, the browser zoom level and the operating system display scaling, and reporters rarely mention them unless asked. Add a link to the intended design so the difference is measurable.
How do I report a bug that only happens sometimes?
Count your attempts and failures, write down the exact time of each failure, and note anything that differed between the attempts that failed and the ones that worked. The intermittent template in this post has fields for all three.