Writing pull requests
Standards for PR titles and descriptions in tldraw/tldraw.
PR title
Use semantic PR titles (Conventional Commits format):
<type>(<scope>): <description>
Types
-
feat
-
New feature
-
fix
-
Bug fix
-
docs
-
Documentation only
-
refactor
-
Code change that neither fixes a bug nor adds a feature
-
perf
-
Performance improvement
-
test
-
Adding or fixing tests
-
chore
-
Maintenance tasks
Scope (optional)
A noun describing the affected area: fix(editor): , feat(sync): , docs(examples):
Examples
-
feat(editor): add snap threshold configuration option
-
fix(arrows): correct binding behavior with rotated shapes
-
docs: update sync documentation
-
refactor(store): simplify migration system
PR body
Use this template:
<description paragraph>
Change type
-
bugfix|improvement|feature|api|other
Test plan
- Step to test...
- Another step...
- Unit tests
- End to end tests
Release notes
- Brief description of changes for users
Description paragraph
Start with: "In order to X, this PR does Y."
-
Keep it specific - avoid vague phrases like "improve user experience"
-
Link related issues in the first paragraph
-
Don't expect readers to also read the linked issue
Change type
-
Tick exactly one type with [x]
-
Delete unticked items
Test plan
-
List manual testing steps if applicable
-
Remove the numbered list if changes cannot be manually tested
-
Tick checkboxes for included test types
Release notes
-
Write brief notes describing user-facing changes
-
Use imperative mood: "Add...", "Fix...", "Remove..."
-
Omit this section entirely for internal work (CI, tooling, tests, etc.) that has no user-facing impact
API changes section
Include when changes affect api-report.md :
API changes
- Added
Editor.newMethod()for X - Breaking! Removed
Editor.oldMethod() - Changed
Editor.method()to accept optionaloptionsparameter
Code changes table
Create a table that includes net LOC changes for each of the following sections. The sum of all rows must match the total PR diff. Omit rows with no changes.
-
Core code — SDK packages (packages/ ) source, excluding tests and API reports
-
Tests — unit tests, e2e tests (.test. , e2e/ )
-
Automated files — generated files (e.g. api-report.api.md , snapshots)
-
Documentation — docs site and examples (apps/docs/ , apps/examples/ )
-
Apps — application code (apps/dotcom/ , apps/mcp-app/ , apps/vscode/ , etc.), excluding e2e tests
-
Templates — starter templates (templates/ )
-
Config/tooling — config files, lock files, lint config, CI, build scripts (eslint.config.* , yarn.lock , etc.)
Code changes
| Section | LOC change |
|---|---|
| Core code | +10 / -2 |
| Tests | +5 / -0 |
| Automated files | +0 / -1 |
| Documentation | +2 / -0 |
| Apps | +3 / -1 |
| Templates | +0 / -0 |
| Config/tooling | +1 / -0 |
Related issues
Search for and link relevant issues that this PR addresses.
Important
-
Never include "Generated with Claude Code" unless the PR directly relates to Claude Code
-
Never use title case for descriptions - use sentence case
-
Never put yourself as co-author of any commits
-
Always include an API changes section if the PR has changes to any api-report.md