Understanding Pull Requests (PRs)¶
You hear "Pull Request" everywhere. PR this. PR that. Open a PR. Merge the PR.
But here's the confusing part: Pull Request is a terrible name.
You're not requesting to pull. You're requesting someone to merge your code into their branch.
It should be called a "Merge Request." (GitLab got it right.)
What a Pull Request Really Is¶
A Pull Request is you saying:
"Hey, I made changes on my branch. Please review them and merge them into main."
That's it. You're asking someone(or yourself) to merge your feature branch into 'a' branch (usually main).
---
config:
look: handDrawn
handDrawnSeed: 42
fontFamily: Caveat
---
flowchart LR
A[Your Feature Branch] -->|Pull Request| B[Review Process]
B -->|Approved| C[Merge into Main]
style A fill:#e1f5ff
style B fill:#fff3e0
style C fill:#e8f5e9
Not a pull. It's a merge request with a review process.
The Name Confusion¶
Why Is It Called 'Pull Request'?
GitHub named it from the repository owner's perspective.
Your perspective:
"I want to merge my changes into main."
Repository owner's perspective:
"Please pull my changes into your repository."
The owner "pulls" your changes in. Hence, "Pull Request."
But it's still confusing because:
- You use git pull to get changes
- You use git push to send changes
- But you "open a pull request" to ask for a merge
What others call it: - GitHub: Pull Request (PR) - GitLab: Merge Request (MR) ← Better name - Bitbucket: Pull Request (PR) - Azure DevOps: Pull Request (PR)
Just remember: PR = "Please merge my code" request.
The Basic Flow¶
This is what happens with every PR:
Step 1: Create a Feature Branch
You don't work on main directly. You create a branch.
Now you're on feature/login.
Step 2: Make Changes and Commit
You write code. You commit it.
Maybe you make more commits:
All commits are on feature/login.
Step 3: Push Your Branch
Push your feature branch to GitHub.
Your branch is now on GitHub. But it's not merged into main yet.
Step 4: Open a Pull Request
Go to GitHub. You'll see a yellow banner:
Click it. Fill in: - Title: What your PR does - Description: Why you made these changes - Reviewers: Who should review it
Click "Create pull request."
Now you wait. Someone needs to review your code.
Step 5: Code Review
Reviewers look at your code. They might:
- Approve it: "Looks good!"
- Request changes: "Fix this bug first"
- Comment: "Why did you do it this way?"
You respond. You make more commits if needed:
The PR updates automatically with your new commits.
Step 6: Merge the PR
Once approved, someone clicks "Merge pull request" on GitHub.
Your feature/login branch merges into main.
Done. Your code is in main. Everyone has it.
Step 7: Delete the Feature Branch
The branch is merged. You don't need it anymore.
On GitHub: Click "Delete branch" after merging.
Locally:
Clean slate. Ready for the next feature.
Quick Command Reference¶
| Task | Command/Action |
|---|---|
| Create feature branch | git checkout -b feature/name |
| Push branch | git push -u origin feature/name |
| Open PR | Go to GitHub, click "Compare & pull request" |
| Update PR with changes | git commit + git push |
| Sync with main during PR | git pull origin main or git rebase main |
| Delete local branch after merge | git branch -d feature/name |
| Delete remote branch | git push origin --delete feature/name |
Common Confusion Cleared¶
Confusion 1: Pull Request vs git pull
They're completely different.
| Term | What It Is | Command/Action |
|---|---|---|
git pull |
Git command to fetch and merge | git pull |
| Pull Request | GitHub feature to request code review | Click button on GitHub |
git pull: You get code from remote.
Pull Request: You ask others to merge your code.
Different things. Same word "pull." Confusing.
Confusion 2: Do I Need to Pull Before Opening a PR?
No, but you should sync with main first.
Before opening a PR:
# Make sure main is up to date
git checkout main
git pull
# Update your feature branch
git checkout feature/login
git merge main
# Or rebase for cleaner history
git rebase main
# Then push
git push
Now your PR has the latest code from main. Fewer conflicts.
Confusion 3: Can I Open a PR Without Pushing?
No. PRs are on GitHub. Your branch must be on GitHub.
Confusion 4: Who Merges the PR?
Depends on your team's rules.
- Option 1: Reviewer merges after approving
- Option 2: You merge after getting approval
- Option 3: Auto-merge after tests pass
Check your team's process.
Confusion 5: Can I Keep Committing After Opening a PR?
Yes! The PR updates automatically.
GitHub adds this commit to your existing PR. Reviewers see it immediately.
Real-World Workflow¶
Scenario 1: Your First PR¶
You're new. You want to contribute.
# 1. Fork the repo on GitHub
# 2. Clone your fork
git clone https://github.com/you/repo.git
cd repo
# 3. Create feature branch
git checkout -b feature/fix-typo
# 4. Make changes
# Edit files...
git add .
git commit -m "Fix typo in README"
# 5. Push
git push -u origin feature/fix-typo
# 6. Open PR on GitHub
# Go to your fork, click "Compare & pull request"
# Make sure base is: original-owner/repo main
# And compare is: you/repo feature/fix-typo
# 7. Wait for review
# 8. After merge, update your fork
git checkout main
git pull upstream main
git push origin main
Scenario 2: PR Has Conflicts¶
You opened a PR. Someone else merged code. Now you have conflicts.
GitHub shows:
Fix it:
If there are conflicts:
# Fix conflicts in files
# Look for <<<<<<< markers
# Stage resolved files
git add .
git commit -m "Resolve merge conflicts"
# Push
git push
PR updates. Conflicts are gone.
Scenario 3: Reviewer Requests Changes¶
You got feedback. Need to make changes.
# You're on feature/login
# Make the requested changes
git add .
git commit -m "Address review feedback: improve error handling"
git push
The PR updates. Reviewer gets notified. They review again.
Scenario 4: Keeping PR Updated During Long Review¶
Your PR is open for days. Main keeps moving forward.
Keep your branch updated:
# Get latest main
git checkout main
git pull
# Update your feature branch
git checkout feature/login
git merge main
# Or rebase (cleaner)
git rebase main
# Push (force push if you rebased)
git push --force-with-lease
Your PR stays current with main.
PR Best Practices¶
Do This
- Small PRs: Easier to review. Aim for < 400 lines changed
- Clear title: "Add login feature" not "Update stuff"
- Good description: Explain what and why
- One feature per PR: Don't mix unrelated changes
- Update often: Keep your branch synced with main
- Respond to reviews: Answer questions, make requested changes
- Add tests: Include tests with your code
- Check CI: Make sure tests pass before requesting review
Writing Good PR Descriptions
Bad:
Good:
Add user authentication feature
What:
- Implemented login/logout
- Added password hashing
- Created user session management
Why:
- Required for accessing protected resources
- Improves security with bcrypt hashing
Testing:
- Added unit tests for auth functions
- Tested manually with different users
Closes #123
Advanced PR Concepts¶
Draft Pull Requests
You're not ready for review yet. But you want to show progress.
Create a Draft PR:
On GitHub, click "Create pull request" dropdown → "Create draft pull request"
What it means: - Shows your work in progress - Can't be merged yet - People can comment but won't formally review - You convert to "Ready for review" when done
When to use: - Getting early feedback - CI/CD testing before review - Showing progress to team
PR Templates
Your repo can have a PR template. It auto-fills the description.
Create .github/pull_request_template.md:
## Description
What does this PR do?
## Type of Change
- [ ] Bug fix
- [ ] New feature
- [ ] Breaking change
## Testing
How was this tested?
## Checklist
- [ ] Tests added
- [ ] Documentation updated
- [ ] No linting errors
Now every PR has this template. Consistent PRs across the team.
Automated Checks on PRs
PRs can trigger:
- Tests: Unit tests, integration tests
- Linting: Code style checks
- Security scans: Check for vulnerabilities
- Build checks: Make sure code builds
GitHub shows:
Or:
Can't merge until checks pass (if required).
Protected Branches and Required Reviews
Repositories can protect main:
- Require PR: Can't push directly to main
- Require reviews: Need X approvals before merge
- Require tests: All checks must pass
- No force push: Can't overwrite history
Check settings: GitHub repo → Settings → Branches → Branch protection rules
Force Pushing to PR Branch
You rebased your feature branch. Now you need to force push.
What happens to PR: - PR updates with new commits - Old commit history is rewritten - Comments on old commits might be hidden
Don't Force Push if Others Are Working on Your Branch
You'll mess up their work. Only force push to branches you own.
Squashing Commits
Your PR has 20 commits. You want to merge as 1 commit.
On GitHub: When merging, choose "Squash and merge"
All your commits become one commit in main.
Before:
After squash:
Clean history in main.
Reverting a Merged PR
You merged a PR. It broke production. You need to undo it.
On GitHub: Go to the merged PR → Click "Revert"
This creates a new PR that undoes all changes from the original PR.
Merge this new PR. The code is back to before.
Merge Strategies¶
When you click "Merge pull request" on GitHub, you have options:
Create a Merge Commit
Default option. Creates a merge commit.
History looks like:
* Merge pull request #123 from feature/login
|\
| * Add login tests
| * Implement login
|/
* Previous commit on main
Pros: Preserves full history, shows branch structure
Cons: History can get messy with many PRs
Squash and Merge
Combines all commits into one.
History looks like:
Pros: Clean linear history
Cons: Loses individual commit messages
Rebase and Merge
Replays commits from feature branch onto main.
History looks like:
Pros: Linear history, keeps individual commits
Cons: Rewrites commit SHAs
Your team chooses which strategy to use.
Common PR Mistakes¶
Opening PR from Main
Wrong:
Don't work on main. Use feature branches.
Right:
Giant PRs (500+ Lines Changed)
Reviewers won't read it carefully. Too much to review.
Break it up: - PR 1: Database changes - PR 2: API changes - PR 3: UI changes
Smaller PRs = better reviews = fewer bugs.
Not Testing Before Opening PR
Your PR breaks tests. CI fails. Reviewer can't approve.
Before opening PR:
Merging Your Own PR Without Review
You opened a PR. You merged it yourself immediately.
Why it's bad: No one checked your code. Bugs slip through.
Exception: Tiny docs fixes, emergency hotfixes (with team agreement).
PR Etiquette¶
Being a Good PR Author
- Respond to reviews within 24 hours
- Don't take feedback personally
- Explain your reasoning if you disagree
- Thank reviewers for their time
- Keep PRs updated with main
- Mark conversations as resolved after fixing
Being a Good Reviewer
- Review within 24-48 hours
- Be constructive, not critical
- Explain why, not just what's wrong
- Approve small fixes, don't nitpick
- Test the code if possible
- Say what's good, not just what's bad
What's Next?¶
You understand Pull Requests. They're merge requests with a review process.
Next up: branches in depth. Remote tracking branches. What origin/main really means. How local and remote branches sync.
But now you know: PR is just a fancy way to say "Please review and merge my code."