Skip to content

How to Write an Effective GitHub Pull Request Template

Most pull requests arrive with a title, a branch name, and nothing else. The reviewer is left to reverse-engineer the intent from the diff, hunt through linked issues that may or may not exist, and ask follow-up questions before they can even start. That back-and-forth is a tax on everyone's time, and it is almost entirely avoidable.

A pull request template shifts the burden upstream. It prompts contributors at the moment they open a pull request to provide the context that reviewers need: what changed, why it changed, whether it breaks anything, and what issue it resolves. Done well, a template makes the review faster, the history more useful, and the project easier to contribute to.

This post covers what a pull request template is, how to set one up in a GitHub repository, and how to write one that contributors will actually fill out.

What Is a Pull Request Template?

A pull request template is a Markdown file GitHub loads into the description field automatically when a contributor opens a new pull request. The contributor sees the template pre-filled in the editor and is expected to replace the placeholder text with information about their change.

GitHub does not enforce that contributors fill out the template. It is a prompt, not a form with required fields. The value comes from making it easy to provide the right context rather than easy to skip it. A template with clear section headers and inline comments that explain what belongs in each section gets filled out. A blank description field does not.

Pull request templates exist alongside issue templates and serve a complementary purpose. Issue templates structure the information contributors provide when reporting a problem or requesting a feature. Pull request templates structure the information contributors provide when proposing a solution. Both reduce the friction of contributing by making the expected format explicit.

Setting One Up

GitHub recognizes a pull request template in three locations within a repository:

  1. PULL_REQUEST_TEMPLATE.md in the repository root
  2. docs/PULL_REQUEST_TEMPLATE.md
  3. .github/PULL_REQUEST_TEMPLATE.md

The .github/ directory is the conventional home. It keeps community health files grouped together and out of the working tree that contributors clone and use. The file must be named PULL_REQUEST_TEMPLATE.md (all caps, matching exactly) and must be on the default branch. GitHub only loads the template from the default branch; a template on a feature branch will not appear until that branch is merged.

Create the file:

mkdir -p .github
touch .github/PULL_REQUEST_TEMPLATE.md

Write the template content, commit it to the default branch, and push. The next time someone opens a pull request against that repository, GitHub will pre-fill the description with the template.

Tip

GitHub also supports multiple pull request templates, placed in a .github/PULL_REQUEST_TEMPLATE/ directory. When multiple templates exist, GitHub does not load one automatically. Instead, contributors specify the template they want by appending a template= query parameter to the pull request URL. For most projects, a single template is the right choice. Multiple templates add complexity that is only justified when a repository has genuinely distinct contribution types with very different review requirements.

Writing an Effective Template

An effective pull request template asks for the information reviewers actually need and nothing more. Each section should have a clear heading, a short HTML comment explaining what belongs there (the comment is invisible in the rendered view), and enough structure to guide contributors without overwhelming them.

The sections that matter most are:

Summary

A short, free-text description of what the pull request does and why. This is the most important section in the template. Reviewers read it first. It should describe the change at a level of detail that makes the diff legible, not a restatement of the title.

### Summary

<!--
    Please provide a clear and concise description of the pull request.
-->

Type

A checklist that maps to Conventional Commits types. This communicates the nature of the change at a glance and enforces consistency with the commit message convention.

### Type

<!--
    Please check the one(s) that applies to this pull request using "x".
-->

- [ ] `fix`: Bug Fix
- [ ] `feat`: Feature or Enhancement
- [ ] `docs`: Documentation
- [ ] `refactor`: Refactoring
- [ ] `chore`: Build, Dependencies, Workflows, etc.
- [ ] `other`: Other (Please describe.)

The types mirror what contributors should be using in their commit messages. When the type in the pull request template matches the commit convention, the reviewer can verify consistency without opening every commit.

Breaking Changes

A binary checklist with a prompt for impact and migration path when the answer is yes. Breaking changes deserve explicit surfacing. A reviewer who misses a breaking change in the diff and does not notice it in the description can merge something that silently breaks downstream consumers.

### Breaking Changes?

<!--
    Please check the one that applies to this pull request using "x".
    If this pull request contains a breaking change, please describe the impact and
    mitigation path.
-->

- [ ] Yes, there are breaking changes.
- [ ] No, there are no breaking changes.

Tests

A checklist confirming that tests have been added or updated, with a prompt for output. This section makes the testing expectation explicit and gives contributors a place to paste the acceptance test output when relevant.

### Tests

<!--
    Please check the one(s) that applies to this pull request using "x".
    For bug fixes and enhancements/features, please ensure that tests and documentation
    have been completed and provide details.
-->

- [ ] Tests have been added or updated.
- [ ] Tests have been completed.

Output:

<!--
    Please provide the output of the acceptance tests as applicable.
-->

Documentation

A checklist confirming that documentation has been added or updated. This matters most for feature additions and behavior changes. An enhancement that ships without documentation creates a gap between what the project does and what contributors and users know it does.

### Documentation

<!--
    Please check the one(s) that applies to this pull request using "x".
    For enhancements/features, please ensure that documentation has been updated.
-->

- [ ] Documentation has been added or updated.

Issue References

Issue references are the connective tissue between a pull request and the work it represents. This section is covered in detail below.

Release Note

A short prose entry suitable for inclusion in a changelog or release notes. This is particularly useful when generating release notes from pull request descriptions, as many teams do. Ask for it here, and it is available when you need it.

### Release Note

<!--
    Please provide context for the release notes.

    For example:

    ```
    - Added support for foo. (#xxx)
    ```
-->

Additional Information

A catch-all section for anything that does not fit elsewhere: screenshots, migration instructions, performance benchmarks, related pull requests in other repositories, or context about why a particular approach was chosen over alternatives.

### Additional Information

<!--
    Please provide any additional information that may be helpful.
-->

Issue References and Linking

The Issue References section deserves special attention because it does more than document a relationship. When written correctly, it creates an automation: GitHub will automatically close the referenced issue when the pull request is merged.

GitHub recognizes specific keywords followed by an issue reference:

Keyword Effect
Closes Links the PR and closes the issue on merge.
Resolves Links the PR and closes the issue on merge.
Fixes Links the PR and closes the issue on merge.

The syntax is the keyword, a space, a #, and the issue number:

Closes #42
Resolves #101
Fixes #7

You can reference multiple issues in the same pull request:

Closes #42
Resolves #101

Each reference must be on its own line. GitHub renders linked issues in the pull request sidebar and, when the pull request is merged into the default branch (or the target branch configured in the issue), closes the referenced issues automatically. There is no manual step required.

Tip

The automatic close only fires when the pull request is merged into the repository's default branch, or into the branch specified in the issue if the issue is tied to a milestone. Merging into a feature or release branch links the issue visually but does not close it. The close happens when the pull request is eventually merged to the default branch.

The keywords are case-insensitive (closes, CLOSES, and Closes are all equivalent), but I use title case for readability. Cross-repository references are also supported: Closes owner/repo#42 will link to an issue in a different repository, though it will only auto-close if the pull request is in the same repository as the issue.

The template section for issue references should explain the mechanic, show the format, and make clear that both Closes and Resolves are valid:

### Issue References

<!--
    Is this related to any GitHub issue(s)? If so, please provide the issue number(s)
    that are closed or resolved by this pull request.

    For bug fixes and enhancements/features, please ensure that a GitHub issue has been
    created and provide the issue number(s) here.

    Please use the 'Closes', 'Resolves', or 'Fixes' keywords followed by a hash and
    issue number. This will link the pull request to the issue(s) and automatically
    close them when the pull request is merged.

    Example:

    Closes #000
    Resolves #001
    Fixes #002
-->

This comment is visible only while editing. In the rendered pull request view, contributors see a blank space, but the reviewer sees the references in the sidebar and on the linked issues.

The Template I Use

Here is the full template I use across my open-source repositories. It incorporates each of the sections above and the Conventional Commits type checklist, with inline HTML comments that guide contributors without cluttering the rendered view.

.github/PULL_REQUEST_TEMPLATE.md
<!-- markdownlint-disable first-line-h1 no-inline-html -->

<!--
    NOTE: Do NOT enter content between the comment markers.

    In order to have the best experience with our community, we recommend that you read
    the code of conduct and contributing guidelines before submitting a pull request.

    By submitting this pull request, you confirm that you have read, understood, and
    agreed to the project's code of conduct and contributing guidelines.

    Please use conventional commits to format the title of the pull request and the
    commit messages.

    For more information, please refer to https://www.conventionalcommits.org and the
    contributing guidelines for this project.
-->

### Summary

<!--
    Please provide a clear and concise description of the pull request.
-->

### Type

<!--
    Please check the one(s) that applies to this pull request using "x".
-->

- [ ] `fix`: Bug Fix
- [ ] `feat`: Feature or Enhancement
- [ ] `docs`: Documentation
- [ ] `refactor`: Refactoring
- [ ] `chore`: Build, Dependencies, Workflows, etc.
- [ ] `other`: Other (Please describe.)

### Breaking Changes?

<!--
    Please check the one that applies to this pull request using "x".
    If this pull request contains a breaking change, please describe the impact and
    mitigation path.
-->

- [ ] Yes, there are breaking changes.
- [ ] No, there are no breaking changes.

### Tests

<!--
    Please check the one(s) that applies to this pull request using "x".
    For bug fixes and enhancements/features, please ensure that tests and documentation
    have been completed and provide details.
-->

- [ ] Tests have been added or updated.
- [ ] Tests have been completed.

Output:

<!--
    Please provide the output of the acceptance tests as applicable.
-->

### Documentation

<!--
    Please check the one(s) that applies to this pull request using "x".
    For enhancements/features, please ensure that documentation has been updated.
-->

- [ ] Documentation has been added or updated.

### Issue References

<!--
    Is this related to any GitHub issue(s)? If so, please provide the issue number(s)
    that are closed or resolved by this pull request.

    For bug fixes and enhancements/features, please ensure that a GitHub issue has been
    created and provide the issue number(s) here.

    Please use the 'Closes', 'Resolves', or 'Fixes' keywords followed by a hash and
    issue number. This will link the pull request to the issue(s) and automatically
    close them when the pull request is merged.

    Example:

    Closes #000
    Resolves #001
    Fixes #002
-->

### Release Note

<!--
    Please provide context for the release notes.

    For example:

    ```
    - Added support for foo. (#xxx)
    ```
-->

### Additional Information

<!--
    Please provide any additional information that may be helpful.
-->

The markdownlint-disable directive at the top suppresses two linter rules that are technically valid complaints against the generated HTML comment structure but do not represent actual problems. If your project does not use markdownlint, that line can be omitted.

The opening HTML comment block (the one with "NOTE: Do NOT enter content between the comment markers") serves as a brief onboarding reminder. New contributors are likely to encounter this template before they have read the contributing guidelines in full. Pointing them to the code of conduct and CONTRIBUTING.md here catches the ones who skipped ahead. It also sets the expectation that commit messages should follow Conventional Commits, which matters because the PR title is often used as the squash commit message.

Putting It Together

A pull request template is a small investment with compounding returns. The first time someone fills it out, you get a better pull request. The hundredth time, you have a repository where every pull request is linked to an issue, every breaking change is flagged before merge, every bug fix has a test output attached, and your changelog almost writes itself.

The key design principles:

  • Keep it skimmable. Section headers let a reviewer jump to what they need. Long prose instructions belong in the comments, not in the visible template.
  • Explain the automation. Most contributors do not know that Closes #42 auto-closes an issue on merge. Tell them. It is a small thing that pays consistent dividends.
  • Tie it to your commit convention. When the Type checklist mirrors your Conventional Commits types, contributors see the connection between their commit messages and the pull request review. It reinforces both practices at once.
  • Do not over-engineer it. A template that takes five minutes to fill out will be abandoned. Ask for what reviewers actually need. Start with the sections above and remove the ones that do not apply to your project.

For the full GitHub documentation on pull request templates, including support for multiple templates and query parameter targeting, see the GitHub documentation on pull request templates.