Pull Requests, Drafts, Linked Issues, Change Sets, and Collaboration Patterns: Concepts, Architecture, and Mental Model
Build a precise mental model of pull requests as GitHub-hosted review and integration objects whose base/head repositories and refs define a proposed change set, while Git commits remain the underlying engineering history.
Learning objectives
- Explain a pull request as a GitHub review/integration resource whose base and head repositories/branches select a proposed change set.
- Relate local branches, hosted branch refs, GitHub pull-request refs, commits, file diffs, mergeability, and review state without conflating them.
- Distinguish draft, ready-for-review, open, closed, and merged states and explain which states are GitHub metadata versus Git history.
- Explain linked Issues, closing keywords, cross-references, task lists, and development relationships with the default-branch rule for automatic closure.
- Separate commit set, file diff, checks, conversation, and deployment evidence so reviewers know which question each surface answers.
-
Inspect a real pull request read-only with the web UI,
gh, Git, and the versioned REST API before changing anything.
1. The problem: a branch is not a review decision
Chapter 04 taught you where branches and remotes live. A pushed topic branch proves that commits exist on a hosted repository; it does not say where those commits are intended to land, whether the change is ready for review, which Issue it addresses, what automation ran, or who accepted the risk. A pull request (PR) supplies that hosted collaboration state around Git refs.
The safest mental model is: Git owns commits and refs; GitHub owns the pull-request resource that points at base/head refs and accumulates review, checks, links, policy state, and timeline evidence. When either ref moves, the PR can change even though the PR number stays the same.
2. Base and head: the coordinates of a proposed integration
flowchart TD L["Local topic branch feature/retry-note"] -->|push| H["Head repo/ref learner/repo:feature/retry-note"] B["Base repo/ref learner/repo:main"] --> PR["Pull request #N"] H --> PR PR --> D["Commit set + \nFiles changed"] PR --> R["Conversation + \nReviews"] PR --> C["Checks / \npolicy evidence"] PR -->|merge later| B
The base is the repository/branch that would receive the change. The head is the repository/branch containing the proposed commits. In a same-repository PR, base and head repositories are the same and branches differ. In a fork PR, the repositories differ. The words base and head are GitHub collaboration coordinates; they do not create new copies of commits.
GitHub shows a three-dot comparison for pull-request changes.
Conceptually, git diff BASE...HEAD compares the merge
base (most recent common ancestor) with the head tip, answering
“what has this topic introduced since it diverged?” That is
different from a two-dot tip-to-tip comparison.
3. A PR also has GitHub-maintained read-only refs
GitHub can expose temporary refs under
refs/pull/NUMBER/. head points at the
latest PR head commit. When GitHub can create a conflict-free test
merge, merge points at a simulated merge result. These
refs are useful evidence for CI and diagnostics; they are not
branches you should push to.
# Read-only example after you know the pull request number.
git ls-remote origin "refs/pull/17/*"
# Fetch the PR head without changing a hosted branch.
git fetch origin refs/pull/17/head
git show --no-patch --decorate FETCH_HEAD
The simulated merge ref can disappear when a PR has conflicts. Its existence is therefore evidence about GitHub’s current test merge, not a permanent commit promised to remain in your repository history.
4. Pull-request state is hosted collaboration state
| State or signal | What it means | What it does not prove |
|---|---|---|
| Draft | Author is explicitly signaling work-in-progress; draft PRs cannot be merged. | That commits are unstable or tests necessarily fail. |
| Ready for review | Author is requesting normal review flow. | That approval exists or merge policy is satisfied. |
| Open | PR is active and not closed/merged. | That it is mergeable. |
| Closed | PR was closed without merge. | That the head commits were deleted. |
| Merged | GitHub recorded integration of the PR through a merge method. | That deployment succeeded. |
| Green checks | Reported checks passed for their tested revision/context. | That review, merge, release, or production deployment succeeded. |
Mergeability is computed from current base/head state and repository
policy. In the REST API, the mergeable field can
temporarily be null while GitHub computes it; a robust
diagnostic client does not interpret null as “blocked
forever.”
5. Draft versus ready is a communication contract, not a Git rewrite
Converting an open PR between draft and ready changes GitHub metadata. It does not create, delete, or rewrite Git commits. Current GitHub behavior allows the PR author or people with write permission to change this stage. Draft PRs are not mergeable, and CODEOWNERS are not automatically requested until the PR is marked ready.
gh pr view 17 --json number,isDraft,state,headRefName,baseRefName
gh pr ready 17
# Later, when the plan supports conversion back to draft:
gh pr ready 17 --undo
6. Linked Issues, closing keywords, cross-references, and task relationships
A pull request can reference work without owning that work.
Mentioning #42 creates context. A supported closing
phrase such as Closes #42 can create a development link
and—when the PR is merged into the repository’s
default branch—close the Issue. GitHub currently
ignores those closing keywords when the PR targets a non-default
branch. That rule matters in release-branch workflows.
| Relationship | Use it for | Lifecycle effect |
|---|---|---|
Plain reference: #42 |
Context/cross-reference | No automatic close |
Closing keyword: Closes #42 |
Explicit “this PR resolves the Issue” relation | Can auto-close when merged into default branch |
| Manual development link | Explicit relationship without editing prose | Can participate in auto-close policy |
| Task list / related work | Breakdown or coordination | Tracks checklist/relationship; not a merge decision |
Closes/Fixes/Resolves
casually. The phrase is automation input, not decorative prose.
7. Commit set, file diff, conversation, checks, and deployment are different evidence planes
flowchart LR PR["PR #N"] --> CM["Commits which commits are proposed?"] PR --> DF["Files changed what content differs?"] PR --> RV["Conversation/reviews what did humans decide?"] PR --> CK["Checks what automated validations reported?"] PR --> IS["Linked Issues what work is related/resolved?"] PR --> DP["Deployment systems what actually shipped?"]
The commit set answers which head-side commits are part of the proposal relative to the base. The file diff answers what content GitHub believes the proposal introduces. Review conversation captures human feedback and decisions. Checks report automated evidence. Deployment records live elsewhere. Reliable change control keeps those meanings separate.
8. Reviewable change sets and stacked/dependent work
A small PR is not automatically good, and a large PR is not automatically bad. The useful unit is a coherent change that a reviewer can reason about, test, and roll back. When one feature truly depends on another unmerged change, teams sometimes use stacked pull requests: PR B is based on PR A’s branch, then its base is retargeted after A merges. This reduces review size but introduces dependency ordering and base-change complexity.
| Pattern | Benefit | Cost / risk |
|---|---|---|
| One coherent PR | Simple lifecycle and one integration decision | Can become too large if scope is not controlled |
| Multiple independent PRs | Parallel review and safer rollback boundaries | Requires clean decomposition |
| Stacked/dependent PRs | Small review units for dependent changes | Ordering, retargeting, and reviewer-context overhead |
9. Permission boundaries: author, reviewer, collaborator, maintainer
Creating a PR requires access to a source/head branch you can propose from. Changing draft/ready stage can be done by the author or someone with write permission. Requesting a specific review requires write access, and the requested reviewer must have appropriate repository access. Public repositories can accept comments/reviews broadly, but administrators can restrict who may submit approving or change-requesting reviews. Fork PRs add another trust boundary: the contributor controls the fork/head branch.
10. Read-only inspection before mutation
\, command substitution such as
$(...), and printf are labeled Git
Bash/Bash/zsh. In PowerShell, use the same Git/gh
arguments on one line or use the backtick for line continuation;
PowerShell-native alternatives are shown for the key file-writing
steps. The GitHub resource semantics are identical.
# Explicit repository removes current-directory ambiguity.
gh pr status -R OWNER/REPO --json number,title,state,isDraft,baseRefName,headRefName,headRefOid
gh pr view 17 -R OWNER/REPO --json number,title,state,isDraft,baseRefName,baseRefOid,headRefName,headRefOid, headRepository,commits,files,reviewRequests,reviewDecision,statusCheckRollup,closingIssuesReferences,url
gh pr diff 17 -R OWNER/REPO --name-only
# Current REST API version.
gh api -H "Accept: application/vnd.github+json" -H "X-GitHub-Api-Version: 2026-03-10" repos/OWNER/REPO/pulls/17 --jq '{number,state,draft,mergeable,base:.base.ref,head:.head.ref,head_sha:.head.sha}'
If the REST response shows mergeable: null, wait
briefly and read again; GitHub may still be computing the test
merge. Do not “repair” anything based on a temporary null.
11. DevOps connection: the PR is a change-control join point
Pull requests are where four systems meet: Git history, human review, automated validation, and repository policy. Later chapters will deepen reviews, merge methods, rulesets, and Actions, but the operating principle starts here: never infer more than the evidence proves. An approval is not a deployment. A green check is not a merge. A Project “Done” status is not a release.
12. Lesson summary
A PR is a hosted object defined around base/head repositories and refs. Its commits and Files changed derive from Git history; draft/ready, links, reviews, checks, and merge state are GitHub collaboration data. Closing keywords can affect Issue lifecycle only under the documented default-branch conditions. Small, coherent change sets make every later control easier to reason about.
Knowledge check
Does creating a pull request copy commits into a new Git repository?
No. The PR references base/head repository branches and adds hosted collaboration state around the Git commits.
Why can git diff main...feature resemble the PR
Files changed view?
The three-dot comparison focuses on changes introduced since the merge base, which is the conceptual basis GitHub uses for PR change review.
What does converting a PR to draft change in Git history?
Nothing. It changes GitHub pull-request stage metadata and merge/review behavior.
A PR targets release/1.2, not the default branch,
and its body says Closes #9. What should you
expect?
Current GitHub documentation says closing keywords are ignored for non-default-branch targets, so do not expect the automatic link/close behavior.
Green checks and an approval exist. Is production deployment proven?
No. Those are review/validation signals; deployment evidence must come from the deployment/release system.
Authoritative references
About pull requests
Branches and pull-request comparisons
Comparing commits
Changing the stage of a pull request
Linking a pull request to an issue
Requesting a pull request review
Approving workflow runs from forks
gh pr
gh pr view
REST API endpoints for pull requests
REST API versions
Keep the academy open
Support free, practical DevOps education.
Every lesson is designed to remain readable in a browser, downloadable from GitHub, and usable without a paid learning platform. Contributions help expand and maintain the curriculum.
0x716c4Ab160C4B66F31a28AE2448BfF68fc3a2ef0
Send only Ethereum/ERC-20 compatible assets to this
address.